@dsh-enhanced/assistant-evolution 0.1.7 → 0.1.14
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +58 -19
- package/cordis.patch.yml +3 -1
- package/lib/guidance.d.ts +2 -0
- package/lib/guidance.d.ts.map +1 -1
- package/lib/guidance.js +7 -1
- package/lib/guidance.js.map +1 -1
- package/lib/index.d.ts +2 -2
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +2 -2
- package/lib/index.js.map +1 -1
- package/lib/review.d.ts +1 -1
- package/lib/review.d.ts.map +1 -1
- package/lib/review.js +22 -0
- package/lib/review.js.map +1 -1
- package/lib/service.d.ts +188 -6
- package/lib/service.d.ts.map +1 -1
- package/lib/service.js +903 -45
- package/lib/service.js.map +1 -1
- package/lib/sqlite.d.ts +1 -1
- package/lib/sqlite.d.ts.map +1 -1
- package/lib/sqlite.js +449 -7
- package/lib/sqlite.js.map +1 -1
- package/lib/store.d.ts +98 -3
- package/lib/store.d.ts.map +1 -1
- package/lib/store.js +1493 -107
- package/lib/store.js.map +1 -1
- package/lib/tools.d.ts.map +1 -1
- package/lib/tools.js +133 -2
- package/lib/tools.js.map +1 -1
- package/lib/types.d.ts +192 -11
- package/lib/types.d.ts.map +1 -1
- package/lib/types.js +2 -0
- package/lib/types.js.map +1 -1
- package/lib/version.d.ts +1 -1
- package/lib/version.d.ts.map +1 -1
- package/lib/version.js +1 -1
- package/lib/version.js.map +1 -1
- package/package.json +14 -4
package/lib/sqlite.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { chmodSync, mkdirSync } from 'node:fs';
|
|
2
2
|
import { dirname, isAbsolute } from 'node:path';
|
|
3
3
|
import { DatabaseSync } from 'node:sqlite';
|
|
4
|
-
export const evolutionSchemaVersion =
|
|
4
|
+
export const evolutionSchemaVersion = 12;
|
|
5
5
|
export class EvolutionDatabaseError extends Error {
|
|
6
6
|
code;
|
|
7
7
|
constructor(code, message) {
|
|
@@ -119,6 +119,398 @@ function migrateV3ToV4(database) {
|
|
|
119
119
|
PRAGMA user_version = 4;
|
|
120
120
|
`);
|
|
121
121
|
}
|
|
122
|
+
function migrateV4ToV5(database) {
|
|
123
|
+
database.exec(`
|
|
124
|
+
ALTER TABLE evolution_episodes ADD COLUMN evidence_kind TEXT NOT NULL
|
|
125
|
+
DEFAULT 'legacy-unknown'
|
|
126
|
+
CHECK (evidence_kind IN ('operational', 'objective', 'verification', 'legacy-unknown'));
|
|
127
|
+
ALTER TABLE evolution_episodes ADD COLUMN evidence_ref TEXT;
|
|
128
|
+
ALTER TABLE evolution_episodes ADD COLUMN learning_eligible INTEGER NOT NULL DEFAULT 0
|
|
129
|
+
CHECK (learning_eligible IN (0, 1))
|
|
130
|
+
CHECK (learning_eligible = 0 OR (
|
|
131
|
+
trust = 'trusted'
|
|
132
|
+
AND evidence_kind IN ('objective', 'verification')
|
|
133
|
+
AND evidence_ref IS NOT NULL));
|
|
134
|
+
|
|
135
|
+
-- A v4 trusted automation row proved only that execution stopped in a
|
|
136
|
+
-- binary state. It did not prove objective correctness. Keep every row for
|
|
137
|
+
-- audit, but quarantine it from all learning projections.
|
|
138
|
+
UPDATE evolution_episodes
|
|
139
|
+
SET evidence_kind = 'legacy-unknown', evidence_ref = NULL, learning_eligible = 0;
|
|
140
|
+
|
|
141
|
+
-- Every pre-v5 pending mutation was computed from evidence that did not
|
|
142
|
+
-- distinguish execution status from objective quality. A later approval
|
|
143
|
+
-- must not activate that stale conclusion after the evidence quarantine.
|
|
144
|
+
UPDATE evolution_proposals
|
|
145
|
+
SET status = 'conflicted', version = version + 1
|
|
146
|
+
WHERE status = 'pending';
|
|
147
|
+
|
|
148
|
+
DROP INDEX IF EXISTS evolution_episodes_adoption;
|
|
149
|
+
DROP INDEX IF EXISTS evolution_episodes_evaluation;
|
|
150
|
+
CREATE INDEX evolution_episodes_adoption
|
|
151
|
+
ON evolution_episodes(
|
|
152
|
+
scope_key, situation, learning_eligible, rule_id, occurred_at DESC, id DESC);
|
|
153
|
+
CREATE INDEX evolution_episodes_evaluation
|
|
154
|
+
ON evolution_episodes(
|
|
155
|
+
rule_id, guidance_version, learning_eligible, occurred_at DESC, id DESC);
|
|
156
|
+
|
|
157
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '5')
|
|
158
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
159
|
+
PRAGMA user_version = 5;
|
|
160
|
+
`);
|
|
161
|
+
}
|
|
162
|
+
function migrateV5ToV6(database) {
|
|
163
|
+
database.exec(`
|
|
164
|
+
-- v5 made immutable Evaluation references mandatory, but caller-owned
|
|
165
|
+
-- idempotency keys could still alias the same result into several rows.
|
|
166
|
+
-- Retain the earliest deterministic row and quarantine every duplicate so
|
|
167
|
+
-- historical ledgers migrate before the uniqueness constraint is created.
|
|
168
|
+
CREATE TEMP TABLE evolution_v6_duplicate_quality AS
|
|
169
|
+
WITH ranked AS (
|
|
170
|
+
SELECT id, scope_key,
|
|
171
|
+
row_number() OVER (
|
|
172
|
+
PARTITION BY scope_key, evidence_ref
|
|
173
|
+
ORDER BY occurred_at ASC, id ASC
|
|
174
|
+
) AS duplicate_rank
|
|
175
|
+
FROM evolution_episodes
|
|
176
|
+
WHERE learning_eligible = 1
|
|
177
|
+
AND evidence_kind IN ('objective', 'verification')
|
|
178
|
+
AND evidence_ref IS NOT NULL
|
|
179
|
+
)
|
|
180
|
+
SELECT id, scope_key FROM ranked WHERE duplicate_rank > 1;
|
|
181
|
+
|
|
182
|
+
UPDATE evolution_episodes
|
|
183
|
+
SET evidence_kind = 'legacy-unknown', evidence_ref = NULL, learning_eligible = 0
|
|
184
|
+
WHERE id IN (SELECT id FROM evolution_v6_duplicate_quality);
|
|
185
|
+
|
|
186
|
+
-- A pending mutation in an affected scope may have been computed from an
|
|
187
|
+
-- inflated sample. Preserve it for audit but prevent delayed activation.
|
|
188
|
+
UPDATE evolution_proposals
|
|
189
|
+
SET status = 'conflicted', version = version + 1
|
|
190
|
+
WHERE status = 'pending'
|
|
191
|
+
AND scope_key IN (SELECT DISTINCT scope_key FROM evolution_v6_duplicate_quality);
|
|
192
|
+
|
|
193
|
+
DROP TABLE evolution_v6_duplicate_quality;
|
|
194
|
+
|
|
195
|
+
CREATE UNIQUE INDEX evolution_episodes_quality_evidence_identity
|
|
196
|
+
ON evolution_episodes(scope_key, evidence_ref)
|
|
197
|
+
WHERE learning_eligible = 1;
|
|
198
|
+
|
|
199
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '6')
|
|
200
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
201
|
+
PRAGMA user_version = 6;
|
|
202
|
+
`);
|
|
203
|
+
}
|
|
204
|
+
function migrateV6ToV7(database) {
|
|
205
|
+
database.exec(`
|
|
206
|
+
-- Every pre-v7 quality row came through the retired caller-controlled
|
|
207
|
+
-- projection seam and cannot be rebound to an authoritative Evaluation
|
|
208
|
+
-- receipt after the fact. Preserve it for audit, but revoke learning
|
|
209
|
+
-- eligibility and invalidate pending conclusions derived from it.
|
|
210
|
+
CREATE TEMP TABLE evolution_v7_legacy_quality_scopes AS
|
|
211
|
+
SELECT DISTINCT scope_key FROM evolution_episodes WHERE learning_eligible = 1;
|
|
212
|
+
|
|
213
|
+
UPDATE evolution_episodes
|
|
214
|
+
SET evidence_kind = 'legacy-unknown', evidence_ref = NULL, learning_eligible = 0
|
|
215
|
+
WHERE learning_eligible = 1;
|
|
216
|
+
UPDATE evolution_proposals
|
|
217
|
+
SET status = 'conflicted', version = version + 1
|
|
218
|
+
WHERE status = 'pending'
|
|
219
|
+
AND scope_key IN (SELECT scope_key FROM evolution_v7_legacy_quality_scopes);
|
|
220
|
+
DROP TABLE evolution_v7_legacy_quality_scopes;
|
|
221
|
+
|
|
222
|
+
-- Evaluation is an independent provenance source. Rebuild the table because
|
|
223
|
+
-- SQLite cannot widen an existing CHECK constraint in place.
|
|
224
|
+
ALTER TABLE evolution_episodes RENAME TO evolution_episodes_v6;
|
|
225
|
+
DROP INDEX IF EXISTS evolution_episodes_adoption;
|
|
226
|
+
DROP INDEX IF EXISTS evolution_episodes_evaluation;
|
|
227
|
+
DROP INDEX IF EXISTS evolution_episodes_quality_evidence_identity;
|
|
228
|
+
|
|
229
|
+
CREATE TABLE evolution_episodes (
|
|
230
|
+
id TEXT PRIMARY KEY,
|
|
231
|
+
idempotency_key TEXT NOT NULL UNIQUE,
|
|
232
|
+
situation TEXT NOT NULL,
|
|
233
|
+
outcome TEXT NOT NULL CHECK (outcome IN ('succeeded', 'failed')),
|
|
234
|
+
detail TEXT NOT NULL,
|
|
235
|
+
source TEXT NOT NULL CHECK (source IN ('automation', 'evaluation', 'foreground')),
|
|
236
|
+
scope_key TEXT NOT NULL,
|
|
237
|
+
trust TEXT NOT NULL CHECK (trust IN ('trusted', 'self-reported', 'legacy')),
|
|
238
|
+
evidence_kind TEXT NOT NULL CHECK (
|
|
239
|
+
evidence_kind IN ('operational', 'objective', 'verification', 'legacy-unknown')),
|
|
240
|
+
evidence_ref TEXT,
|
|
241
|
+
learning_eligible INTEGER NOT NULL CHECK (learning_eligible IN (0, 1)),
|
|
242
|
+
rule_id TEXT,
|
|
243
|
+
guidance_version INTEGER CHECK (guidance_version IS NULL OR guidance_version >= 1),
|
|
244
|
+
claimed_rule_id TEXT,
|
|
245
|
+
occurred_at INTEGER NOT NULL,
|
|
246
|
+
CHECK (learning_eligible = 0 OR (
|
|
247
|
+
source = 'evaluation'
|
|
248
|
+
AND
|
|
249
|
+
trust = 'trusted'
|
|
250
|
+
AND evidence_kind IN ('objective', 'verification')
|
|
251
|
+
AND evidence_ref IS NOT NULL))
|
|
252
|
+
) STRICT;
|
|
253
|
+
|
|
254
|
+
INSERT INTO evolution_episodes(
|
|
255
|
+
id, idempotency_key, situation, outcome, detail, source, scope_key,
|
|
256
|
+
trust, evidence_kind, evidence_ref, learning_eligible,
|
|
257
|
+
rule_id, guidance_version, claimed_rule_id, occurred_at)
|
|
258
|
+
SELECT
|
|
259
|
+
id, idempotency_key, situation, outcome, detail, source, scope_key,
|
|
260
|
+
trust, evidence_kind, evidence_ref, learning_eligible,
|
|
261
|
+
rule_id, guidance_version, claimed_rule_id, occurred_at
|
|
262
|
+
FROM evolution_episodes_v6;
|
|
263
|
+
DROP TABLE evolution_episodes_v6;
|
|
264
|
+
|
|
265
|
+
CREATE INDEX evolution_episodes_adoption
|
|
266
|
+
ON evolution_episodes(
|
|
267
|
+
scope_key, situation, learning_eligible, rule_id, occurred_at DESC, id DESC);
|
|
268
|
+
CREATE INDEX evolution_episodes_evaluation
|
|
269
|
+
ON evolution_episodes(
|
|
270
|
+
rule_id, guidance_version, learning_eligible, occurred_at DESC, id DESC);
|
|
271
|
+
CREATE UNIQUE INDEX evolution_episodes_quality_evidence_identity
|
|
272
|
+
ON evolution_episodes(scope_key, evidence_ref)
|
|
273
|
+
WHERE learning_eligible = 1;
|
|
274
|
+
|
|
275
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '7')
|
|
276
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
277
|
+
PRAGMA user_version = 7;
|
|
278
|
+
`);
|
|
279
|
+
}
|
|
280
|
+
function migrateV7ToV8(database) {
|
|
281
|
+
database.exec(`
|
|
282
|
+
ALTER TABLE evolution_episodes ADD COLUMN learning_subject_ref TEXT;
|
|
283
|
+
|
|
284
|
+
-- v7 recorded only the Evaluation identity. For an Automation objective it
|
|
285
|
+
-- therefore cannot prove whether several Evaluation rows assessed one run.
|
|
286
|
+
-- Preserve those rows for audit, but quarantine every old learning row and
|
|
287
|
+
-- every pending conclusion that may have counted it more than once.
|
|
288
|
+
CREATE TEMP TABLE evolution_v8_legacy_learning_scopes AS
|
|
289
|
+
SELECT DISTINCT scope_key FROM evolution_episodes WHERE learning_eligible = 1;
|
|
290
|
+
UPDATE evolution_episodes
|
|
291
|
+
SET evidence_kind = 'legacy-unknown', evidence_ref = NULL,
|
|
292
|
+
learning_subject_ref = NULL, learning_eligible = 0
|
|
293
|
+
WHERE learning_eligible = 1;
|
|
294
|
+
UPDATE evolution_proposals
|
|
295
|
+
SET status = 'conflicted', version = version + 1
|
|
296
|
+
WHERE status = 'pending'
|
|
297
|
+
AND scope_key IN (SELECT scope_key FROM evolution_v8_legacy_learning_scopes);
|
|
298
|
+
DROP TABLE evolution_v8_legacy_learning_scopes;
|
|
299
|
+
|
|
300
|
+
CREATE UNIQUE INDEX evolution_episodes_learning_subject_identity
|
|
301
|
+
ON evolution_episodes(scope_key, learning_subject_ref)
|
|
302
|
+
WHERE learning_eligible = 1;
|
|
303
|
+
|
|
304
|
+
-- SQLite cannot extend the v7 table CHECK in place. These triggers make the
|
|
305
|
+
-- migrated schema enforce the same invariant as a fresh v8 database.
|
|
306
|
+
CREATE TRIGGER evolution_episodes_learning_subject_insert
|
|
307
|
+
BEFORE INSERT ON evolution_episodes
|
|
308
|
+
WHEN (NEW.learning_eligible = 1 AND NEW.learning_subject_ref IS NULL)
|
|
309
|
+
OR (NEW.learning_eligible = 0 AND NEW.learning_subject_ref IS NOT NULL)
|
|
310
|
+
BEGIN
|
|
311
|
+
SELECT RAISE(ABORT, 'learning subject eligibility mismatch');
|
|
312
|
+
END;
|
|
313
|
+
CREATE TRIGGER evolution_episodes_learning_subject_update
|
|
314
|
+
BEFORE UPDATE OF learning_eligible, learning_subject_ref ON evolution_episodes
|
|
315
|
+
WHEN (NEW.learning_eligible = 1 AND NEW.learning_subject_ref IS NULL)
|
|
316
|
+
OR (NEW.learning_eligible = 0 AND NEW.learning_subject_ref IS NOT NULL)
|
|
317
|
+
BEGIN
|
|
318
|
+
SELECT RAISE(ABORT, 'learning subject eligibility mismatch');
|
|
319
|
+
END;
|
|
320
|
+
|
|
321
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '8')
|
|
322
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
323
|
+
PRAGMA user_version = 8;
|
|
324
|
+
`);
|
|
325
|
+
}
|
|
326
|
+
const taskLearningProjectionSchema = `
|
|
327
|
+
CREATE TABLE evolution_task_learning_state (
|
|
328
|
+
scope_key TEXT NOT NULL,
|
|
329
|
+
scope_watermark INTEGER NOT NULL CHECK (scope_watermark >= 1),
|
|
330
|
+
subject_kind TEXT NOT NULL CHECK (subject_kind IN ('automation-run', 'outcome')),
|
|
331
|
+
subject_ref TEXT NOT NULL,
|
|
332
|
+
version INTEGER NOT NULL CHECK (version >= 1),
|
|
333
|
+
digest TEXT NOT NULL CHECK (length(digest) = 64),
|
|
334
|
+
disposition TEXT NOT NULL CHECK (disposition IN ('upsert', 'retract')),
|
|
335
|
+
situation TEXT NOT NULL,
|
|
336
|
+
episode_id TEXT,
|
|
337
|
+
updated_at INTEGER NOT NULL,
|
|
338
|
+
PRIMARY KEY(scope_key, subject_kind, subject_ref),
|
|
339
|
+
CHECK ((disposition = 'upsert' AND episode_id IS NOT NULL)
|
|
340
|
+
OR (disposition = 'retract' AND episode_id IS NULL)),
|
|
341
|
+
FOREIGN KEY(episode_id) REFERENCES evolution_episodes(id) ON DELETE RESTRICT
|
|
342
|
+
) STRICT, WITHOUT ROWID;
|
|
343
|
+
CREATE INDEX evolution_task_learning_state_situation
|
|
344
|
+
ON evolution_task_learning_state(scope_key, situation, disposition, updated_at DESC);
|
|
345
|
+
|
|
346
|
+
CREATE TABLE evolution_task_learning_revisions (
|
|
347
|
+
scope_key TEXT NOT NULL,
|
|
348
|
+
scope_watermark INTEGER NOT NULL CHECK (scope_watermark >= 1),
|
|
349
|
+
subject_kind TEXT NOT NULL CHECK (subject_kind IN ('automation-run', 'outcome')),
|
|
350
|
+
subject_ref TEXT NOT NULL,
|
|
351
|
+
version INTEGER NOT NULL CHECK (version >= 1),
|
|
352
|
+
digest TEXT NOT NULL CHECK (length(digest) = 64),
|
|
353
|
+
disposition TEXT NOT NULL CHECK (disposition IN ('upsert', 'retract')),
|
|
354
|
+
situation TEXT NOT NULL,
|
|
355
|
+
episode_id TEXT,
|
|
356
|
+
applied_at INTEGER NOT NULL,
|
|
357
|
+
PRIMARY KEY(scope_key, subject_kind, subject_ref, version),
|
|
358
|
+
CHECK ((disposition = 'upsert' AND episode_id IS NOT NULL)
|
|
359
|
+
OR (disposition = 'retract' AND episode_id IS NULL)),
|
|
360
|
+
FOREIGN KEY(episode_id) REFERENCES evolution_episodes(id) ON DELETE RESTRICT
|
|
361
|
+
) STRICT, WITHOUT ROWID;
|
|
362
|
+
CREATE INDEX evolution_task_learning_revisions_applied
|
|
363
|
+
ON evolution_task_learning_revisions(applied_at, scope_key, subject_kind, subject_ref);
|
|
364
|
+
`;
|
|
365
|
+
const supervisedGrowthAnalystSchema = `
|
|
366
|
+
CREATE TABLE evolution_supervised_analyst_reviews (
|
|
367
|
+
review_token TEXT PRIMARY KEY,
|
|
368
|
+
scope_key TEXT NOT NULL,
|
|
369
|
+
occurrence_id TEXT NOT NULL,
|
|
370
|
+
contract_version TEXT NOT NULL CHECK (contract_version = 'supervised-growth-analyst/v1'),
|
|
371
|
+
situation TEXT NOT NULL,
|
|
372
|
+
failures INTEGER NOT NULL CHECK (failures >= 0),
|
|
373
|
+
total INTEGER NOT NULL CHECK (total > 0 AND failures <= total),
|
|
374
|
+
evidence_digest TEXT NOT NULL CHECK (length(evidence_digest) = 64),
|
|
375
|
+
evidence_total INTEGER NOT NULL CHECK (evidence_total = total),
|
|
376
|
+
evidence_window INTEGER NOT NULL CHECK (evidence_window >= evidence_total),
|
|
377
|
+
sample_episode_ids_json TEXT NOT NULL CHECK (
|
|
378
|
+
json_valid(sample_episode_ids_json)
|
|
379
|
+
AND json_type(sample_episode_ids_json) = 'array'
|
|
380
|
+
AND json_array_length(sample_episode_ids_json) BETWEEN 1 AND 50
|
|
381
|
+
AND json_array_length(sample_episode_ids_json) <= evidence_total),
|
|
382
|
+
evidence_json TEXT NOT NULL CHECK (
|
|
383
|
+
json_valid(evidence_json) AND json_type(evidence_json) = 'array'),
|
|
384
|
+
scope_watermark INTEGER NOT NULL CHECK (scope_watermark >= 1),
|
|
385
|
+
task_revisions_json TEXT NOT NULL CHECK (
|
|
386
|
+
json_valid(task_revisions_json) AND json_type(task_revisions_json) = 'array'),
|
|
387
|
+
proposal_id TEXT,
|
|
388
|
+
created_at INTEGER NOT NULL,
|
|
389
|
+
proposed_at INTEGER,
|
|
390
|
+
UNIQUE(scope_key, occurrence_id),
|
|
391
|
+
FOREIGN KEY(proposal_id) REFERENCES evolution_proposals(id) ON DELETE RESTRICT
|
|
392
|
+
) STRICT;
|
|
393
|
+
CREATE INDEX evolution_supervised_analyst_reviews_proposal
|
|
394
|
+
ON evolution_supervised_analyst_reviews(proposal_id)
|
|
395
|
+
WHERE proposal_id IS NOT NULL;
|
|
396
|
+
`;
|
|
397
|
+
const applicationReceiptSchema = `
|
|
398
|
+
CREATE TABLE evolution_application_receipts (
|
|
399
|
+
local_proposal_id TEXT PRIMARY KEY,
|
|
400
|
+
policy_proposal_id TEXT NOT NULL UNIQUE,
|
|
401
|
+
application_status TEXT NOT NULL CHECK (
|
|
402
|
+
application_status IN ('applied', 'conflicted', 'expired', 'rejected')),
|
|
403
|
+
operation TEXT NOT NULL CHECK (operation IN ('adopt', 'owner-undo', 'retire')),
|
|
404
|
+
terminal_at INTEGER NOT NULL,
|
|
405
|
+
receipt_digest TEXT NOT NULL UNIQUE CHECK (length(receipt_digest) = 64),
|
|
406
|
+
revision INTEGER NOT NULL CHECK (revision >= 2),
|
|
407
|
+
rule_id TEXT,
|
|
408
|
+
resulting_rule_version INTEGER CHECK (
|
|
409
|
+
resulting_rule_version IS NULL OR resulting_rule_version >= 1),
|
|
410
|
+
rule_status TEXT CHECK (rule_status IS NULL OR rule_status IN ('active', 'retired')),
|
|
411
|
+
CHECK (application_status <> 'applied' OR (
|
|
412
|
+
rule_id IS NOT NULL AND resulting_rule_version IS NOT NULL AND rule_status IS NOT NULL)),
|
|
413
|
+
FOREIGN KEY(local_proposal_id) REFERENCES evolution_proposals(id) ON DELETE RESTRICT
|
|
414
|
+
) STRICT;
|
|
415
|
+
|
|
416
|
+
CREATE TABLE evolution_application_outbox (
|
|
417
|
+
local_proposal_id TEXT PRIMARY KEY,
|
|
418
|
+
state TEXT NOT NULL CHECK (state IN ('pending', 'published')),
|
|
419
|
+
attempt_count INTEGER NOT NULL DEFAULT 0 CHECK (attempt_count >= 0),
|
|
420
|
+
updated_at INTEGER NOT NULL,
|
|
421
|
+
published_at INTEGER,
|
|
422
|
+
last_error TEXT,
|
|
423
|
+
FOREIGN KEY(local_proposal_id)
|
|
424
|
+
REFERENCES evolution_application_receipts(local_proposal_id) ON DELETE RESTRICT
|
|
425
|
+
) STRICT, WITHOUT ROWID;
|
|
426
|
+
CREATE INDEX evolution_application_outbox_pending
|
|
427
|
+
ON evolution_application_outbox(state, updated_at, local_proposal_id);
|
|
428
|
+
`;
|
|
429
|
+
function migrateV8ToV9(database) {
|
|
430
|
+
database.exec(`
|
|
431
|
+
-- v8 rows were projected from a raw immutable Evaluation outcome. They
|
|
432
|
+
-- cannot represent a later owner override or objective conflict, so they
|
|
433
|
+
-- must not remain votes once the canonical task projection becomes the
|
|
434
|
+
-- only source. Evaluation v5 requeues retained tasks and repopulates this
|
|
435
|
+
-- ledger through the versioned seam after startup.
|
|
436
|
+
CREATE TEMP TABLE evolution_v9_legacy_learning_scopes AS
|
|
437
|
+
SELECT DISTINCT scope_key FROM evolution_episodes WHERE learning_eligible = 1;
|
|
438
|
+
UPDATE evolution_episodes
|
|
439
|
+
SET evidence_kind = 'legacy-unknown', evidence_ref = NULL,
|
|
440
|
+
learning_subject_ref = NULL, learning_eligible = 0
|
|
441
|
+
WHERE learning_eligible = 1;
|
|
442
|
+
UPDATE evolution_proposals
|
|
443
|
+
SET status = 'conflicted', version = version + 1
|
|
444
|
+
WHERE status = 'pending'
|
|
445
|
+
AND scope_key IN (SELECT scope_key FROM evolution_v9_legacy_learning_scopes);
|
|
446
|
+
DROP TABLE evolution_v9_legacy_learning_scopes;
|
|
447
|
+
|
|
448
|
+
${taskLearningProjectionSchema}
|
|
449
|
+
|
|
450
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '9')
|
|
451
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
452
|
+
PRAGMA user_version = 9;
|
|
453
|
+
`);
|
|
454
|
+
}
|
|
455
|
+
function migrateV9ToV10(database) {
|
|
456
|
+
database.exec(`
|
|
457
|
+
${supervisedGrowthAnalystSchema}
|
|
458
|
+
|
|
459
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '10')
|
|
460
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
461
|
+
PRAGMA user_version = 10;
|
|
462
|
+
`);
|
|
463
|
+
}
|
|
464
|
+
function migrateV10ToV11(database) {
|
|
465
|
+
database.exec(`
|
|
466
|
+
${applicationReceiptSchema}
|
|
467
|
+
|
|
468
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '11')
|
|
469
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
470
|
+
PRAGMA user_version = 11;
|
|
471
|
+
`);
|
|
472
|
+
}
|
|
473
|
+
function migrateV11ToV12(database) {
|
|
474
|
+
const hasColumn = (table, column) => database
|
|
475
|
+
.prepare(`SELECT name FROM pragma_table_info(?) WHERE name = ?`)
|
|
476
|
+
.get(table, column) !== undefined;
|
|
477
|
+
if (!hasColumn('evolution_task_learning_state', 'scope_watermark')) {
|
|
478
|
+
database.exec(`ALTER TABLE evolution_task_learning_state
|
|
479
|
+
ADD COLUMN scope_watermark INTEGER NOT NULL DEFAULT 0 CHECK (scope_watermark >= 0)`);
|
|
480
|
+
}
|
|
481
|
+
if (!hasColumn('evolution_task_learning_revisions', 'scope_watermark')) {
|
|
482
|
+
database.exec(`ALTER TABLE evolution_task_learning_revisions
|
|
483
|
+
ADD COLUMN scope_watermark INTEGER NOT NULL DEFAULT 0 CHECK (scope_watermark >= 0)`);
|
|
484
|
+
}
|
|
485
|
+
if (!hasColumn('evolution_supervised_analyst_reviews', 'scope_watermark')) {
|
|
486
|
+
database.exec(`ALTER TABLE evolution_supervised_analyst_reviews
|
|
487
|
+
ADD COLUMN scope_watermark INTEGER NOT NULL DEFAULT 0 CHECK (scope_watermark >= 0)`);
|
|
488
|
+
}
|
|
489
|
+
if (!hasColumn('evolution_supervised_analyst_reviews', 'task_revisions_json')) {
|
|
490
|
+
database.exec(`ALTER TABLE evolution_supervised_analyst_reviews
|
|
491
|
+
ADD COLUMN task_revisions_json TEXT NOT NULL DEFAULT '[]'
|
|
492
|
+
CHECK (json_valid(task_revisions_json) AND json_type(task_revisions_json) = 'array')`);
|
|
493
|
+
}
|
|
494
|
+
database.exec(`
|
|
495
|
+
CREATE TABLE IF NOT EXISTS evolution_scope_learning_watermarks (
|
|
496
|
+
scope_key TEXT PRIMARY KEY,
|
|
497
|
+
watermark INTEGER NOT NULL CHECK (watermark >= 1),
|
|
498
|
+
updated_at INTEGER NOT NULL
|
|
499
|
+
) STRICT, WITHOUT ROWID;
|
|
500
|
+
|
|
501
|
+
-- No pre-v12 pending proposal froze the authoritative Evaluation scope
|
|
502
|
+
-- watermark and complete task tuple. Preserve it for audit, but never let a
|
|
503
|
+
-- later approval apply it. Attached rows receive terminal receipts during
|
|
504
|
+
-- the normal constructor backfill.
|
|
505
|
+
UPDATE evolution_proposals
|
|
506
|
+
SET status = 'conflicted', version = version + 1
|
|
507
|
+
WHERE status = 'pending';
|
|
508
|
+
|
|
509
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '12')
|
|
510
|
+
ON CONFLICT(key) DO UPDATE SET value = excluded.value;
|
|
511
|
+
PRAGMA user_version = 12;
|
|
512
|
+
`);
|
|
513
|
+
}
|
|
122
514
|
function createCurrentSchema(database) {
|
|
123
515
|
database.exec(`
|
|
124
516
|
CREATE TABLE schema_meta (
|
|
@@ -134,19 +526,41 @@ function createCurrentSchema(database) {
|
|
|
134
526
|
situation TEXT NOT NULL,
|
|
135
527
|
outcome TEXT NOT NULL CHECK (outcome IN ('succeeded', 'failed')),
|
|
136
528
|
detail TEXT NOT NULL,
|
|
137
|
-
source TEXT NOT NULL CHECK (source IN ('automation', 'foreground')),
|
|
529
|
+
source TEXT NOT NULL CHECK (source IN ('automation', 'evaluation', 'foreground')),
|
|
138
530
|
scope_key TEXT NOT NULL,
|
|
139
531
|
trust TEXT NOT NULL CHECK (trust IN ('trusted', 'self-reported', 'legacy')),
|
|
532
|
+
evidence_kind TEXT NOT NULL CHECK (
|
|
533
|
+
evidence_kind IN ('operational', 'objective', 'verification', 'legacy-unknown')),
|
|
534
|
+
evidence_ref TEXT,
|
|
535
|
+
learning_subject_ref TEXT,
|
|
536
|
+
learning_eligible INTEGER NOT NULL CHECK (learning_eligible IN (0, 1)),
|
|
140
537
|
rule_id TEXT,
|
|
141
538
|
guidance_version INTEGER CHECK (guidance_version IS NULL OR guidance_version >= 1),
|
|
142
539
|
claimed_rule_id TEXT,
|
|
143
|
-
occurred_at INTEGER NOT NULL
|
|
540
|
+
occurred_at INTEGER NOT NULL,
|
|
541
|
+
CHECK ((learning_eligible = 0 AND learning_subject_ref IS NULL) OR (
|
|
542
|
+
learning_eligible = 1
|
|
543
|
+
AND learning_subject_ref IS NOT NULL
|
|
544
|
+
AND
|
|
545
|
+
source = 'evaluation'
|
|
546
|
+
AND
|
|
547
|
+
trust = 'trusted'
|
|
548
|
+
AND evidence_kind IN ('objective', 'verification')
|
|
549
|
+
AND evidence_ref IS NOT NULL))
|
|
144
550
|
) STRICT;
|
|
145
551
|
|
|
146
552
|
CREATE INDEX evolution_episodes_adoption
|
|
147
|
-
ON evolution_episodes(
|
|
553
|
+
ON evolution_episodes(
|
|
554
|
+
scope_key, situation, learning_eligible, rule_id, occurred_at DESC, id DESC);
|
|
148
555
|
CREATE INDEX evolution_episodes_evaluation
|
|
149
|
-
ON evolution_episodes(
|
|
556
|
+
ON evolution_episodes(
|
|
557
|
+
rule_id, guidance_version, learning_eligible, occurred_at DESC, id DESC);
|
|
558
|
+
CREATE UNIQUE INDEX evolution_episodes_quality_evidence_identity
|
|
559
|
+
ON evolution_episodes(scope_key, evidence_ref)
|
|
560
|
+
WHERE learning_eligible = 1;
|
|
561
|
+
CREATE UNIQUE INDEX evolution_episodes_learning_subject_identity
|
|
562
|
+
ON evolution_episodes(scope_key, learning_subject_ref)
|
|
563
|
+
WHERE learning_eligible = 1;
|
|
150
564
|
|
|
151
565
|
CREATE TABLE evolution_rules (
|
|
152
566
|
id TEXT PRIMARY KEY,
|
|
@@ -233,8 +647,20 @@ function createCurrentSchema(database) {
|
|
|
233
647
|
CREATE INDEX evolution_autonomous_rollbacks_occurred
|
|
234
648
|
ON evolution_autonomous_rollbacks(occurred_at);
|
|
235
649
|
|
|
236
|
-
|
|
237
|
-
|
|
650
|
+
${taskLearningProjectionSchema}
|
|
651
|
+
|
|
652
|
+
CREATE TABLE evolution_scope_learning_watermarks (
|
|
653
|
+
scope_key TEXT PRIMARY KEY,
|
|
654
|
+
watermark INTEGER NOT NULL CHECK (watermark >= 1),
|
|
655
|
+
updated_at INTEGER NOT NULL
|
|
656
|
+
) STRICT, WITHOUT ROWID;
|
|
657
|
+
|
|
658
|
+
${supervisedGrowthAnalystSchema}
|
|
659
|
+
|
|
660
|
+
${applicationReceiptSchema}
|
|
661
|
+
|
|
662
|
+
INSERT INTO schema_meta(key, value) VALUES ('schema-version', '12');
|
|
663
|
+
PRAGMA user_version = 12;
|
|
238
664
|
`);
|
|
239
665
|
}
|
|
240
666
|
/** Serialize every schema transition and re-read the version after the lock. */
|
|
@@ -258,6 +684,22 @@ function migrate(database) {
|
|
|
258
684
|
migrateV2ToV3(database);
|
|
259
685
|
else if (version === 3)
|
|
260
686
|
migrateV3ToV4(database);
|
|
687
|
+
else if (version === 4)
|
|
688
|
+
migrateV4ToV5(database);
|
|
689
|
+
else if (version === 5)
|
|
690
|
+
migrateV5ToV6(database);
|
|
691
|
+
else if (version === 6)
|
|
692
|
+
migrateV6ToV7(database);
|
|
693
|
+
else if (version === 7)
|
|
694
|
+
migrateV7ToV8(database);
|
|
695
|
+
else if (version === 8)
|
|
696
|
+
migrateV8ToV9(database);
|
|
697
|
+
else if (version === 9)
|
|
698
|
+
migrateV9ToV10(database);
|
|
699
|
+
else if (version === 10)
|
|
700
|
+
migrateV10ToV11(database);
|
|
701
|
+
else if (version === 11)
|
|
702
|
+
migrateV11ToV12(database);
|
|
261
703
|
version = schemaVersion(database);
|
|
262
704
|
}
|
|
263
705
|
database.exec('COMMIT');
|
package/lib/sqlite.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"sqlite.js","sourceRoot":"","sources":["../src/sqlite.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,SAAS,CAAA;AAC9C,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,MAAM,WAAW,CAAA;AAC/C,OAAO,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AAE1C,MAAM,CAAC,MAAM,sBAAsB,GAAG,
|
|
1
|
+
{"version":3,"file":"sqlite.js","sourceRoot":"","sources":["../src/sqlite.ts"],"names":[],"mappings":"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"}
|
package/lib/store.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { EpisodeInput,
|
|
1
|
+
import type { EpisodeInput, EvolutionCreationInput, EvolutionMutation, EvolutionSettlementExpectation, GuidanceExposure, ProposalStatus, RuleCandidate, RuleInput, SituationStats, StoredEpisode, StoredEvolutionApplicationOutboxEntry, StoredEvolutionApplicationReceipt, StoredAutonomousRollback, StoredProposal, StoredRule, StoredSupervisedGrowthAnalystReview, StoredTaskLearningProjection, SupervisedGrowthAnalystContractVersion, TaskLearningProjectionInput, TaskLearningProjectionResult } from './types.js';
|
|
2
2
|
export type EvolutionStoreErrorCode = 'idempotency-conflict' | 'invalid-input' | 'invalid-state' | 'not-found' | 'version-conflict';
|
|
3
3
|
export declare class EvolutionStoreError extends Error {
|
|
4
4
|
readonly code: EvolutionStoreErrorCode;
|
|
@@ -18,11 +18,31 @@ export interface EvolutionStoreHealth {
|
|
|
18
18
|
pendingProposals: number;
|
|
19
19
|
conflictedProposals: number;
|
|
20
20
|
trustedEpisodes: number;
|
|
21
|
+
qualityEligibleEpisodes: number;
|
|
22
|
+
operationalEpisodes: number;
|
|
23
|
+
legacyQuarantinedEpisodes: number;
|
|
21
24
|
unattributedTrustedEpisodes: number;
|
|
25
|
+
unattributedQualityEligibleEpisodes: number;
|
|
22
26
|
lastTrustedEpisodeAt: number;
|
|
27
|
+
lastQualityEligibleEpisodeAt: number;
|
|
23
28
|
autonomousRollbacks: number;
|
|
29
|
+
taskLearningProjections: number;
|
|
30
|
+
retractedTaskLearningProjections: number;
|
|
31
|
+
taskLearningProjectionRevisions: number;
|
|
32
|
+
taskLearningProjectionIntegrityErrors: number;
|
|
24
33
|
}
|
|
25
34
|
declare function digest(value: unknown): string;
|
|
35
|
+
/**
|
|
36
|
+
* Stable analyst proposal identity. Deliberately do not add guidance, owner,
|
|
37
|
+
* execution, token, TTL, samples or timestamps: those are not the learned fact.
|
|
38
|
+
*/
|
|
39
|
+
export declare function supervisedGrowthAnalystProposalIdempotencyKey(input: {
|
|
40
|
+
scopeKey: string;
|
|
41
|
+
situation: string;
|
|
42
|
+
evidenceDigest: string;
|
|
43
|
+
evidenceTotal: number;
|
|
44
|
+
contractVersion: SupervisedGrowthAnalystContractVersion;
|
|
45
|
+
}): string;
|
|
26
46
|
/**
|
|
27
47
|
* Durable evidence and rule ledger.
|
|
28
48
|
*
|
|
@@ -43,10 +63,28 @@ export declare class EvolutionStore {
|
|
|
43
63
|
health(): Readonly<EvolutionStoreHealth>;
|
|
44
64
|
/** Record one observed outcome. Idempotent on `idempotencyKey`. */
|
|
45
65
|
recordEpisode(input: EpisodeInput): StoredEpisode;
|
|
46
|
-
/**
|
|
66
|
+
/**
|
|
67
|
+
* Apply one authoritative Evaluation task revision. The current pointer,
|
|
68
|
+
* immutable revision audit, active learning vote and stale-proposal fence are
|
|
69
|
+
* committed under one SQLite writer lock.
|
|
70
|
+
*
|
|
71
|
+
* The first accepted revision may be greater than one because several old
|
|
72
|
+
* Evaluation outbox triggers all resolve to the latest canonical task. A
|
|
73
|
+
* lower revision is never acknowledged: it indicates an Evaluation rollback
|
|
74
|
+
* or a mismatched database restore and must remain visible to recovery.
|
|
75
|
+
*/
|
|
76
|
+
applyTaskLearningProjection(input: TaskLearningProjectionInput): TaskLearningProjectionResult;
|
|
77
|
+
getTaskLearningProjection(input: {
|
|
78
|
+
scopeKey: string;
|
|
79
|
+
subjectKind: 'automation-run' | 'outcome';
|
|
80
|
+
subjectRef: string;
|
|
81
|
+
}): StoredTaskLearningProjection | undefined;
|
|
82
|
+
/** Failure counts over the most recent explicitly quality-eligible episodes. */
|
|
47
83
|
stats(scopeKey: string, situation: string, window: number): SituationStats;
|
|
48
84
|
listRules(scopeKey: string, status?: 'active' | 'retired'): StoredRule[];
|
|
49
85
|
getRule(ruleId: string): StoredRule | undefined;
|
|
86
|
+
/** Principal whose exact approved adoption created this immutable rule. */
|
|
87
|
+
ruleApprovalPrincipal(ruleId: string): string | undefined;
|
|
50
88
|
activeRule(scopeKey: string, situation: string): StoredRule | undefined;
|
|
51
89
|
nextGeneration(scopeKey: string, situation: string): number;
|
|
52
90
|
/** Persist proof only after the corresponding guidance injection returned. */
|
|
@@ -58,6 +96,7 @@ export declare class EvolutionStore {
|
|
|
58
96
|
guidanceVersion: number;
|
|
59
97
|
}): GuidanceExposure;
|
|
60
98
|
hasGuidanceExposure(sessionId: string, scopeKey: string, ruleId: string, guidanceVersion: number): boolean;
|
|
99
|
+
countGuidanceExposures(sessionId: string, scopeKey: string): number;
|
|
61
100
|
/** Return only an unambiguous exact-situation receipt for one session. */
|
|
62
101
|
captureGuidanceExposure(sessionId: string, scopeKey: string, situation: string): GuidanceExposure | undefined;
|
|
63
102
|
/**
|
|
@@ -93,6 +132,41 @@ export declare class EvolutionStore {
|
|
|
93
132
|
retireFailureRate: number;
|
|
94
133
|
evidenceSampleLimit?: number;
|
|
95
134
|
}): RuleCandidate | undefined;
|
|
135
|
+
/**
|
|
136
|
+
* Freeze the one adoption candidate shown to an exact production analyst
|
|
137
|
+
* execution. Repeating review in the same occurrence returns the same opaque
|
|
138
|
+
* token; if its evidence changed, the old execution is fenced instead.
|
|
139
|
+
*/
|
|
140
|
+
registerSupervisedGrowthAnalystReview(input: {
|
|
141
|
+
scopeKey: string;
|
|
142
|
+
occurrenceId: string;
|
|
143
|
+
candidate: RuleCandidate;
|
|
144
|
+
evidenceWindow: number;
|
|
145
|
+
}): Readonly<{
|
|
146
|
+
review: StoredSupervisedGrowthAnalystReview;
|
|
147
|
+
proposalExists: boolean;
|
|
148
|
+
}>;
|
|
149
|
+
getSupervisedGrowthAnalystReview(reviewToken: string): StoredSupervisedGrowthAnalystReview | undefined;
|
|
150
|
+
/**
|
|
151
|
+
* Create or join the proposal for one evidence identity under the SQLite
|
|
152
|
+
* writer lock. The existing proposal is deliberately returned without
|
|
153
|
+
* comparing guidance: the first committed wording is the durable winner.
|
|
154
|
+
*/
|
|
155
|
+
createSupervisedGrowthAnalystProposal(input: {
|
|
156
|
+
reviewToken: string;
|
|
157
|
+
scopeKey: string;
|
|
158
|
+
occurrenceId: string;
|
|
159
|
+
requester: string;
|
|
160
|
+
principal: string;
|
|
161
|
+
mutation: Extract<EvolutionMutation, {
|
|
162
|
+
op: 'adopt';
|
|
163
|
+
}>;
|
|
164
|
+
expiresAt: number;
|
|
165
|
+
creationIntent: EvolutionCreationInput;
|
|
166
|
+
}): Readonly<{
|
|
167
|
+
proposal: StoredProposal;
|
|
168
|
+
replayed: boolean;
|
|
169
|
+
}>;
|
|
96
170
|
/**
|
|
97
171
|
* Retire one exact active guidance generation through the narrow autonomous
|
|
98
172
|
* rollback lane.
|
|
@@ -121,11 +195,32 @@ export declare class EvolutionStore {
|
|
|
121
195
|
principal: string;
|
|
122
196
|
mutation: EvolutionMutation;
|
|
123
197
|
expiresAt: number;
|
|
124
|
-
creationIntent?:
|
|
198
|
+
creationIntent?: EvolutionCreationInput;
|
|
125
199
|
}): StoredProposal;
|
|
126
200
|
attachPolicy(proposalId: string, policyProposalId: string, expectation?: EvolutionSettlementExpectation): StoredProposal;
|
|
127
201
|
getProposal(proposalId: string): StoredProposal | undefined;
|
|
202
|
+
getProposalByIdempotencyKey(idempotencyKey: string): StoredProposal | undefined;
|
|
128
203
|
listPendingProposals(limit: number): StoredProposal[];
|
|
204
|
+
/**
|
|
205
|
+
* Recover cross-database creation intents that may already own a Policy card
|
|
206
|
+
* even when local evidence invalidation made the proposal terminal first.
|
|
207
|
+
*/
|
|
208
|
+
listUnattachedProposalIntents(limit: number): StoredProposal[];
|
|
209
|
+
/**
|
|
210
|
+
* Policy has authoritatively confirmed that an expired unattached intent did
|
|
211
|
+
* not create a proposal. Drop only that now-useless recovery payload so the
|
|
212
|
+
* terminal local conflict is not rediscovered forever.
|
|
213
|
+
*/
|
|
214
|
+
completeAbandonedProposalRecovery(proposalId: string): StoredProposal;
|
|
215
|
+
getEvolutionApplicationReceipt(localProposalId: string): StoredEvolutionApplicationReceipt | undefined;
|
|
216
|
+
/** Independent terminal-presentation outbox; it never scans pending proposals. */
|
|
217
|
+
listPendingEvolutionApplicationReceipts(limit: number): StoredEvolutionApplicationOutboxEntry[];
|
|
218
|
+
settleEvolutionApplicationPublication(input: {
|
|
219
|
+
localProposalId: string;
|
|
220
|
+
receiptDigest: string;
|
|
221
|
+
outcome: 'published' | 'retry';
|
|
222
|
+
error?: string;
|
|
223
|
+
}): StoredEvolutionApplicationOutboxEntry;
|
|
129
224
|
/** Move an inspected-but-still-pending row behind its peers, durably. */
|
|
130
225
|
deferPendingProposal(proposalId: string): void;
|
|
131
226
|
/**
|