Skip to content

fix(platform): pass the corpus scope rows as one jsonb parameter - #3222

Merged
larryro merged 1 commit into
mainfrom
fix/knowledge-scope-reconcile-jsonb
Sep 5, 2026
Merged

fix(platform): pass the corpus scope rows as one jsonb parameter#3222
larryro merged 1 commit into
mainfrom
fix/knowledge-scope-reconcile-jsonb

Conversation

@larryro

@larryro larryro commented Sep 5, 2026

Copy link
Copy Markdown
Collaborator

Summary

reconcileDocumentScopeStamps (the daily corpus scope reconcile from #3216) passed a pre-serialized JSON string as the $2::jsonb parameter of pool.unsafe. postgres.js learns the parameter type from the server's description and JSON-encodes jsonb parameters itself, so the payload arrived double-encoded and Postgres refused it with cannot call jsonb_to_recordset on a non-array. Effects on main: the reconcile never corrected a drifted row, and the real-Postgres integration proof truncated at that lane (RUN TRUNCATED at checkCorpusScopeReconcile, 19/133 lanes).

Change

  • services/platform/backend/domains/knowledge/service.ts: hand the rows over as pool.json(intended), the typed jsonb parameter the rest of the backend uses.
  • scope-reconcile.test.ts: the fake pool models sql.json; a new case pins that the payload is a jsonb parameter carrying an array, never a string.

Tests & gates observed

  • bunx vitest --run --project server backend/domains/knowledge/scope-reconcile.test.ts → 10 passed
  • bunx tsc --noEmit → 0 errors
  • Integration proof: see the follow-up comment (run on this branch against a throwaway tale-db + MinIO).

Found while gating the backend deep-review fix campaign (every fixer's itest run stopped at this lane).

reconcileDocumentScopeStamps handed `pool.unsafe` a pre-serialized JSON
string for the `$2::jsonb` parameter. postgres.js learns the parameter
type from the server's description and JSON-encodes jsonb parameters
itself, so the string arrived double-encoded and `jsonb_to_recordset`
refused it ("cannot call jsonb_to_recordset on a non-array"). The daily
scope reconcile (#3216) therefore never corrected a row, and the
integration proof truncated at the reconcile lane (19/133 lanes ran).

Hand the rows over as `pool.json(intended)` — the typed parameter the
rest of the backend uses — and pin the shape in the unit test.
@larryro

larryro commented Sep 5, 2026

Copy link
Copy Markdown
Collaborator Author

Integration proof on this branch (throwaway tale-db + MinIO, TALE_CONFIG_DIR temp dir, SANDBOX_LLM_GATEWAY_ADMIN_PASSWORD exported):

[itest] 464/466 checks passed across 133/133 lanes

Before the fix, main truncates at lane 19 (RUN TRUNCATED at checkCorpusScopeReconcile — cannot call jsonb_to_recordset on a non-array, 19/133 lanes). The two remaining fails are not this change:

  • knowledge: corpus scope drift is corrected and reporteddrifted=null: the lane drifts a stamp on the corpus row of a live document, but in this harness the document's RAG index is still queued (no worker drains it), so no corpus row exists to drift. The reconcile itself runs (scanned 12, corrected 0, second run identical). Lane precondition, tracked separately in the knowledge-domain review.
  • webdav re-home — red on main before this branch (known).

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant