Contents
Plain-language companion: v0.3.0.md
v0.3.0 — DVM Correctness, SAST & Test Coverage
Status: Released (2026-03-11).
Goal: Re-enable all 18 previously-ignored DVM correctness E2E tests by fixing HAVING, FULL OUTER JOIN, correlated EXISTS+HAVING, and correlated scalar subquery differential computation bugs. Harden the SAST toolchain with privilege-context rules and an unsafe-block baseline. Expand TPC-H coverage with rollback, mode-comparison, single-row, and DAG tests.
DVM Correctness Fixes
In plain terms: The Differential View Maintenance engine — the core algorithm that computes what changed incrementally — had four correctness bugs in specific SQL patterns. Queries using these patterns were silently producing wrong results and had their tests marked “ignored”. This release fixes all four: HAVING clauses on aggregates, FULL OUTER JOINs, correlated EXISTS subqueries combined with HAVING, and correlated scalar subqueries in SELECT lists. All 18 previously-ignored E2E tests now pass.
| Item | Description | Status |
|---|---|---|
| DC1 | HAVING clause differential correctness — fix COUNT(*) rewrite and threshold-crossing upward rescan (5 tests un-ignored) |
✅ Done |
| DC2 | FULL OUTER JOIN differential correctness — fix row-id mismatch, compound GROUP BY expressions, SUM NULL semantics, and rescan CTE SELECT list (5 tests un-ignored) | ✅ Done |
| DC3 | Correlated EXISTS with HAVING differential correctness — fix EXISTS sublink parser discarding GROUP BY/HAVING, row-id mismatch for Project(SemiJoin), and diff_project row-id recomputation (1 test un-ignored) |
✅ Done |
| DC4 | Correlated scalar subquery differential correctness — rewrite_correlated_scalar_in_select rewrites correlated scalar subqueries to LEFT JOINs before DVM parsing (2 tests un-ignored) |
✅ Done |
DVM correctness subtotal: 18 previously-ignored E2E tests re-enabled (0 remaining)
SAST Program (Phases 1–3)
In plain terms: Adds formal static security analysis (SAST) to every build. CodeQL and Semgrep scan for known vulnerability patterns — for example, using SECURITY DEFINER functions without locking down
search_path, or callingSET ROLEin ways that could be abused. Separately, every Rustunsafe {}block is inventoried and counted; any PR that adds new unsafe blocks beyond the committed baseline fails CI automatically.
| Item | Description | Status |
|---|---|---|
| S1 | CodeQL + cargo deny + initial Semgrep baseline — zero findings across 115 Rust source files |
✅ Done |
| S2 | Narrow rust.panic-in-sql-path scope — exclude src/dvm/** and src/bin/** to eliminate 351 false-positive alerts |
✅ Done |
| S3 | sql.row-security.disabled Semgrep rule — flag SET LOCAL row_security = off |
✅ Done |
| S4 | sql.set-role.present Semgrep rule — flag SET ROLE / RESET ROLE patterns |
✅ Done |
| S5 | Updated sql.security-definer.present message to require explicit SET search_path |
✅ Done |
| S6 | scripts/unsafe_inventory.sh + .unsafe-baseline — per-file unsafe { counter with committed baseline (1309 blocks across 6 files) |
✅ Done |
| S7 | .github/workflows/unsafe-inventory.yml — advisory CI workflow; fails if any file exceeds its baseline |
✅ Done |
| S8 | Remove pull_request trigger from CodeQL + Semgrep workflows (no inline PR annotations; runs on push-to-main + weekly schedule) |
✅ Done |
SAST subtotal: Phases 1–3 complete; Phase 4 rule promotion tracked as post-v0.3.0 cleanup
TPC-H Test Suite Enhancements (T1–T6)
In plain terms: TPC-H is an industry-standard analytical query benchmark — 22 queries against a simulated supply-chain database. This extends the pg_trickle TPC-H test suite to verify four additional scenarios that the basic correctness checks didn’t cover: that ROLLBACK atomically undoes an IVM stream table update; that DIFFERENTIAL and IMMEDIATE mode produce identical answers for the same data; that single-row mutations work correctly (not just bulk changes); and that multi-level stream table DAGs refresh in the correct topological order.
| Item | Description | Status |
|---|---|---|
| T1 | __pgt_count < 0 guard in assert_tpch_invariant — over-retraction detector, applies to all existing TPC-H tests |
✅ Done |
| T2 | Skip-set regression guard in DIFFERENTIAL + IMMEDIATE tests — any newly skipped query not in the allowlist fails CI | ✅ Done |
| T3 | test_tpch_immediate_rollback — verify ROLLBACK restores IVM stream table atomically across RF mutations |
✅ Done |
| T4 | test_tpch_differential_vs_immediate — side-by-side comparison: both incremental modes produce identical results after shared mutations |
✅ Done |
| T5 | test_tpch_single_row_mutations + SQL fixtures — single-row INSERT/UPDATE/DELETE IVM trigger paths on Q01/Q06/Q03 |
✅ Done |
| T6a | test_tpch_dag_chain — two-level DAG (Q01 → filtered projection), refreshed in topological order |
✅ Done |
| T6b | test_tpch_dag_multi_parent — multi-parent fan-in (Q01 + Q06 → UNION ALL), DIFFERENTIAL mode |
✅ Done |
TPC-H subtotal: T1–T6 complete; 22/22 TPC-H queries passing
Exit criteria:
- [x] All 18 previously-ignored DVM correctness E2E tests re-enabled
- [x] SAST Phases 1–3 deployed; unsafe baseline committed; CodeQL zero findings
- [x] TPC-H T1–T6 implemented; rollback, differential-vs-immediate, single-row, and DAG tests pass
- [x] Extension upgrade path tested (0.2.3 → 0.3.0)