fix(type-inference): map Any to pa.null() for empty container handling (ENG-389) - #155
Conversation
Empty containers ([] / {}) infer element type as typing.Any, which previously
raised ValueError in python_type_to_arrow_type. Now Any maps to pa.null() (Arrow's
canonical unknown-type), and pa.null() maps back to Any on the reverse path.
Closes ENG-389
…/dict[Any, Any] ENG-389
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Codecov Report✅ All modified and coverable lines are covered by tests. 📢 Thoughts on this report? Let us know! |
…ners-infer-as-dictany-any-listany
There was a problem hiding this comment.
Pull request overview
This PR fixes ENG-389 by making typing.Any (commonly produced by empty-container schema inference like list[Any] / dict[Any, Any]) convertible to/from PyArrow types in UniversalTypeConverter, using pa.null() as the Arrow representation for “unknown element type”.
Changes:
- Map
typing.Any→pa.null()in the Python→Arrow type map to preventUnsupported Python type: typing.Anyfor inferred empty containers. - Map
pa.null()→typing.Anyin the Arrow→Python conversion path to ensure clean round-trips and avoid spurious fallback warnings. - Add targeted tests covering conversion, round-trips, and empty-container inference behavior; document the resolved design issue.
Reviewed changes
Copilot reviewed 6 out of 6 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
src/orcapod/semantic_types/universal_converter.py |
Adds Any ↔ pa.null() handling and removes now-unreachable Any-specific error hint. |
tests/test_semantic_types/test_universal_converter.py |
Adds converter + round-trip tests ensuring Any/empty-container inference no longer raises. |
tests/test_semantic_types/test_pydata_utils.py |
Adds tests documenting that empty containers infer as list[Any] / dict[Any, Any]. |
DESIGN_ISSUES.md |
Records ENG-389 (UC1) as resolved with the implemented approach. |
superpowers/specs/2026-06-08-eng-389-empty-container-type-inference.md |
Adds an approved spec describing the problem and chosen solution. |
superpowers/plans/2026-06-08-eng-389-empty-container-type-inference.md |
Adds an implementation plan reflecting the changes and verification steps. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Review round responseCopilot reviewed all 6 changed files and generated no comments — no actionable issues were raised. No code changes are required for this review round. The implementation is complete as submitted:
|
Summary
list[Any]anddict[Any, Any](inferred from empty containers) no longer raiseValueError: Unsupported Python type: typing.Anywhen passed topython_type_to_arrow_typeAny: pa.null()to_PYTHON_TO_ARROW_MAPinUniversalTypeConverter(forward path)pa.types.is_null → Anycheck in_convert_arrow_to_python(reverse path), suppressing a spurious fallback warningAny-specific hint from the error branch in_convert_python_to_arrowDESIGN_ISSUES.mdTest plan
test_any_to_arrow_type—python_type_to_arrow_type(Any) == pa.null()test_list_any_to_arrow_type—list[Any]maps topa.large_list(pa.null())test_dict_any_any_to_arrow_type—dict[Any, Any]maps to expected structtest_null_arrow_to_any_python_type—pa.null()maps back toAnytest_list_any_round_tripandtest_dict_any_any_round_trip— full round tripstest_empty_container_inference_to_arrow_no_error— end-to-end, no exceptiontest_pyarrow_empty_list_with_null_type— PyArrow accepts empty lists for null-typed columnstest_infer_empty_list_schemaandtest_infer_empty_dict_schema— inference already correctCloses ENG-389
🤖 Generated with Claude Code