Skip to content

Docs for TrueQuery 0.1.6View as Markdown

What the checker finds and promises

The checker reads your code and looks for SQL that silently returns the wrong answer. It works with no AI involved. Your agent runs it for you, or you can run it on its own.

What it finds#

$ truequery detect samples/bad_orders.sql
samples/bad_orders.sql:7:19 [error] sql/accidental-cross-join — no predicate links o: every row pairs with every row on the other side
    fix: add ON <keys>, or CROSS JOIN if cartesian is intended
samples/bad_orders.sql:13:7 [error] sql/not-in-nullable-subquery — a NULL in the subquery makes NOT IN return zero rows
    fix: rewrite as NOT EXISTS, or add WHERE col IS NOT NULL
samples/bad_orders.sql:17:14 [error] sql/count-star-after-left-join — COUNT(*) over an outer join counts 1 for unmatched rows
    fix: count the nullable-side key instead, e.g. COUNT(o.<key>)
...
5 errors, 2 warnings in 1 file checked offline

truequery review adds the receipt. Its Not checked lines are the point: they name what this pass could not verify. Here that's the data itself; a limit such as integer division is listed only when a file could hit it.

TrueQuery receipt
Checked      1 SQL file · contracts for 0 of 3 tables
Found        5 errors · 2 warnings
Not checked  your data: TrueQuery reads files and never connects to your database
No contract  customers, orders, staging_orders

What it promises#

  • Offline and deterministic. No LLM in the check path and no network calls. Your code never leaves your machine.
  • Never a false "clean". A file it couldn't parse, a statement it could read only as an opaque command, or a function body in procedural code (PL/pgSQL, BEGIN … END) is listed as not checked, and the exit code says so. The query inside EXPLAIN, PREPARE, DECLARE … CURSOR and CREATE … AS, and the statements in a SQL function body, are checked.
  • Checks the SQL inside Python too. SQL strings passed to execute, read_sql, text(), .sql() or sql= (including f-strings, .format(), % and a query held in a same-file variable) get the same checks as .sql files, and findings point at the Python line and column. SQL your program builds at run time (in a loop, in another function or module) can't be read from the file: it's listed as not checked, never as clean.
  • Checks pandas pipelines too. A Python file that imports pandas gets the pandas checks (see "pandas" below), alongside any SQL inside it.
  • Runs as the agent works. Hooks check each edit to a SQL file (or a Python file with SQL inside, or that imports pandas) for bugs that are never intended (= NULL, an unguarded DELETE, a WHERE that empties a left join). At the end of each turn they run every enabled check over the files touched. New findings go back to the agent once, a clean pass is silent, and no edit is ever refused.
  • Works anywhere SQL lives. In a terminal and in CI, for any agent or person: text, JSON or SARIF output. Exit codes: 0 means clean; 1 means findings at or above --fail-on (default error); 2 is a usage or config error; 3 means some files couldn't be checked (--allow-unverified turns 3 into 0).