Governed substrate for autonomous agents: scoped identity (passports), audited actions, MCP workspace. Infra IPs and secrets redacted for public release.
100 lines
3.8 KiB
PL/PgSQL
100 lines
3.8 KiB
PL/PgSQL
-- ADR-0003 Phase 6 / ticket 126415 (6.3) — bdd_doc_gate read-only view.
|
|
--
|
|
-- Aggregates must-criterion gate state per (spec, source_doc). Downstream:
|
|
-- header `📐 готово` widget, status-machine watchdog (draft ↔
|
|
-- regressed-published), and future GET /api/v3/documents/:id/bdd-gate.
|
|
--
|
|
-- Substrate note: bdd_specs/bdd_criteria/bdd_tests/bdd_test_runs are CRM
|
|
-- *logical* tables (rows in public.table_rows keyed by table_id). Hard
|
|
-- table_ids are fixed: 7255 specs, 7256 criteria, 7258 tests, 7259 runs.
|
|
-- Registered in public.universal_tables — see ADR-0002 substrate.
|
|
--
|
|
-- Gate semantics:
|
|
-- must_total = # must-priority criteria under the spec
|
|
-- must_verified = # must criteria with status='verified'
|
|
-- must_failed = # must criteria with status='failed'
|
|
-- ready = must_total > 0 AND must_total = must_verified
|
|
--
|
|
-- Latest test run is joined per criterion (AC #3) but not currently folded
|
|
-- into the aggregate — status on the criterion row is the canonical flip
|
|
-- (updated via TOTP-signed verify in C-4 / ticket 126391). Exposing the
|
|
-- run join now keeps the view ready for a tighter double-gate rule later
|
|
-- without a schema churn.
|
|
--
|
|
-- Idempotent — CREATE OR REPLACE VIEW.
|
|
|
|
BEGIN;
|
|
|
|
CREATE OR REPLACE VIEW bdd_doc_gate AS
|
|
WITH specs AS (
|
|
SELECT
|
|
id AS spec_id,
|
|
(data->>'source_doc_id')::int AS source_doc_id,
|
|
updated_at AS spec_updated_at
|
|
FROM table_rows
|
|
WHERE table_id = 7255
|
|
AND data ? 'source_doc_id'
|
|
AND (data->>'source_doc_id') ~ '^-?\d+$'
|
|
),
|
|
criteria AS (
|
|
SELECT
|
|
id AS criterion_id,
|
|
(data->>'spec_id')::int AS spec_id,
|
|
data->>'priority' AS priority,
|
|
data->>'status' AS status,
|
|
updated_at AS criterion_updated_at
|
|
FROM table_rows
|
|
WHERE table_id = 7256
|
|
AND data ? 'spec_id'
|
|
AND (data->>'spec_id') ~ '^-?\d+$'
|
|
),
|
|
tests AS (
|
|
SELECT
|
|
id AS test_id,
|
|
(data->>'criterion_id')::int AS criterion_id
|
|
FROM table_rows
|
|
WHERE table_id = 7258
|
|
AND data ? 'criterion_id'
|
|
AND (data->>'criterion_id') ~ '^-?\d+$'
|
|
),
|
|
latest_runs AS (
|
|
SELECT DISTINCT ON (t.criterion_id)
|
|
t.criterion_id,
|
|
r.id AS run_id,
|
|
r.data->>'status' AS run_status,
|
|
COALESCE(
|
|
NULLIF(r.data->>'finished_at','')::timestamptz,
|
|
r.updated_at
|
|
) AS run_ts
|
|
FROM tests t
|
|
JOIN table_rows r
|
|
ON r.table_id = 7259
|
|
AND (r.data->>'test_id') ~ '^-?\d+$'
|
|
AND (r.data->>'test_id')::int = t.test_id
|
|
ORDER BY
|
|
t.criterion_id,
|
|
COALESCE(NULLIF(r.data->>'finished_at','')::timestamptz, r.updated_at) DESC
|
|
)
|
|
SELECT
|
|
s.source_doc_id,
|
|
s.spec_id,
|
|
COUNT(*) FILTER (WHERE c.priority = 'must')::int AS must_total,
|
|
COUNT(*) FILTER (WHERE c.priority = 'must' AND c.status = 'verified')::int AS must_verified,
|
|
COUNT(*) FILTER (WHERE c.priority = 'must' AND c.status = 'failed')::int AS must_failed,
|
|
(COUNT(*) FILTER (WHERE c.priority = 'must') > 0
|
|
AND COUNT(*) FILTER (WHERE c.priority = 'must')
|
|
= COUNT(*) FILTER (WHERE c.priority = 'must' AND c.status = 'verified')) AS ready,
|
|
GREATEST(
|
|
MAX(s.spec_updated_at),
|
|
MAX(c.criterion_updated_at),
|
|
MAX(lr.run_ts)
|
|
) AS updated_at
|
|
FROM specs s
|
|
LEFT JOIN criteria c ON c.spec_id = s.spec_id
|
|
LEFT JOIN latest_runs lr ON lr.criterion_id = c.criterion_id
|
|
GROUP BY s.source_doc_id, s.spec_id;
|
|
|
|
COMMENT ON VIEW bdd_doc_gate IS
|
|
'ADR-0003 Phase 6.3 / ticket 126415. Must-criterion gate aggregate per (spec, source_doc). Read-only.';
|
|
|
|
COMMIT;
|