Repository navigation
Conversation
### What problem does this PR solve? Issue Number: N/A Problem Summary: Add the startup-only enable_local_tvf setting, defaulting to false. Reject LOCAL TVF and FILE TVF with local storage before property parsing or backend access. Explicit opt-in restores each branch's existing behavior. Dedicated regression deployments opt in to retain LOCAL coverage. ### Release note LOCAL TVF and FILE TVF with local storage are disabled by default. Set enable_local_tvf=true in fe.conf on every query-serving FE and restart those FEs to restore the existing behavior. ### Check List (For Author) - Test: 7 focused FE unit tests passed with zero failures or skips; focused FE Checkstyle passed. SQL regression coverage added; runtime validation recorded separately. - Behavior changed: Yes. Local TVF access requires explicit startup opt-in. - Does this need documentation: Yes. Release note documents the default and opt-in.
|
Thank you for your contribution to Apache Doris. Please clearly describe your PR:
|
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69526 Problem Summary: Canonical glob results were not checked against the secure root, and LOCAL Lance bypassed local-path validation. Check the canonical root and resolved paths, enforce ADMIN/OPERATOR before file access, validate Lance schema and scan paths, and preserve LOCAL/S3 range types. Reject local storage selected through S3 Lance before dataset opening. ### Release note Enabled LOCAL reads remain restricted to user_files_secure_path and require ADMIN/OPERATOR. LOCAL Lance accepts only local paths inside that directory. The existing default-disabled startup gate is retained. ### Check List (For Author) - Test: 26 focused FE tests, Checkstyle and changed-line clang-format 16 passed. BE tests could not build because the local dependency package lacks libgoogle_cloud_cpp_oauth2.a. - Behavior changed: Yes, enforce secure local path containment and authorization after explicit opt-in. - Does this need documentation: Covered by the PR release note.
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69526 Problem Summary: FILE_LOCAL also identifies existing local Lance catalogs. Apply the new secure-root check only to the documented LOCAL TVF version-zero ranges, retaining fixed-version catalog warehouse paths. Add catalog compatibility coverage, qualify the nested DatasetKey type in the new tests, and bind the existing glob fixture to its own root across build profiles. ### Release note Fixed-version local Lance catalog reads keep their existing warehouse paths. ### Check List (For Author) - Test: changed-line clang-format 16 passed. Local BE execution remains blocked by missing GCS dependencies; targeted compilation diagnostics also identify an existing Lance-C SDK API mismatch. Existing final FE changes have 26 passing tests. - Behavior changed: Scope the new path check to LOCAL TVF. - Does this need documentation: Covered by the PR release note.
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69526 Problem Summary: A rejected glob result could disclose its expanded filename through a canonical-path error or a failed resolution of a dangling symlink. Return one generic target-validation error for both cases before the status reaches SQL clients. Extend temporary-directory tests to assert that neither real target names nor paths appear in errors. ### Release note LOCAL path validation errors no longer reveal expanded or resolved target filenames. ### Check List (For Author) - Test: Targeted compilation diagnostics passed for the two modified C++ files. Full BE execution remains blocked by the previously recorded Lance-C SDK/GCS dependency gaps. Modified lines pass clang-format 16; independent Standards and Spec review found no remaining issue in this supplement. - Behavior changed: Yes, target-validation errors use a generic message. - Does this need documentation: Covered by the PR release note.
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69526 Problem Summary: S3 Lance could open a local dataset through BrokerProperties because the entry point rejected only LocalProperties. Validate the final dataset URI before loading metadata. Allow the pinned SDK's remote providers and reject local aliases and malformed authorities that could fall back to local paths. Keep valid ports, underscore buckets, hostless GooseFS and normalized S3/OSS HTTP locations working without changing catalog or non-Lance paths. ### Release note S3 Lance rejects local dataset URIs and malformed remote URI authorities before opening a dataset, regardless of storage-property selection. ### Check List (For Author) - Test: 31 focused FE unit tests passed on this branch; changed Java files pass Checkstyle and git diff --check passes. - Behavior changed: Yes. S3 Lance requires a valid supported remote URI. - Does this need documentation: No additional documentation for this security validation; the parent PR's configuration documentation is pending.
|
/review |
There was a problem hiding this comment.
Request changes: two verified findings are attached inline: a P1 remote-URI validation bypass that reaches local Lance storage, and a P2 regression for valid percent-encoded LOCAL Lance file URIs. There were no existing inline threads or additional user focus points.
Reviewed all 20 changed files at a7a0f19, with independent BE, FE/configuration, and URI/path risk reviews. The policy goal is only partly achieved: direct LOCAL/FILE-local authorization and top-level glob/dataset containment improve, but the S3 URI check still permits local fallback.
Critical checkpoints:
- Goal and proof: traced constructor authorization, file discovery, schema RPC, range construction, SDK metadata open, dataset/cache key, scan and close. The two inline cases remain incorrect; added tests omit both.
- Scope and clarity: changes are focused on startup policy, path/URI validation, range identity and supporting tests/configuration.
- Concurrency and locks: no new thread, lock, lock order or shared production mutation; existing query/scanner and RPC contexts remain in use.
- Lifecycle/static initialization: local URI values, existing dataset RAII and session ownership remain intact; no new cross-TU initializer dependency or cleanup defect found.
- Configuration: enable_local_tvf is false by default and nonmutable; ConfigBase rejects runtime updates. Enabling requires configuration and restart on every query-serving FE. Seven regression deployments explicitly opt in.
- Compatibility: default-off and ADMIN/OPERATOR requirements are intentional behavior changes. Existing fixed-version catalogs retain their warehouse paths; the encoded file-URI regression needs correction. Mixed deployments require upgrading the nodes that enforce the policy.
- Protocol definitions: no Thrift/protobuf IDs, required fields, function symbols or persistent format definitions changed.
- Parallel paths: checked LOCAL, FILE delegation, non-Lance glob, Lance schema/latest scan/cache reuse, remote fixed snapshots and catalog/search/row-ID paths. HDFS/HTTP TVFs reject Lance in common parsing.
- Conditional logic: explicit per-range LOCAL/S3 identity and scan-level fallback agree with their producers; positive catalog versions intentionally bypass LOCAL-TVF containment. The URI predicate has the documented P1 exception.
- Test coverage: inspected BE containment/symlink/root/schema/scan tests, FE gate/privilege/revocation/URI/range tests, and LOCAL/FILE SELECT/EXPLAIN regression checks. Mocked loader acceptance does not prove Rust provider dispatch; real remote reads and full Groovy execution were not verified here.
- Expected results: no golden result files changed; added row IDs and file sizes agree with the committed fixture and literals.
- Observability/errors: new Status failures propagate through existing schema/RPC/scan boundaries; rejected expanded targets use generic errors. Existing open/version/URI profile counters remain. No new execution stage requiring new metrics was introduced.
- Transactions/persistence/failover: not affected; no EditLog, publish, delete-bitmap or visible-version change.
- Data writes/atomicity/crashes: production changes are read-only; no new transaction, write rollback or crash-recovery protocol.
- FE/BE propagation: schema already tags file_type; execution now preserves the TVF identity in the existing optional range field. Both LOCAL schema and execution use the resolver before opening/cache access.
- Performance/memory: added validation runs at construction or dataset/split setup, outside row loops; no significant new allocation, unbounded cache or read amplification identified.
- Other checks: decoding, NULLs, row alignment, predicates and EOF behavior are unchanged. Top-level directory containment does not provide an SDK-wide sandbox for preexisting dataset-internal symlinks; no introduced defect was established for that separate limitation.
Static source review only: no builds or tests were run and no product files were changed. No unresolved review candidate or uncovered changed file remains. Operator documentation is still pending according to the PR description; the release note describes the intended startup migration.
Review converged after 3 round(s).
BE UT Coverage ReportIncrement line coverage Increment coverage report
|
BE Regression && UT Coverage ReportIncrement line coverage Increment coverage report
|
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69527 Problem Summary: Apply the startup-only LOCAL gate to INSERT and EXPLAIN INSERT. Escape the canonical secure root as a literal glob prefix. Validate raw S3 Lance ports and IPv6 before SDK access; decode file URI paths once after removing query and fragment while preserving bare paths. ### Release note LOCAL TVF INSERT and EXPLAIN INSERT honor enable_local_tvf. Secure directories containing glob metacharacters remain usable. LOCAL Lance preserves percent-encoded file URI identity; malformed remote Lance authorities are rejected before SDK access. ### Check List (For Author) - Test: Unit Test: 35 FE and 11 BE selected tests passed; relevant Java Checkstyle, clang-format 16, and git diff --check passed. Regression assertions added, full Groovy not run. - Behavior changed: Yes, enforce the existing LOCAL startup setting at the write entry and preserve valid local path identity. - Does this need documentation: Yes, the original PR release note describes the startup opt-in requirement; documentation PR remains pending.
|
/review |
1 similar comment
|
/review |
There was a problem hiding this comment.
Static review of 90a3a93 found one new P2: LOCAL Lance file URIs with parent segments can select a different in-root dataset because filesystem symlinks are resolved before URL dot-segment normalization. The inline comment contains the concrete case and fix direction.
Existing threads were independently revalidated: P1 4361485535 is fixed by original-port digit validation and IPv6 validation; P2 4361485545 is fixed for its escaped-versus-literal path cases by one-pass file-URI decoding. Neither is reposted or carried as a current blocker. The new finding concerns URL dot-segment ordering in the newly added filesystem helper, independently of the earlier percent-decoding issue. No additional user focus was supplied.
Critical checkpoint conclusions:
- Goal and proof: startup opt-in, early read authorization and pre-open containment are implemented; the new P2 is the remaining identified correctness defect. Focused tests exist but omit its dot-segment/symlink interaction.
- Scope: changes are focused on LOCAL admission, secure paths, Lance URI identity and regression opt-ins.
- Concurrency and locks: validation uses existing planning/RPC/scanner contexts and request-local state; no new threads, locks, lock order or lock-held heavy work.
- Lifecycle and static initialization: dataset ownership/cleanup is unchanged; no new resource cycle or cross-translation-unit initializer dependency.
- Configuration: enable_local_tvf defaults false and is immutable at runtime. Enabling it requires configuration and restart on every query-serving FE, as described in the PR.
- Compatibility: the default-disable behavior is intentional; positive-version catalog routing is preserved. File-URI compatibility needs the inline correction. No wire/storage format or function-signature change.
- Shared definitions: no Thrift/protobuf definitions changed; cross-release field-ID checks are not applicable.
- Parallel paths: LOCAL/FILE reads, INSERT/EXPLAIN, schema/execution, shared-storage/single-BE, cloud/shared-nothing selection, S3/Broker normalization and fixed-version catalogs were traced.
- Special conditions: range-type precedence, version-zero LOCAL confinement, catalog exceptions, literal glob roots, provider allowlist, signed ports and IPv6 checks match their producers and pinned SDK behavior, apart from the inline URI-normalization defect.
- Tests: inspected all changed FE/BE tests and the Groovy suite. Positive/negative admission, privilege ordering, aliases/authorities, range identity, symlink/glob roots and escaped URI cases are represented; dot segments with symlinks are missing. Opted-in pipeline configurations normally exercise the enabled Groovy branch.
- Results: no expected-result files changed; new expectations agree with inspected inputs. Author-reported test runs were not independently executed.
- Observability: admission errors are explicit; generic containment errors avoid exposing expanded target names. Existing reader profiles and failure propagation remain in place.
- Persistence and transactions: no EditLog, transaction publication, visible-version, delete-bitmap or persisted metadata changes.
- Data writes and crashes: only sink admission changes; external-file write atomicity and crash/cleanup behavior are otherwise unchanged.
- FE-to-BE transport: existing optional file_type is now explicit on Lance TVF execution ranges; schema requests were already tagged, and catalog/remote snapshot versions remain fixed.
- Performance and memory: bounded planning/per-open path validation introduces no per-row allocation, retained buffer or cache amplification; per-match canonicalization is required for glob confinement.
- Further review: rechecked parser/provider dispatch, cached dataset opens, bare percent/query/fragment identity, legacy tags, authorization initialization and symlink resolution. No additional substantiated defect or unresolved code-analysis question remains.
Coverage: all 22 changed paths were reviewed, with two complete-scope reviewers and a separate remote-URI risk reviewer. Static inspection only: no Doris builds, test suites or live SDK/data scans were run; isolated filesystem path demonstrations supported the inline finding. Source files and submodules were unchanged. Runtime interoperability and full regression execution remain validation limits, not claimed results.
Review converged after 2 round(s).
There was a problem hiding this comment.
Static review of all 22 changed paths at 90a3a93aae68c021024842b1f19e32965e730508, with independent BE, FE, and URI-risk coverage.
One new P2 finding is inline: valid uppercase/mixed-case file: schemes now fail LOCAL Lance schema discovery. The existing dot-segment/symlink finding still applies and was not reposted. The earlier signed-port/IPv6 bypass and percent-decoding finding are fixed for their reported cases. No existing P0/P1 was independently confirmed to remain applicable, so existing_blocking_comment_ids is empty. Review opinion: URI compatibility still needs correction.
Individual critical-checkpoint conclusions:
| Checkpoint | Conclusion |
|---|---|
| Goal and functional proof | Default-off LOCAL/FILE-local reads and LOCAL writes, early read authorization, canonical containment, and remote/local Lance routing are implemented on traced paths; new and existing URI compatibility defects remain as identified above. Tests are present, but were not executed here. |
| Scope and clarity | Production changes focus on admission, path resolution, and range identity, with matching tests/configuration opt-ins. |
| Concurrency and locking | New state is request-local or immutable after startup. Existing heavy-pool/scanner tasks remain; no new threads, locks, lock order, or lock-held I/O was introduced. |
| Lifecycle and static initialization | Schema dataset RAII and scan/session ownership remain intact; no new ownership cycle, cache handle, or cross-TU static dependency found. |
| Configuration | enable_local_tvf=false is startup-only because ConfField defaults to nonmutable. Every serving FE must opt in and restart; seven regression deployment configs opt in. |
| Compatibility and upgrades | Default-disable is intentional and documented. Existing optional range tags are reused; legacy scan-level fallback, positive-version catalog warehouses, and remote options remain. File-scheme compatibility has the new inline regression. No storage-format/symbol change. |
| Thrift/protobuf definitions | None changed; cross-release ID/enum comparison is not applicable. |
| Parallel paths | Checked LOCAL, FILE delegation, SELECT/EXPLAIN, INSERT/EXPLAIN, schema/scan/cache opens, non-Lance glob, remote range override, catalog routing, and the existing LOCAL-backed metadata-glob caller. |
| Special conditions | Comments explain version-zero LOCAL routing, per-range type precedence, Broker passthrough, GooseFS authority exception, and port/IPv6 validation. The reported URI defects identify remaining incorrect conditions. |
| Test coverage | FE tests cover gates/auth/delegation/sinks/range tags/remote URI rejection; BE tests cover glob classes, symlinks, literal roots, NUL, relative/escaped datasets, schema/scan identity, and catalog/remote routing. Case-insensitive scheme and known dot-segment identity cases are missing. The Groovy disabled branch requires a separately disabled deployment; unit tests cover disabled admission. |
| Changed expected results | No .out files or data fixtures changed. Added row/error assertions agree with inspected control flow; execution was not verified. |
| Observability | Errors propagate through exceptions/Status; glob RPC publishes entries only on overall success. Existing schema warnings and dataset URI/version profiles remain; no new metrics-critical operation introduced. |
| Transactions and persistence | No EditLog, internal visible-version, delete-bitmap, transaction, or failover protocol change. |
| Writes and crash behavior | LOCAL sink gate runs before writer creation; existing external-write/cleanup and nontransactional semantics are unchanged. No new crash-cleanup path found. |
| FE/BE propagation | Lance TVF ranges explicitly carry existing FILE_LOCAL/FILE_S3 tags; schema ranges already did. URI/version/fragments/options and consumer precedence were inspected. No new transmission field. |
| Performance and memory | Validation is linear in URI/path or match count at planning/discovery/open, outside row/batch loops. No new significant untracked buffer, unbounded cache, or repeated per-row work found. |
| Other concerns and user focus | No additional user focus was supplied. Every candidate/risk was accepted, deduplicated, or dismissed with evidence; no concrete unresolved static-review coverage gap remains. |
Validation limits: static inspection only, including pinned SDK/parser primary sources. No builds, tests, runtime reproduction, deployment restart, real remote-store reads, or exhaustive parser fuzzing were performed. Author-reported test results were treated as context, not independent validation.
Review converged after 2 round(s).
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69527 Problem Summary: LOCAL Lance canonicalization followed symlinks before URL dot-segment normalization, so a valid file URI could open a different in-root dataset. Uppercase file schemes were rejected. Normalize the actual file URI scheme, separators and raw dot segments before one-pass decoding and filesystem containment; preserve bare path behavior. ### Release note LOCAL Lance preserves file URI dataset identity for dot segments, case-insensitive schemes and raw URI separators while retaining secure-root containment. ### Check List (For Author) - Test: 13 selected BE filesystem/Lance tests passed with fresh XML, zero failures/skips and unchanged sources. New regressions fail before the fix, including actual schema and row-value mismatch. Changed-line clang-format16 and git diff --check passed. FE source is unchanged. - Behavior changed: Yes, restore valid file URI identity without changing bare paths, remote TVFs or fixed-version catalogs. - Does this need documentation: The original PR documents the LOCAL startup opt-in; no additional public configuration or syntax is introduced.
|
/review |
There was a problem hiding this comment.
Static review of #69527 at 33cbacc reports two new P2 dataset-identity regressions in LOCAL Lance file-URI resolution. Both can silently select another existing dataset inside the allowed root. The inline comments provide independent triggering inputs and fix directions.
The four existing threads were independently revalidated: signed ports/malformed IPv6 (4361485535), percent decoding (4361485545), dot-segment/symlink order (4365942546), and case-insensitive schemes (4365978318). Their reported triggers are fixed at this head; no existing P0/P1 remains confirmed. These new findings require neither percent escapes, dot segments nor mixed-case schemes and are distinct from those threads. No additional user focus was supplied.
Critical checkpoints:
- Goal and evidence: default-deny LOCAL/FILE-local admission and canonical containment are implemented; SDK-compatible file-URI identity still fails in the two inline cases. Added tests exercise the intended gates and prior fixes but omit these collisions.
- Scope: changes are focused on admission, range identity, filesystem validation and matching tests/configuration.
- Concurrency: no new threads or locks. Glob/schema RPCs use the existing heavy-work pool; readers own per-scan state, and shared session initialization retains call_once. No new lock-order or heavy-under-lock issue found.
- Lifecycle/static initialization: validation precedes schema and cached dataset opens; scanner/dataset release order is preserved. No new persistent owner, reference cycle or cross-TU static dependency.
- Configuration: enable_local_tvf defaults false, is immutable, and explicitly requires every FE restart. Pipeline opt-ins are deliberate.
- Compatibility: existing file-type fields and values are reused, including scan-level fallback; positive-version catalog and remote ranges preserve their providers. No new storage-format or symbol incompatibility found.
- Thrift/proto: no definitions changed; cross-release ID comparison is inapplicable.
- Parallel paths: LOCAL and FILE delegation, SELECT/EXPLAIN, legacy construction, independent INSERT/EXPLAIN sink binding, schema RPC, execution ranges, remote TVFs and local catalogs were traced. Existing sink ADMIN/LOAD admission remains.
- Conditions: comments explain version-zero LOCAL handling, per-range precedence, canonical containment and final remote-URI validation. Both new URI identity findings apply to schema discovery and scanning.
- Tests: reviewed positive/negative admission, privilege revocation, URI normalization, symlink/glob containment, literal root operators, remote/catalog preservation, range tags and actual scanner assertions. Disabled-sink regression coverage is conditional on configuration; binder unit tests cover it independently. Add distinguishable datasets and bare-path controls for the two new cases.
- Results: no expected-result files changed. Assertions/error text were checked statically. No builds, tests or benchmarks were run; prior thread reports are not claimed as this invocation's validation.
- Observability: existing errors and Lance URI/version/open profiling remain. Admission checks do not need new metrics; no added logging/counter defect found.
- Persistence/transactions: no EditLog, transaction-state or visibility-protocol changes. Fixed snapshot and delete/bitmap semantics are untouched.
- Writes/crashes: the independent LOCAL sink gains admission checking; existing writer/coordinator cleanup and file-output atomicity are unchanged. No new crash-related leak/deadlock identified.
- FE/BE variables: execution now explicitly carries LOCAL/S3 range identity; schema requests already carry it. No additional variable or serialization path is introduced.
- Performance/memory: added parsing/canonicalization occurs during admission or split setup rather than per row; no new large retained allocation, redundant dataset open or hot-path regression was substantiated.
- Further sweep: checked parser/provider mismatches, rootless URLs, whitespace preprocessing, second parsing of canonical paths, symlink/dot/decode ordering, partial glob-result leakage and metadata-count/catalog exemptions. No unresolved candidates or uncovered changed paths remain.
Coverage includes all 22 changed files and their relevant upstream/downstream paths. Findings are supported by checked-out code and pinned SDK sources; runtime behavior remains unverified under the static-only contract.
Review converged after 2 round(s).
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69527 Problem Summary: LOCAL Lance file URLs without a slash were resolved relative to the secure root, URI whitespace was treated as literal data, and bare dot segments followed symlinks before SDK lexical normalization. Match file URI preprocessing and absolute-root semantics, and normalize bare paths only at the LOCAL Lance entry before canonical containment. Preserve literal bare whitespace, encoded spaces, glob behavior and existing remote/catalog routing. ### Release note LOCAL Lance preserves dataset identity for rootless file URLs, raw URI whitespace and bare dot segments while retaining secure-root containment. This does not add FE execution support for rootless Hadoop paths. ### Check List (For Author) - Test: 13 selected BE filesystem/Lance tests passed with fresh XML, zero failures/skips and unchanged sources. New regressions fail before the fix, including actual schema and row-value mismatch. Changed-line clang-format16 and git diff --check passed. FE source is unchanged. - Behavior changed: Yes, restore valid file URI identity without changing bare paths, remote TVFs or fixed-version catalogs. - Does this need documentation: The original PR documents the LOCAL startup opt-in; no additional public configuration or syntax is introduced.
|
/review |
There was a problem hiding this comment.
Three new findings: one P1 admission bypass, one P2 LOCAL Lance home-path regression, and one P3 drive-style file-URL compatibility regression. Request changes for the P1; all verified findings are inline.
Reviewed exact head 0d96b297bd650f18441aa054b9a4cc49cedb6ed5 against the supplied merge-base diff. All 22 changed files were covered by the main review, separate FE/BE complete reviews, and an additional parser/admission risk review. The review converged in two rounds on this unchanged finding set.
All six existing threads were independently revalidated as fixed: signed-port/mapped-IPv6 local fallback, percent decoding, URL dot-segment/symlink ordering, case-insensitive file schemes, rootless file URLs, and URL whitespace/control preprocessing. No existing P0/P1 remains applicable, so no existing blocking IDs are carried forward and none of those issues is reposted. There was no additional user-provided focus.
Critical checkpoint conclusions:
| Checkpoint | Conclusion |
|---|---|
| Goal and functional proof | Default LOCAL admission and canonical containment improve, but the JNI route bypasses the new switch and two SDK path identities regress. New tests cover the principal named routes; they omit these three cases. |
| Scope and clarity | Changes remain focused on admission, path handling, scan identity and regression opt-in. |
| Concurrency and locks | No new workers, shared query state, lock ordering or heavy work inside locks; existing schema/scanner and glob execution contexts remain. |
| Lifecycle and initialization | Early auth sees initialized superclass state; later auth rechecks resource/global privileges. Schema RAII, reader dataset ownership, session initialization and C-string lifetimes remain valid. No new cross-TU dependency or reference cycle. |
| Configuration | enable_local_tvf=false is intentionally startup-only; ConfField defaults to immutable and ConfigBase rejects runtime changes. Every serving FE must be configured/restarted. |
| Compatibility | No wire schema, function signature or storage-format change. Existing range file-type tags are reused. Positive-version catalog warehouses retain routing; complete enforcement requires upgraded BEs. |
| Thrift/protobuf definitions | None changed; no cross-branch field-ID/enum comparison is applicable. |
| Parallel paths | LOCAL/FILE reads, INSERT/EXPLAIN, schema/scan, native/JNI writers, S3/Broker normalization and fixed-version catalogs traced. The JNI omission is inline. |
| Special conditions | URI-only preprocessing/decode/dot ordering and version-zero LOCAL dispatch are justified; tilde and drive exceptions need the inline fixes. |
| Test coverage | BE tests include real schema/rows, containment, glob classes, symlinks and URI collisions. FE tests cover admission/tagging; S3 positives mock metadata loading. JNI bypass, tilde and drive cases are missing. |
| Expected results | Changed assertions and expected rows/errors match their fixtures; no generated result files changed. |
| Observability and errors | New failures are explicit and expanded denied paths are sanitized. Existing dataset profiles/errors remain; no new per-row metrics/logging requirement. |
| Transactions and persistence | No EditLog, native visibility, delete bitmap or transaction protocol changes; no failover persistence added. |
| Writes and crash behavior | Named LOCAL writes are gated before property validation. Existing external-file write atomicity/lifetimes are unchanged; JNI can still truncate a local target through a remote name. |
| FE-to-BE propagation | Schema and execution retain LOCAL/S3 identity through the existing file_type field, including FILE delegation. No new transmitted variable. |
| Performance and memory | Path checks occur before dataset open/key reuse, with no new per-row work or large allocation. No further substantiated performance or memory defect. |
| Other risks and disposition | All R1-R3 risks and candidates are accepted, deduplicated or dismissed with evidence in the ledger; no unresolved review-scope candidate remains. |
Static review only: no builds or tests were run. SDK behavior was checked against pinned primary sources. Full Groovy execution, disabled-mode SQL/JNI reproduction and real remote data reads remain unexecuted; inspected test code and the PR author's reported runs are not independent runtime validation. These execution limits do not imply uncovered static scope.
Review converged after 2 round(s).
…ntity
### What problem does this PR solve?
Issue Number: N/A
Related PR: apache#69527
Problem Summary: Remote-named TVF sinks could select the built-in local JNI writer while LOCAL was disabled. Apply the shared LOCAL admission check before sink analysis and final sink binding, matching the loader's class-name representation. LOCAL Lance also needs to preserve the pinned SDK's home aliases and file-URL drive components before canonical containment; add distinguishable schema and scan fixtures without changing ordinary glob or remote/catalog routing.
### Release note
The LOCAL startup setting covers sinks using the built-in local JNI writer under S3/HDFS names. LOCAL Lance preserves supported home aliases and file URL drive identity inside the secure directory.
### Check List (For Author)
- Test: 39 selected FE tests and 15 selected BE filesystem/Lance tests passed through standard wrappers with fresh XML, zero failures/errors/skips and unchanged sources. Java Checkstyle, changed-line clang-format16 where applicable and git diff --check passed.
- Behavior changed: Yes, enforce the existing default-disable policy and retain valid local dataset identity.
- Does this need documentation: The original PR documents the startup opt-in; this supplement adds no new configuration or syntax.
|
/review |
There was a problem hiding this comment.
Request changes: one new P1 remains in effective local-storage admission. A native HDFS sink can select fs.defaultFS=file:/// while LOCAL TVF is disabled, creating BE-local files; its optional cleanup can recursively delete an FE-local directory. The inline finding contains the concrete LOAD-user input and complete call-chain evidence. This is a distinct native path from the already-reported JNI writer issue.
Reviewed exact head d1ec854a5d1a1b6751583f0f900b805b9a702fee against the supplied authoritative merge-base diff: all 23 changed paths, all FE/BE tests and regression configurations, and relevant upstream/downstream paths. No additional user focus was supplied. Static inspection only: no builds, tests, runtime reproductions, source modifications or submodule initialization were performed.
The two existing P1 comments were independently revalidated and their reported instances are fixed: 4366199143 now gates the built-in LocalFileJniWriter across remote sink names, including slash/dot/NUL class identity; 4361485535 now rejects signed ports and malformed IPv6 before remote Lance metadata access. Therefore existing_blocking_comment_ids is empty. Existing BE percent-decoding, dot/symlink, case, whitespace, rootless-URL, drive and home-alias scenarios are also addressed; none is reposted.
Critical checkpoints:
- Goal and evidence: default-deny LOCAL/FILE-local reads, early ADMIN/OPERATOR authorization, secure expanded-path containment, and consistent LOCAL Lance schema/scan identity are implemented. The native HDFS admission gap prevents the complete local-storage protection goal. Tests exercise the intended controls but omit this native local-provider case.
- Scope and clarity: production changes are focused on admission, path resolution and range identity, with corresponding unit/regression coverage and explicit CI opt-ins.
- Concurrency and locks: no new threads, lock acquisitions, lock-order protocol or shared mutable request state is introduced. Added filesystem checks use per-call state; passwd fallback is reentrant. Existing execution concurrency remains unchanged.
- Lifecycle and static initialization: no new cross-TU initializer dependency, reference cycle or retained owner is introduced. Dataset ownership, session initialization and scanner close order remain intact.
- Configuration:
enable_local_tvf=falseis intentionally startup-only; every serving FE must be restarted after enabling it. The annotation is not mutable, and dynamic configuration rejects immutable settings. Regression deployments explicitly opt in. - Compatibility: default-disabled behavior is an intentional operational change requiring the documented FE rollout action. No persisted storage format or protocol definition changes; existing optional range types are reused, and fixed-version catalogs preserve their URI routing. Older FE binaries cannot enforce the new FE admission policy during a mixed-version deployment.
- Thrift/protobuf definitions: no
gensrcfiles changed, so no field-ID/enum compatibility change is present. - Parallel paths: LOCAL and FILE delegation, schema and cached-scan opens, legacy scan-level and modern range tags, native/JNI sinks, remote S3 normalization/broker passthrough, HDFS/HTTP Lance rejection and fixed-version catalogs were traced. The one uncovered effective-provider admission path is reported inline.
- Special conditions: LOCAL/version-zero validation and positive-version catalog exclusion match their callers. URI-only preprocessing preserves ordinary bare-path spelling; root escaping and component containment cover glob operators and symlinks. Effective native HDFS selection needs the additional admission check.
- Test coverage: inspected positive/negative FE admission, privilege revocation, JNI aliases, remote URI controls, glob/symlink/root containment, and real Lance schema/key/row identity fixtures. End-to-end Groovy execution, real remote-service reads and the new native-HDFS reproduction were not run under this static-only contract.
- Expected results: no generated
.outfiles changed. Inspected assertions and Groovy backend-error expectations match their code paths; author-reported passing runs were not treated as validation performed here. - Observability: new denials provide actionable enablement/privilege errors and intentionally hide expanded external target names. Existing RPC status and reader profiles remain available; no new hot-path metric requirement was identified.
- Transactions and persistence: no EditLog, transaction commit, visible-version or delete-bitmap protocol changes are introduced. Positive catalog snapshot routing remains unchanged.
- Writes and crash behavior: accepted requests retain the existing sink lifecycle and its nontransactional file semantics. New admission normally precedes cleanup/execution, but the reported native HDFS bypass permits local side effects before those protections apply; no separate crash/cleanup regression was verified.
- FE-BE propagation: no new wire variable is added. Explicit Lance range
file_typenow matches the schema request; per-range identity takes precedence over legacy scan parameters, and URI/version/options remain in dataset cache keys. - Performance and memory: parsing/allocation is bounded by input size and path resolution occurs during schema/dataset setup rather than per output row. No new substantial retained allocation, redundant batch operation or material performance regression was verified.
- Additional issues and limits: the final missed-issue sweep found no second actionable defect. Pathless file-URL query/fragment handling was explicitly assessed as a low-impact parser edge, rather than a root escape or ordinary valid-dataset regression. No assigned changed-file or risk-mechanism coverage remains open; runtime validation remains excluded.
Converged after 2 review rounds: all assigned reviewers returned NO_NEW_VALUABLE_FINDINGS on the unchanged final finding set, required static coverage is complete, and all candidates and risk focuses have explicit dispositions. Convergence describes review completeness; the new P1 still warrants changes. No documentation file is added in this PR; its description says the documentation PR is pending.
Review converged after 2 round(s).
### What problem does this PR solve? Issue Number: N/A Related PR: apache#69527 Problem Summary: Native HDFS sinks could select Hadoop local storage and perform BE writes or FE cleanup while LOCAL was disabled. Check the selected filesystem before analysis, after backend-property normalization and before cleanup, including built-in local provider overrides, Hadoop key normalization and default-FS aliases. Indirect filesystem selectors require the existing startup opt-in because the FE cannot prove their runtime storage is remote. ### Release note The LOCAL startup opt-in also covers effective local Hadoop sinks and FE cleanup. Indirect Hadoop filesystem selectors require enable_local_tvf=true and an FE restart. Explicit remote configurations and unselected local providers remain available. ### Check List (For Author) - Test: 45 selected FE tests passed via the standard JDK17 wrapper with fresh XML, zero failures/errors/skips and unchanged sources; Java Checkstyle and git diff --check passed. Tests cover INSERT/EXPLAIN, LOAD, normalized config resources, provider/default aliases, opt-in, remote controls and rejection before filesystem creation. BE/Lance source is unchanged. - Behavior changed: Yes, complete the existing default-off LOCAL write policy. - Does this need documentation: Document the effective/indirect filesystem selector boundary alongside the original startup opt-in.
|
run buildall |
|
/review |
There was a problem hiding this comment.
Changes are still required. The new inline P2 identifies LOCAL Lance reads that can escape user_files_secure_path through dataset child symlinks. Existing P1 4366424083 also remains applicable to effective-local native HDFS storage: its direct file:/// example is fixed, but ordinary ViewFS mount delegation still bypasses the switch. I have retained that comment ID instead of posting a duplicate.
For the remaining P1, with enable_local_tvf=false, a global LOAD user can issue:
INSERT INTO hdfs(
'file_path'='/local/prefix_', 'format'='csv',
'fs.defaultFS'='viewfs://cluster',
'fs.viewfs.mounttable.cluster.link./local'='file:///tmp'
) SELECT 1;Both raw and normalized admission inspect only the selected viewfs scheme/provider. Hadoop's ordinary ViewFileSystem delegates creation and deletion to its mount target, so this reaches BE-local /tmp. With file_path=/local/victim/prefix_ and delete_existing_files=true, FE cleanup likewise reaches recursive deletion of /tmp/victim/. Admission must account for delegated local targets before either side effect. These are static source traces, not executed reproductions.
Critical checkpoint conclusions:
- Goal and proof: startup opt-in, pre-discovery privilege checks and canonical confinement are implemented broadly; the two containment/admission gaps above prevent considering the security goal satisfied. Added tests cover many direct cases but omit these cases.
- Scope and clarity: the patch stays focused on admission, path identity, range tags and associated test/deployment changes.
- Concurrency and locks: no new threads, locks or shared per-query mutable state; checks occur during planning or pre-open setup. No new lock-order issue found.
- Lifecycle and initialization: existing schema/dataset ownership and close flow are retained; no new cross-translation-unit static initialization dependency or ownership cycle found.
- Configuration: enable_local_tvf defaults false and is startup-only; its message requires restarting every FE. Seven regression environments explicitly opt in.
- Compatibility: the disabled default is an intentional operational change described in Config and the release note. No storage format or function ABI changes; legacy scan-level type fallback and positive-version catalogs remain. Older binaries retain their former enforcement during upgrades.
- Thrift/protobuf: no definitions changed; existing file_type is now explicitly supplied on Lance scan ranges.
- Parallel paths: LOCAL/FILE reads, SELECT/EXPLAIN, INSERT/EXPLAIN, JNI/native writers, final binding, FE cleanup, schema/scan and catalog/TVF/remote routing were traced. ViewFS delegation and Lance child files are the verified gaps.
- Conditional checks: parser ordering, C-string identity, aliases and indirect Hadoop selectors have explanatory comments; delegated mount targets remain unhandled.
- Test coverage: FE admission/auth/remote controls, BE glob/path and real Lance identity fixtures, plus the Groovy startup-config checks were inspected. No builds or tests were run under this static-only contract. Add descendant-symlink and delegated-local write/cleanup cases.
- Expected results: no golden result files changed; new assertions were reviewed statically without claiming a passing runtime result.
- Observability: rejection messages identify enable/auth failures and redact expanded filesystem targets; no new per-row logging or metric requirement was identified.
- Transactions, persistence and failover: no EditLog, internal transaction visibility, partition-version or MoW bitmap changes.
- Writes, atomicity and crashes: existing external writes/cleanup remain nontransactional; this patch adds admission, with the ViewFS gap described above. No new resource cleanup/lifetime defect found.
- FE/BE propagation: schema and scan preserve LOCAL/S3 type identity; version-zero LOCAL validation and fixed-version catalog routing are consistent. No other transmitted variable was introduced.
- Performance and memory: new work is per-plan/per-dataset setup, outside row loops; no material additional hot-path or memory-lifetime issue found.
- Other issues and existing threads: earlier local JNI-writer P1 4366199143 and remote-authority P1 4361485535 are fixed for their reported paths; earlier percent/dot/case/whitespace/rootless/drive/home findings are addressed and are not reposted.
No additional user focus was supplied. All 24 changed paths and assigned risk scopes received static review. The review converged after three rounds with one new verified P2 and the existing P1 above; no unresolved candidate or static coverage gap remains. Runtime behavior, full regression execution and real remote-service access remain unverified.
Review converged after 3 round(s).
Existing P0/P1 findings confirmed for this head: #69527 (comment)
| .lexically_normal() | ||
| .string(); | ||
| } | ||
| return io::global_local_filesystem()->canonicalize_local_file( |
There was a problem hiding this comment.
[P2] Check containment of the files inside a Lance dataset
With enable_local_tvf=true and user_files_secure_path=/srv/user_files, let alias.lance be a real directory under that root whose _versions and data entries link to the corresponding directories of /srv/private/real.lance. An authorized LOCAL Lance read passes this check because canonicalizing alias.lance does not inspect its children. Schema discovery then lists the external manifests, and scanning opens the external fragment files through the pinned SDK without another containment check. Copying the manifests inside the root and linking only data outward also bypasses row-read confinement. The new secure-root validation therefore leaves a symlink escape even though the dataset directory itself is in-root. Validate the actual LOCAL metadata/fragment targets before opening them and add schema/scan negative coverage for outward child links. This concerns descendant files, separately from the existing requested-URI normalization findings.
What problem does this PR solve?
Issue Number: N/A
Related PR: #69526
Problem Summary:
LOCAL file discovery could escape the configured secure directory through expanded paths and symlinks. The opt-in setting also needs to cover the LOCAL write entry.
LocalFileJniWriterclass, including dot/slash spellings and JNI C-string identity.~/~/home aliases before anchoring and containment. Preserve file URL drive components and raw-drive parent semantics according to the pinned Unix SDK, including the distinctfile:/C|andfile:///C|identities. Ordinary filesystem/glob behavior is unchanged.Release note
LOCAL TVF and FILE TVF with local storage are disabled by default. Set enable_local_tvf=true in fe.conf on every query-serving FE and restart those FEs to enable them; the setting cannot be changed at runtime. LOCAL INSERT/EXPLAIN and remote-named sinks using the built-in local JNI writer honor the setting. Enabled reads still require ADMIN/OPERATOR and remain inside BE user_files_secure_path, including directories containing glob metacharacters. Resolution errors do not disclose target names.
LOCAL Lance preserves dataset identity for file URI preprocessing, rootless URLs and bare dot segments, while retaining literal bare-path whitespace and secure-root containment. S3 Lance rejects local aliases and malformed remote dataset authorities before opening data.
Hadoop sinks and FE cleanup honor LOCAL admission for their effective local storage. When enable_local_tvf is false, indirect Hadoop provider/default-FS selectors (including runtime references and the native
defaultselector) require enabling the setting and restarting every FE; literal remote configurations and unused local provider settings retain their behavior.Check List (For Author)
Local validation for the latest revision:
45 selected FE tests passed through the standard JDK17 wrapper with fresh XML, zero failures/errors/skips and unchanged sources. Native HDFS cases cover file:/// defaults, selected LocalFileSystem/RawLocalFileSystem, trimmed keys, canonical/legacy aliases, indirect selectors, normalized configuration resources and startup opt-in; explicit remote and unselected local-provider controls pass.
INSERT/EXPLAIN, direct binding and a global-LOAD command entry are covered. Cleanup tests assert rejection before FileSystemFactory or executor interactions and perform no real filesystem cleanup. Existing class-loader alias checks remain covered.
Java Checkstyle and git diff --check passed. Independent Standards and Spec reviews found no remaining issue in this supplement.
Only four FE files changed per branch. BE/Lance source is unchanged; its earlier scoped results remain historical evidence for the unchanged code. Full Groovy regression and actual remote-service data reads remain unverified locally.
Behavior changed:
Does this need documentation?
Check List (For Reviewer who merge this PR)