Skip to content

fix(parse): check the write target when nothing else does - #346

Merged
tiagolauer merged 1 commit into
masterfrom
fix/271-unknown-write-target
Aug 2, 2026
Merged

fix(parse): check the write target when nothing else does#346
tiagolauer merged 1 commit into
masterfrom
fix/271-unknown-write-target

Conversation

@tiagolauer

Copy link
Copy Markdown
Owner

Fixes #271.

The bug

StrictQuery<DB, 'insert into ghosts (name) values ($1)'>  // Record<string, never>[] - no error
StrictQuery<DB, 'delete from ghosts'>                     // same
StrictQuery<DB, 'update ghosts set name = $1'>            // same

Add returning id and the expected QueryTypeError<'unknown table: ghosts'> appears. Add a WHERE to the DELETE and it also errors. So the hole sits exactly on the everyday INSERT — and a mistyped write target is about the most common write mistake there is. The README's limitations section says strict mode turns unknown tables into a QueryTypeError.

The fix

Table existence was only ever verified as a side effect of resolving some column, in RETURNING or in WHERE/ON. The EmptyRow path in InferRowWithChecked never resolved Sources against the schema at all.

It now does, in strict mode, reusing the AllKnownTables / FirstUnknownTable pair StarRow already reports with — so the message is identical to the one every other path produces. Loose mode still returns the empty row.

Verification

tests/unknown-write-target.test-d.ts, ten cases. Four red on master:

tests/unknown-write-target.test-d.ts(19,3): error TS2344: Type 'false' does not satisfy the constraint 'true'.
tests/unknown-write-target.test-d.ts(23,3): ... (27,3), (31,3)
  • unknown INSERT / DELETE / UPDATE targets, through StrictRow and StrictQuery
  • the RETURNING form that already reported it still does

Controls: a real target with no RETURNING and no WHERE still projects nothing (all three write shapes, plus update ... from orders), and loose mode is unchanged.

tsc --noEmit clean, 192 runtime tests pass, budget 193,122 (+636).

    StrictQuery<DB, 'insert into ghosts (name) values ($1)'>  // was Record<string, never>[]
    StrictQuery<DB, 'delete from ghosts'>                     // same
    StrictQuery<DB, 'update ghosts set name = $1'>            // same

Table existence was only ever verified as a side effect of resolving some
column, in RETURNING or in WHERE. Add `returning id` and the expected
`unknown table: ghosts` appeared; write the statement the way people
normally write it and nothing looked the table up at all. The README's
limitations section says strict mode turns an unknown table into a
QueryTypeError, and a mistyped INSERT target is about the most common write
mistake there is.

The EmptyRow path - a write that projects nothing - now resolves its sources
against the schema in strict mode, reusing the same AllKnownTables and
FirstUnknownTable that StarRow reports with, so the message reads the same
way it does everywhere else. Loose mode is untouched.

Fixes #271

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@tiagolauer
tiagolauer force-pushed the fix/271-unknown-write-target branch from 32544e5 to b029c98 Compare August 2, 2026 13:04
@tiagolauer
tiagolauer merged commit ae9600c into master Aug 2, 2026
12 checks passed
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.

Strict mode accepts writes against unknown tables when there is no RETURNING or WHERE

1 participant