Skip to content

[finding] ObjectGrid's legacy defaultFilters leg still reaches $filter without the toFilterNode hop #4082

Description

@yinlianghui

Observation-class finding, recorded from the objectui#4041 implementation (PR #4081) so it is not rediscovered. Unassigned, and no pm:queue — I did not measure a live producer, so I am not claiming a user hits this today. Filed plainly; let triage grade it.

The fact

packages/plugin-grid/src/ObjectGrid.tsx, the query assembly, after PR #4081:

if (schemaFilter !== undefined) {
  params.$filter = schemaFilter;      // lowered through toFilterNode at the read point
} else if (schema.defaultFilters) {
  // Legacy support
  params.$filter = schema.defaultFilters;   // byte-for-byte, no lowering
}

objectui#4041 converged the declared filter key onto the repo's single lowering hop (toFilterNode, "the last hop before the wire"). The legacy defaultFilters fallback beside it was deliberately left untouched as out of scope for that card — it is a different key, undeclared in the block's inputs, and widening #4041 to it would have been scope creep on a ruled card.

But the hazard toFilterNode exists to close applies to it verbatim. defaultFilters is the MongoDB-style Record< string, any > shape (plugin-list's buildEffectiveFilter names it as exactly that: "its last fallback is table.defaultFilters, declared Record< string, any >"). isFilterAST is false for a plain object, so such a value sent raw is the 400 INVALID_FILTER shape objectui#3431 measured against a real backend. toFilterNode already handles this case — it routes objects through convertFiltersToAST — so the fix, if wanted, is a one-line reuse of the sink rather than new logic.

Why I am not asserting impact

Two reasons to let triage decide rather than grade it myself:

  1. No measured producer. defaultFilters is not in object-grid's registered inputs, so an author writing it gets unknown-prop from the save gate (a warning, not a rejection — sdui-parser/src/validate.ts pushes severity: 'warning'). Whether any host injects it onto an object-grid node was not measured.
  2. The sibling path already lowers. Where ObjectView feeds a list, the value goes through buildEffectiveFilter, which does call toFilterNode. So the un-lowered leg may be dormant in practice — which is precisely the "dormant code / unexercised drift" class rather than a live defect.

Severity judged at filing time is unreliable in both directions, so this is recorded as observed rather than argued up or down.

Related


Generated by Claude Code

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions