Skip to content

Singleton get({ include }) silently flattens a nested shape, losing take and other bounds #1371

Description

@borisno2

Raised during PR #1370 (issue #1255, part of #1127). The implementer stopped rather than guess — the fix needs a public-API decision, not a patch.

The defect

get({ include }) on the singleton delegate silently flattens nested shapes. { posts: { take: 5 } } loses its bound: the nested object is treated as truthy and the relation is included whole.

Silently is the problem. A caller who writes a bound and does not get one has no signal — the read simply returns more than asked for, and on a large relation that is a materialisation the caller explicitly tried to avoid.

The decision this needs

include's contract on the secured surface is not yet settled for this entry point:

  • Does a nested object become a Refinement? If so, which of take / where / orderBy / select map onto it, and with what precedence against the surrounding read?
  • Or is a non-boolean value refused outright, so the caller is told rather than silently given more?

Refusing is the conservative reading and the cheaper one to reverse later. Mapping to a Refinement is friendlier but needs each key's semantics pinned, and needs an answer for keys the refinement cannot express.

Cost of either choice: none, today

The only in-repo caller is SingletonView.tsx, which calls delegate.get() with no argument. So whichever way this is resolved, there is no caller churn — which makes now the cheap moment to decide it, before the surface has consumers relying on the flattening.

Acceptance criteria

  • A nested include shape is either honoured with documented semantics, or refused with a clear error — never silently flattened
  • If honoured: take bounds the relation, and the behaviour of where / orderBy / select is documented and tested
  • If refused: the error names the offending key and says what is accepted
  • A test covers a nested shape; it must fail if the flattening returns
  • The contract is documented wherever include is documented for the secured surface

Related

#1255 / PR #1370 (where this surfaced), and the singleton get() access fix in the same PR.


Generated by Claude Code

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    ready-for-agentFully specified, ready for an AFK agent

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions