Aot/interleaved lance materializer#2236
Conversation
- Introduced `LanceRowIdImageMaterializationStage` for materializing images from Lance stable row IDs. - Added `LanceTableConfig` for shared configuration of Lance tables. - Implemented fetch utilities in `fetch.py` for handling stable-row-id image materialization. - Updated `__init__.py` files to include new classes in the public API. - Added tests for the new materialization stage, ensuring correct processing and error handling. Signed-off-by: Ao Tang <aot@nvidia.com>
Signed-off-by: Ao Tang <aot@nvidia.com>
- Removed the `subprocess_fetch.py` file and associated subprocess fetching logic from the Lance image materialization process. - Updated `LanceRowIdImageMaterializationStage` to eliminate the `fetch_mode` parameter, simplifying the fetcher creation process. - Adjusted tests to reflect the removal of subprocess fallback functionality, ensuring they align with the new fetching approach. Signed-off-by: Ao Tang <aot@nvidia.com>
|
Auto-sync is disabled for draft pull requests in this repository. Workflows must be run manually. Contributors can view more details about this message here. |
Greptile SummaryThis PR adds a Lance image materialization stage (
Confidence Score: 4/5The new materialization stage and fetch utilities are well-structured with thorough validation, test coverage for all major code paths, and correct ordering logic verified through both unit and integration tests. The flagged items are non-blocking quality issues. The core logic — multi-task address collection, combined fetch, per-task
Important Files Changed
Sequence Diagram%%{init: {'theme': 'neutral'}}%%
sequenceDiagram
participant Caller
participant Stage as LanceRowIdImageMaterializationStage
participant Fetcher as _LanceRowIdFetcher / _LanceRowAddressFetcher
participant Lance as Lance Dataset
Caller->>Stage: process_batch(tasks)
Stage->>Stage: _ensure_fetcher() → create fetcher (opens Lance dataset)
Stage->>Stage: _prepare_task() × N (validate, extract addresses)
Stage->>Stage: flatten requested_addresses across all tasks
Stage->>Fetcher: fetch(requested_addresses)
loop retry on _LanceFetchTimeoutError
Fetcher->>Lance: _take_rows / fragment.take (via ThreadPoolExecutor)
Lance-->>Fetcher: pa.Table chunks
Fetcher->>Fetcher: _restore_fetched_original_order
Fetcher-->>Stage: _RowIdFetchResult (tables in original order)
end
Stage->>Stage: _slice_fetched_tables per task
loop for each prepared task
Stage->>Stage: _apply_projection (scatter or replace columns)
Stage->>Stage: _apply_presence (set presence flag)
end
Stage->>Stage: _log_metrics
Stage->>Stage: _maybe_recycle_fetcher_after_success
Stage-->>Caller: list[InterleavedBatch]
%%{init: {'theme': 'base', 'themeVariables': {"darkMode": true, "background": "#0d1117", "primaryColor": "#21262d", "primaryTextColor": "#e6edf3", "primaryBorderColor": "#8b949e", "lineColor": "#8b949e", "textColor": "#e6edf3", "edgeLabelBackground": "#161b22", "actorBkg": "#21262d", "actorBorder": "#8b949e", "actorTextColor": "#e6edf3", "actorLineColor": "#8b949e", "signalColor": "#8b949e", "signalTextColor": "#e6edf3", "noteBkgColor": "#373320", "noteBorderColor": "#d4a72c", "noteTextColor": "#f0e6c0", "labelBoxBkgColor": "#21262d", "labelBoxBorderColor": "#8b949e", "labelTextColor": "#e6edf3", "loopTextColor": "#e6edf3", "activationBkgColor": "#30363d", "activationBorderColor": "#8b949e"}}}%%
sequenceDiagram
participant Caller
participant Stage as LanceRowIdImageMaterializationStage
participant Fetcher as _LanceRowIdFetcher / _LanceRowAddressFetcher
participant Lance as Lance Dataset
Caller->>Stage: process_batch(tasks)
Stage->>Stage: _ensure_fetcher() → create fetcher (opens Lance dataset)
Stage->>Stage: _prepare_task() × N (validate, extract addresses)
Stage->>Stage: flatten requested_addresses across all tasks
Stage->>Fetcher: fetch(requested_addresses)
loop retry on _LanceFetchTimeoutError
Fetcher->>Lance: _take_rows / fragment.take (via ThreadPoolExecutor)
Lance-->>Fetcher: pa.Table chunks
Fetcher->>Fetcher: _restore_fetched_original_order
Fetcher-->>Stage: _RowIdFetchResult (tables in original order)
end
Stage->>Stage: _slice_fetched_tables per task
loop for each prepared task
Stage->>Stage: _apply_projection (scatter or replace columns)
Stage->>Stage: _apply_presence (set presence flag)
end
Stage->>Stage: _log_metrics
Stage->>Stage: _maybe_recycle_fetcher_after_success
Stage-->>Caller: list[InterleavedBatch]
|
| if TYPE_CHECKING: | ||
| from .config import LanceTableConfig |
There was a problem hiding this comment.
LanceTableConfig is only imported under TYPE_CHECKING, so it is absent from the module's namespace at runtime. The @dataclass decorator itself works fine with from __future__ import annotations because annotations are stored as strings. However, anything that calls typing.get_type_hints(LanceRowIdImageMaterializationStage) — common in serialization libraries, dependency-injection frameworks, and documentation generators — will raise NameError: name 'LanceTableConfig' is not defined because it tries to resolve the string annotation in the module globals. Moving the import outside the TYPE_CHECKING guard avoids this without any functional cost.
| if TYPE_CHECKING: | |
| from .config import LanceTableConfig | |
| from .config import LanceTableConfig | |
| if TYPE_CHECKING: | |
| pass |
| msg = "unreachable Lance fetch retry state" | ||
| raise RuntimeError(msg) |
There was a problem hiding this comment.
The
raise RuntimeError("unreachable Lance fetch retry state") is dead code. The for loop spans exactly max_attempts iterations; the last iteration always either returns successfully or hits attempt >= max_attempts and raises RuntimeError. The loop body can never exhaust without one of those two outcomes, so execution never reaches the line after the loop.
| msg = "unreachable Lance fetch retry state" | |
| raise RuntimeError(msg) | |
| # Unreachable: the loop always returns or raises on the final attempt. |
Note: If this suggestion doesn't match your team's coding style, reply to this and let me know. I'll remember it for next time!
Description
Usage
# Add snippet demonstrating usageChecklist