ds4-context-engine 0.1.2 → 0.2.0-beta.1
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 +79 -13
- package/docs/ARCHITECTURE.md +33 -16
- package/docs/CONTEXT_MANIFEST.md +3 -1
- package/docs/CONTEXT_PLANNER.md +9 -1
- package/docs/CONTEXT_QUALITY.md +91 -0
- package/docs/HYBRID_RETRIEVAL.md +117 -0
- package/docs/LEARNED_RANKING.md +90 -0
- package/docs/MEMORY_AND_PINS.md +11 -5
- package/docs/PORTABLE_CORE.md +9 -5
- package/docs/PROJECT_KNOWLEDGE.md +26 -16
- package/docs/RELEASING.md +18 -13
- package/docs/RETRIEVAL.md +1 -1
- package/docs/ROADMAP_0.2.0.md +12 -0
- package/docs/RUNTIME_ADAPTER_KIT.md +143 -0
- package/docs/STORAGE.md +35 -7
- package/package.json +12 -7
- package/quality/corpus-v1.json +208 -0
- package/quality/semantic-corpus-v1.json +84 -0
- package/quality/symbol-corpus-v1.json +38 -0
- package/scripts/compare-context-quality.mjs +23 -0
- package/src/extension/commands.ts +213 -1
- package/src/extension/index.ts +1 -0
- package/src/extension/runtime.ts +622 -16
- package/src/pi-adapter/local-embedding.ts +132 -0
- package/src/pi-adapter/memory-adapter.ts +18 -8
- package/src/pi-adapter/project-memory-sync.ts +499 -0
- package/src/pi-adapter/ranking-adapter.ts +72 -0
- package/src/pi-adapter/runtime-contract.ts +86 -0
- package/src/pi-adapter/version.ts +3 -3
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
# Learned Ranking
|
|
2
|
+
|
|
3
|
+
M18 adds an optional metadata-only linear ranker while preserving the deterministic static ranker as the universal fallback.
|
|
4
|
+
|
|
5
|
+
## Modes
|
|
6
|
+
|
|
7
|
+
```json
|
|
8
|
+
{
|
|
9
|
+
"ranking": {
|
|
10
|
+
"mode": "shadow",
|
|
11
|
+
"modelPath": "ds4-context/ranking-model.json",
|
|
12
|
+
"minimumTrainingSamples": 20,
|
|
13
|
+
"maxTrainingSamples": 10000,
|
|
14
|
+
"maxLatencyMs": 10
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
- `off` does not load or evaluate a learned model.
|
|
20
|
+
- `shadow` evaluates a valid model, records only aggregate rank disagreement, and keeps static selection unchanged.
|
|
21
|
+
- `active` changes supplemental-candidate ordering only when the checksummed artifact contains a successful promotion report. Missing, incompatible, corrupt, unpromoted, or regressing artifacts fall back to static ranking.
|
|
22
|
+
|
|
23
|
+
`off` is the upgrade default. Privacy filtering, mandatory pins, current-request retention, category budgets, atomic groups, and hard input limits remain authoritative in every mode.
|
|
24
|
+
|
|
25
|
+
## Bounded feature schema
|
|
26
|
+
|
|
27
|
+
`ranking-features-v1` contains only a source-kind enum and ten finite normalized numbers:
|
|
28
|
+
|
|
29
|
+
- static score;
|
|
30
|
+
- exact-match score;
|
|
31
|
+
- FTS score;
|
|
32
|
+
- vector score;
|
|
33
|
+
- recency;
|
|
34
|
+
- active-branch relation;
|
|
35
|
+
- symbol relation;
|
|
36
|
+
- classification eligibility;
|
|
37
|
+
- token cost;
|
|
38
|
+
- prior selection outcome.
|
|
39
|
+
|
|
40
|
+
All numbers are bounded to `[0, 1]`. Candidate text, excerpts, prompts, file paths, symbols, claims, provider payloads, and credentials are not model features. Stable candidate and repository identities are SHA-256 hashes in canonical labels.
|
|
41
|
+
|
|
42
|
+
## Canonical labels and local training
|
|
43
|
+
|
|
44
|
+
Explicit feedback is appended through Pi as a classified `ds4-context-ranking-feedback-v1` custom entry:
|
|
45
|
+
|
|
46
|
+
```text
|
|
47
|
+
/context ranking feedback useful CANDIDATE_ID --classification internal
|
|
48
|
+
/context ranking feedback irrelevant CANDIDATE_ID --classification local-only
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
Only candidates from the latest managed context are accepted. A feedback entry contains schema/version, feedback ID, timestamp, classification, label source, label, two hashes, and the bounded feature vector. It contains no candidate text. Sanitized replay labels use the same schema with `labelSource: "replay"`.
|
|
52
|
+
|
|
53
|
+
Train a local shadow artifact from the active canonical Pi branch:
|
|
54
|
+
|
|
55
|
+
```text
|
|
56
|
+
/context ranking train
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
Training is deterministic for the same unique labels and timestamp, requires both useful and irrelevant examples, and is bounded by `minimumTrainingSamples` and `maxTrainingSamples`. The artifact is written with mode `0600` where supported. Training never calls a provider and does not make the resulting artifact active.
|
|
60
|
+
|
|
61
|
+
## Artifact integrity and deterministic inference
|
|
62
|
+
|
|
63
|
+
`ranking-model.json` uses schema version `1`, feature version `ranking-features-v1`, algorithm `bounded-linear-centroid-v1`, bounded weights, training counts, a deterministic model ID, and a SHA-256 checksum over its stable JSON payload. Inference uses rounded finite arithmetic and resolves equal scores by static score and then candidate ID.
|
|
64
|
+
|
|
65
|
+
The model artifact is local derived state. Deleting it preserves Pi JSONL labels and restores static ranking. A newly trained artifact can be reconstructed from canonical labels.
|
|
66
|
+
|
|
67
|
+
## Promotion gate
|
|
68
|
+
|
|
69
|
+
`evaluateRankingPromotion()` in `ds4-context-core/ranking/learned-ranker` evaluates sanitized held-out fixtures. `withRankingPromotion()` seals the resulting report into a new checksummed artifact. Promotion succeeds only when all of these conditions hold:
|
|
70
|
+
|
|
71
|
+
- primary quality score improves;
|
|
72
|
+
- exact-identifier recall does not regress;
|
|
73
|
+
- privacy violations do not increase;
|
|
74
|
+
- atomicity failures do not increase;
|
|
75
|
+
- overflow does not increase;
|
|
76
|
+
- measured p95 latency stays within budget;
|
|
77
|
+
- repeated inference yields identical ordering;
|
|
78
|
+
- the configured minimum number of held-out repositories is represented.
|
|
79
|
+
|
|
80
|
+
An artifact without an eligible report can run in shadow mode but cannot alter context in active mode.
|
|
81
|
+
|
|
82
|
+
## Diagnostics
|
|
83
|
+
|
|
84
|
+
```text
|
|
85
|
+
/context ranking
|
|
86
|
+
/context health
|
|
87
|
+
/context manifest
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
Ranking diagnostics include mode/status, versions, model identity, promotion state, label counts, malformed/duplicate counts, candidate count, top-rank disagreement, pairwise disagreements, mean rank shift, inference duration, and fallback reason. Shadow diagnostics and Context Manifests contain aggregate comparison only—never candidate IDs, labels, features, or text.
|
package/docs/MEMORY_AND_PINS.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Memory and Persistent Pins
|
|
2
2
|
|
|
3
|
-
M9 separates durable, user-curated state from conversation history while keeping Pi JSONL canonical.
|
|
3
|
+
M9 separates durable, user-curated state from conversation history while keeping Pi JSONL canonical. M17 optionally reconstructs explicit project-scoped mutations from sibling Pi sessions for the same trusted canonical project.
|
|
4
4
|
|
|
5
5
|
## Authority and scope
|
|
6
6
|
|
|
@@ -30,9 +30,12 @@ Pins remain subordinate to system/developer instructions. Memory tells the model
|
|
|
30
30
|
/context memory supersede MEMORY_ID [--classification LEVEL] [--source ID,ID] <new claim>
|
|
31
31
|
/context memory invalidate MEMORY_ID [reason]
|
|
32
32
|
/context memory expire MEMORY_ID [reason]
|
|
33
|
+
/context memory sources
|
|
34
|
+
/context memory exclude SESSION_ID [reason]
|
|
35
|
+
/context memory include SESSION_ID
|
|
33
36
|
```
|
|
34
37
|
|
|
35
|
-
Arguments support single/double quotes and backslash escaping. `--` ends option parsing. Source entry IDs must be on Pi's active branch. Project scope requires Pi project trust.
|
|
38
|
+
Arguments support single/double quotes and backslash escaping. `--` ends option parsing. Source entry IDs must be on Pi's active branch. Project scope requires Pi project trust. Source exclusion affects only project-scoped contributions and persists until `include`; the active session cannot be newly excluded but can restore a prior exclusion.
|
|
36
39
|
|
|
37
40
|
Mutations are manual-first. Repeating the same normalized pin/claim returns its existing ID without appending another entry.
|
|
38
41
|
|
|
@@ -60,7 +63,7 @@ No row is silently overwritten. SQLite mutation and materialized tables are disp
|
|
|
60
63
|
3. replays all known mutations in timestamp + canonical entry order;
|
|
61
64
|
4. rebuilds memory, pin, source, lifecycle, and FTS rows transactionally.
|
|
62
65
|
|
|
63
|
-
Deleting `context.db` and reopening the canonical source session reconstructs its state.
|
|
66
|
+
Deleting `context.db` and reopening the canonical source session reconstructs its state. With `memory.crossSession: true`, DS4 discovers bounded sibling `.jsonl` files, accepts only headers whose `cwd` resolves to the exact trusted canonical project identity, incrementally indexes each source, and reconstructs project items without opening every session manually. No claim is extracted from ordinary conversation text.
|
|
64
67
|
|
|
65
68
|
## Supersession and contradiction handling
|
|
66
69
|
|
|
@@ -80,7 +83,7 @@ A conflicting `add` is rejected with the IDs involved. The user must issue expli
|
|
|
80
83
|
"Package export mode defaults to SingleFile."
|
|
81
84
|
```
|
|
82
85
|
|
|
83
|
-
The old item remains stored as `superseded` and points to the new active item. During replay,
|
|
86
|
+
The old item remains stored as `superseded` and points to the new active item. During replay, records are ordered by timestamp, source session ID, source entry order, mutation ID and mutation entry key. Concurrent active records with the same key are both preserved; the deterministic later record is marked `invalid` with a conflict reason rather than replacing the earlier one. Selected items retain source-session file/ID, mutation entry, creation branch leaf, evidence entries, classification, supersession and contradiction IDs.
|
|
84
87
|
|
|
85
88
|
Pins use the same immutable replacement pattern through `--supersedes`. `/context unpin` records a soft `deleted` lifecycle mutation.
|
|
86
89
|
|
|
@@ -126,7 +129,7 @@ User text is JSON-quoted. Context Manifests contain IDs, scope, classification,
|
|
|
126
129
|
|
|
127
130
|
M10 stores an optional classification in the canonical mutation. Before a remote call, a prohibited pin/memory is omitted as a whole and recorded only by ID/classification/reason. Explicit classification cannot be downgraded by markers inside its content. See [`PRIVACY.md`](PRIVACY.md).
|
|
128
131
|
|
|
129
|
-
## SQLite schema v9
|
|
132
|
+
## SQLite schema v9 and v15
|
|
130
133
|
|
|
131
134
|
Schema v9 extends materialized `memory_items` and `pins` with:
|
|
132
135
|
|
|
@@ -136,6 +139,8 @@ Schema v9 extends materialized `memory_items` and `pins` with:
|
|
|
136
139
|
|
|
137
140
|
`memory_mutations` and `pin_mutations` reference canonical indexed Pi custom entries. `memory_sources` retains exact scoped entry provenance. `memory_fts` is rebuilt transactionally.
|
|
138
141
|
|
|
142
|
+
Schema v15 adds source-branch provenance, per-session project-memory checkpoints, source status and explicit source exclusions. These rows are derived and disposable. Missing, truncated, moved, identity-mismatched or corrupt sibling files are marked unavailable and their unverifiable project-scoped mutations stop contributing; session-scoped state remains isolated and the active session keeps its last transactional projection on refresh failure. Restoration or database deletion causes deterministic replay from JSONL.
|
|
143
|
+
|
|
139
144
|
Migration preserves legacy materialized rows for inspection. Because they have no canonical mutation entry, a later full replay may discard them; new operations are always event-sourced.
|
|
140
145
|
|
|
141
146
|
## Diagnostics
|
|
@@ -148,6 +153,7 @@ Migration preserves legacy materialized rows for inspection. Because they have n
|
|
|
148
153
|
/context excluded
|
|
149
154
|
/context pins
|
|
150
155
|
/context memory
|
|
156
|
+
/context memory sources
|
|
151
157
|
/context health
|
|
152
158
|
/context rebuild-index
|
|
153
159
|
```
|
package/docs/PORTABLE_CORE.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Portable Core
|
|
2
2
|
|
|
3
|
-
M13 extracts the runtime-neutral implementation into the independently buildable `ds4-context-core` workspace package. The root `ds4-context-engine` package remains the Pi integration.
|
|
3
|
+
M13 extracts the runtime-neutral implementation into the independently buildable `ds4-context-core` workspace package. The root `ds4-context-engine` package remains the Pi integration. M19 adds the versioned adapter contract/conformance kit in core and a separately compiled non-Pi callback/JSONL reference adapter.
|
|
4
4
|
|
|
5
5
|
## Dependency rule
|
|
6
6
|
|
|
@@ -14,7 +14,7 @@ ds4-context-core
|
|
|
14
14
|
|
|
15
15
|
Core never imports an adapter or runtime SDK. The Pi adapter imports core through its public ESM exports.
|
|
16
16
|
|
|
17
|
-
The core may use Node.js standard-library facilities such as `node:sqlite`, filesystem APIs and cryptographic hashing. Portable means independent of
|
|
17
|
+
The core may use Node.js standard-library facilities such as `node:sqlite`, filesystem APIs and cryptographic hashing. Portable means independent of every agent runtime SDK and reusable by another Node-based agent runtime; it does not mean browser-compatible.
|
|
18
18
|
|
|
19
19
|
## Package contents
|
|
20
20
|
|
|
@@ -44,7 +44,7 @@ The root adapter owns all Pi-specific behavior:
|
|
|
44
44
|
|
|
45
45
|
## Adapter responsibilities
|
|
46
46
|
|
|
47
|
-
|
|
47
|
+
Every `runtime-adapter-v1` implementation must:
|
|
48
48
|
|
|
49
49
|
1. preserve its runtime's canonical history and expose stable source identifiers;
|
|
50
50
|
2. convert native messages to DS4 canonical messages without losing tool-call/result atomicity;
|
|
@@ -57,14 +57,18 @@ A future runtime adapter must:
|
|
|
57
57
|
9. discard or rebuild SQLite and artifact projections safely;
|
|
58
58
|
10. fall back to native runtime behavior when operational integration fails.
|
|
59
59
|
|
|
60
|
+
The executable contract, independent capability negotiation and framework-neutral seven-case conformance runner are exported from `ds4-context-core/adapter/runtime-adapter` and `ds4-context-core/adapter/conformance`. See [Runtime Adapter Kit](RUNTIME_ADAPTER_KIT.md).
|
|
61
|
+
|
|
60
62
|
## Build and exports
|
|
61
63
|
|
|
62
64
|
```bash
|
|
63
65
|
npm run build:core
|
|
66
|
+
npm run build:adapters
|
|
64
67
|
npm run typecheck
|
|
65
68
|
npm test
|
|
66
69
|
npm run pack:check
|
|
67
70
|
npm pack --dry-run --workspace ds4-context-core
|
|
71
|
+
npm pack --dry-run --workspace ds4-context-reference-adapter
|
|
68
72
|
```
|
|
69
73
|
|
|
70
74
|
TypeScript sources compile to `packages/core/dist` as ESM JavaScript, source maps and declaration files. The npm package exports a top-level API and fine-grained subpaths such as:
|
|
@@ -74,11 +78,11 @@ import { calculateContextBudget } from "ds4-context-core";
|
|
|
74
78
|
import { planManagedContext } from "ds4-context-core/planner/context-planner";
|
|
75
79
|
```
|
|
76
80
|
|
|
77
|
-
The Pi
|
|
81
|
+
The Pi and reference packages declare exact same-release dependencies on `ds4-context-core`. Release order is core, reference adapter, then Pi adapter. `npm run pack:check` verifies all three tarball inventories, installs them together in a clean temporary consumer, probes core ESM exports, runs compiled reference conformance and starts the packaged Pi adapter with isolated RPC state. See [Releasing DS4](RELEASING.md) for the publication checklist.
|
|
78
82
|
|
|
79
83
|
## Enforcement
|
|
80
84
|
|
|
81
|
-
`tests/unit/portable-core-boundary.test.ts` recursively rejects Pi SDK and adapter imports from core source, then imports the compiled package and exercises portable model/budget policy. Existing integration tests consume core through package exports, so the Pi adapter is tested across the actual package boundary.
|
|
85
|
+
`tests/unit/portable-core-boundary.test.ts` recursively rejects Pi SDK and adapter imports from core source, then imports the compiled package and exercises portable model/budget policy. Runtime-adapter unit tests validate capability isolation and canonical tool groups; the reference package passes the shared conformance runner. Existing integration tests consume core through package exports, so the Pi adapter is tested across the actual package boundary.
|
|
82
86
|
|
|
83
87
|
## State guarantees
|
|
84
88
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Project Knowledge
|
|
2
2
|
|
|
3
|
-
M7 indexes trusted project files as a disposable SQLite projection and injects only task-relevant, hash-current snippets. Live files remain canonical.
|
|
3
|
+
M7 indexes trusted project files as a disposable SQLite projection and injects only task-relevant, hash-current snippets. M15 adds runtime-neutral structural symbol parsing and exact symbol lookup. M16 optionally adds vectors over those structural/text chunks while preserving exact and FTS retrieval. Live files remain canonical.
|
|
4
4
|
|
|
5
5
|
## Trust boundary
|
|
6
6
|
|
|
@@ -36,29 +36,37 @@ DS4 excludes VCS metadata, `.pi`, dependencies, build outputs, caches, virtual e
|
|
|
36
36
|
|
|
37
37
|
## File and snippet index
|
|
38
38
|
|
|
39
|
-
SQLite schema v7
|
|
39
|
+
SQLite schema v7 introduced:
|
|
40
40
|
|
|
41
41
|
- `project_states`: canonical project path, Git root/branch/HEAD, dirty flag, changed paths, index time;
|
|
42
42
|
- `project_files`: path, SHA-256, bytes, mtime, language, indexed Git HEAD, tracked/modified state, lifecycle;
|
|
43
|
-
- `project_snippets`: immutable file hash, line range, source,
|
|
43
|
+
- `project_snippets`: immutable file hash, line range, source, token estimate and stale flag;
|
|
44
44
|
- `project_snippets_fts`: FTS5 content/path/symbol index.
|
|
45
45
|
|
|
46
|
-
|
|
46
|
+
Schema v12 adds derived structural metadata to each snippet: chunk kind, parser version, symbol ID/name/kind, qualified name, signature, parent symbol, imports and references. Exact-name indexes remain disposable and rebuild from live project files. Schema v13 stores separately keyed derived vectors; a file-hash change prunes only vectors for no-longer-current chunks, while unrelated source and embedding-profile rows remain intact.
|
|
47
47
|
|
|
48
|
-
|
|
48
|
+
`ds4-context-core` exposes a `SymbolParser` interface. The built-in `regex-structural-v1` parser has deterministic coverage for TypeScript, JavaScript, Python and Go without native dependencies. Optional parser adapters run first through `SymbolParserChain`; an unavailable or throwing adapter falls through to the built-in parser. Unsupported languages, malformed delimiter structure, supported files with no declarations and files carrying explicit DS4 classification spans retain the M7 overlapping text-window fallback. Keeping marked spans intact ensures M10 privacy enforcement sees the same boundaries as the 0.1 index.
|
|
49
|
+
|
|
50
|
+
Structural chunks follow declaration boundaries and retain signatures, parent relationships, imports/references and exact line ranges. Large declarations are split into bounded overlapping subchunks while sharing one symbol identity. Symbol IDs are SHA-256 values derived from canonical project identity, relative path, file hash, structural range, symbol kind and qualified name. Text fallback IDs retain their deterministic project/path/hash/range derivation.
|
|
51
|
+
|
|
52
|
+
A full or incremental sync compares size, mtime, Git revision and modified state. Source is re-read and SHA-256 hashed whenever metadata changes. Replacing one file marks only that path's prior snippets stale, then transactionally inserts the new file-hash rows and FTS entries; unrelated file rows keep their IDs. Stale rows remain inspectable, but every exact and FTS query requires `stale = 0` and a current file row.
|
|
49
53
|
|
|
50
54
|
## Retrieval and ranking
|
|
51
55
|
|
|
52
|
-
The same current-request `TaskDescriptor` used for historical retrieval supplies file paths, symbols, identifiers, errors, quoted phrases, technologies
|
|
56
|
+
The same current-request `TaskDescriptor` used for historical retrieval supplies file paths, symbols, identifiers, errors, quoted phrases, technologies and keywords. Candidate generation queries literal exact path/basename and exact qualified/simple symbol indexes before generic literal content and escaped FTS5 candidates. Exact lookup does not treat comment, string or reference text as a declaration.
|
|
57
|
+
|
|
58
|
+
When `retrieval.semantic` is enabled, the current embedding profile also contributes a bounded cosine-ranked pool. Deterministic reciprocal-rank fusion combines lexical and vector ranks; exact paths and symbols retain higher score tiers. Source vectors are populated during index sync and query vectors use a bounded volatile cache. Vector/model/privacy failures return the exact/FTS candidates unchanged. See [`HYBRID_RETRIEVAL.md`](HYBRID_RETRIEVAL.md).
|
|
53
59
|
|
|
54
60
|
Deterministic ranking prioritizes:
|
|
55
61
|
|
|
56
62
|
```text
|
|
57
|
-
exact
|
|
58
|
-
exact
|
|
59
|
-
|
|
63
|
+
exact qualified symbol 190
|
|
64
|
+
exact project-relative path 180
|
|
65
|
+
exact simple symbol 170
|
|
66
|
+
exact basename 150
|
|
67
|
+
declared fallback symbol 115
|
|
60
68
|
exact phrase 90
|
|
61
|
-
symbol text
|
|
69
|
+
symbol text 65
|
|
62
70
|
FTS match 60..20
|
|
63
71
|
working-tree change 10
|
|
64
72
|
tracked source 3
|
|
@@ -123,17 +131,19 @@ Source text is not copied into the Context Manifest or structured logs. It remai
|
|
|
123
131
|
|
|
124
132
|
## Fail-open behavior
|
|
125
133
|
|
|
126
|
-
Project discovery, Git, indexing, FTS, validation
|
|
134
|
+
Project discovery, Git, optional parser adapters, indexing, FTS, validation and retrieval errors are isolated from session indexing and context planning. Parser adapter failure uses deterministic regex fallback; unsupported or invalid source uses bounded text chunks. A project subsystem failure records local diagnostics and contributes no snippets; Pi and historical retrieval continue. SQLite startup failure retains the existing runtime-wide Pi fallback.
|
|
135
|
+
|
|
136
|
+
## Verification and benchmark
|
|
127
137
|
|
|
128
|
-
|
|
138
|
+
`quality/symbol-corpus-v1.json` is a synthetic, versioned TypeScript/JavaScript/Python/Go corpus with expected and forbidden declarations. Unit coverage verifies that structural parsing produces fewer false symbol matches than the preserved 0.1 regex extractor. Integration coverage verifies exact qualified/path lookup, metadata fields, stable IDs, unsupported/invalid fallback, changed-file invalidation, unrelated-file stability, trust/exclusion behavior and live-hash validation.
|
|
129
139
|
|
|
130
140
|
`tests/benchmarks/project-knowledge.bench.ts` creates and indexes 5,000 source files, then executes exact path/symbol plus FTS retrieval with live hash validation:
|
|
131
141
|
|
|
132
142
|
```text
|
|
133
|
-
mean
|
|
134
|
-
p75
|
|
135
|
-
p99 21
|
|
136
|
-
max 21
|
|
143
|
+
mean 29.99 ms
|
|
144
|
+
p75 31.71 ms
|
|
145
|
+
p99 37.21 ms
|
|
146
|
+
max 37.21 ms
|
|
137
147
|
```
|
|
138
148
|
|
|
139
149
|
Command:
|
package/docs/RELEASING.md
CHANGED
|
@@ -1,21 +1,22 @@
|
|
|
1
1
|
# Releasing DS4
|
|
2
2
|
|
|
3
|
-
DS4 publishes
|
|
3
|
+
DS4 publishes three packages with the same version:
|
|
4
4
|
|
|
5
|
-
1. `ds4-context-core`, the runtime-neutral compiled package;
|
|
6
|
-
2. `ds4-context-
|
|
5
|
+
1. `ds4-context-core`, the runtime-neutral compiled package and adapter kit;
|
|
6
|
+
2. `ds4-context-reference-adapter`, the non-Pi callback/JSONL reference implementation;
|
|
7
|
+
3. `ds4-context-engine`, the Pi adapter.
|
|
7
8
|
|
|
8
|
-
|
|
9
|
+
Both adapters have an exact dependency on the matching core version, so core must be published first.
|
|
9
10
|
|
|
10
11
|
## Prerequisites
|
|
11
12
|
|
|
12
13
|
- use a clean `main` checkout synchronized with `origin/main`;
|
|
13
|
-
- use a supported Node.js release and npm account authorized for
|
|
14
|
-
- verify that
|
|
15
|
-
- verify that
|
|
14
|
+
- use a supported Node.js release and npm account authorized for all three package names;
|
|
15
|
+
- verify that all three `package.json` files use the intended version;
|
|
16
|
+
- verify that both adapters depend exactly on that version of `ds4-context-core`;
|
|
16
17
|
- do not include session data, `.pi` state, databases, credentials, or provider payloads.
|
|
17
18
|
|
|
18
|
-
The automated package check enforces matching versions,
|
|
19
|
+
The automated package check enforces matching versions, exact core dependencies, runtime-SDK isolation, bounded tarball inventories, clean consumer installation, core ESM exports, compiled reference-adapter conformance, and packaged Pi extension startup through isolated RPC state.
|
|
19
20
|
|
|
20
21
|
## Validate
|
|
21
22
|
|
|
@@ -29,26 +30,29 @@ git status --short
|
|
|
29
30
|
|
|
30
31
|
CI runs the same checks on the minimum supported Node.js version and the current Node.js LTS line. `npm run pack:check` uses a temporary directory and removes it when complete. Set `DS4_KEEP_PACK_TMP=1` only when diagnosing a failed package check.
|
|
31
32
|
|
|
32
|
-
Review
|
|
33
|
+
Review all public tarballs before publishing:
|
|
33
34
|
|
|
34
35
|
```bash
|
|
35
36
|
npm pack --dry-run --workspace ds4-context-core
|
|
37
|
+
npm pack --dry-run --workspace ds4-context-reference-adapter
|
|
36
38
|
npm pack --dry-run
|
|
37
39
|
```
|
|
38
40
|
|
|
39
41
|
## Version
|
|
40
42
|
|
|
41
|
-
Keep the root package,
|
|
43
|
+
Keep the root package, both workspaces, and exact adapter dependencies synchronized. For a future version stored in `$VERSION`:
|
|
42
44
|
|
|
43
45
|
```bash
|
|
44
46
|
npm pkg set version="$VERSION"
|
|
45
47
|
npm pkg set version="$VERSION" --workspace ds4-context-core
|
|
48
|
+
npm pkg set version="$VERSION" --workspace ds4-context-reference-adapter
|
|
46
49
|
npm pkg set dependencies.ds4-context-core="$VERSION"
|
|
50
|
+
npm pkg set dependencies.ds4-context-core="$VERSION" --workspace ds4-context-reference-adapter
|
|
47
51
|
npm install --package-lock-only
|
|
48
52
|
npm run pack:check
|
|
49
53
|
```
|
|
50
54
|
|
|
51
|
-
Review `package.json`,
|
|
55
|
+
Review `package.json`, both workspace package manifests, and `package-lock.json` before committing the release change.
|
|
52
56
|
|
|
53
57
|
## Publish
|
|
54
58
|
|
|
@@ -57,12 +61,13 @@ Authenticate with npm, verify the active account, and publish in dependency orde
|
|
|
57
61
|
```bash
|
|
58
62
|
npm whoami
|
|
59
63
|
npm publish --workspace ds4-context-core --access public
|
|
64
|
+
npm publish --workspace ds4-context-reference-adapter --access public
|
|
60
65
|
npm publish --access public
|
|
61
66
|
```
|
|
62
67
|
|
|
63
|
-
If core succeeds but adapter publication fails, fix
|
|
68
|
+
If core succeeds but an adapter publication fails, fix that adapter release and retry it with the same version. Do not rewrite or unpublish a valid core release merely to make the commands appear atomic.
|
|
64
69
|
|
|
65
|
-
After
|
|
70
|
+
After all registry packages are available:
|
|
66
71
|
|
|
67
72
|
1. install them in a fresh temporary project and rerun the package smoke check if registry propagation was delayed;
|
|
68
73
|
2. create and push the signed or annotated `v$VERSION` tag;
|
package/docs/RETRIEVAL.md
CHANGED
|
@@ -15,7 +15,7 @@ M6 recovers original session evidence that Pi compaction removed from the active
|
|
|
15
15
|
9. Deduplicate normalized identical text, preferring the higher-ranked/newer source.
|
|
16
16
|
10. Build individually bounded evidence messages, enforce the active provider privacy policy, and let the managed planner fit allowed groups after recent turns but before summaries.
|
|
17
17
|
|
|
18
|
-
No LLM is called during retrieval. `retrieval.semantic: true`
|
|
18
|
+
No chat LLM is called during retrieval. Since M16, `retrieval.semantic: true` adds opt-in vectors through the runtime-neutral `EmbeddingPort`; exact and FTS retrieval remain authoritative and any embedding failure falls back to lexical results. See [Hybrid Semantic Retrieval](HYBRID_RETRIEVAL.md).
|
|
19
19
|
|
|
20
20
|
## Ranking
|
|
21
21
|
|
package/docs/ROADMAP_0.2.0.md
CHANGED
|
@@ -49,6 +49,8 @@ M14 is first because adaptive ranking must be measured against a stable baseline
|
|
|
49
49
|
|
|
50
50
|
## M14 — Context Quality Metrics
|
|
51
51
|
|
|
52
|
+
Status: **implemented on `main` for `0.2.0-alpha.1`**. The active planner remains the 0.1 deterministic baseline; quality collection is opt-in and candidate strategies are replay-only.
|
|
53
|
+
|
|
52
54
|
### Deliverables
|
|
53
55
|
|
|
54
56
|
- A sanitized replay corpus with expected evidence source IDs and task descriptors.
|
|
@@ -70,6 +72,8 @@ Quality samples store planner/profile versions, source-kind counts, token totals
|
|
|
70
72
|
|
|
71
73
|
## M15 — Rich Symbol Indexing
|
|
72
74
|
|
|
75
|
+
Status: **implemented on `main` for `0.2.0-alpha.1`**. Structural parsing remains a disposable local projection; unsupported or invalid source retains deterministic text-window behavior.
|
|
76
|
+
|
|
73
77
|
### Deliverables
|
|
74
78
|
|
|
75
79
|
- A parser interface in `ds4-context-core` with deterministic regex fallback.
|
|
@@ -90,6 +94,8 @@ The parser implementation must not introduce a mandatory native build dependency
|
|
|
90
94
|
|
|
91
95
|
## M16 — Hybrid Semantic Retrieval
|
|
92
96
|
|
|
97
|
+
Status: **implemented on `main` for `0.2.0-alpha.2`**. Semantic retrieval remains opt-in; exact/FTS ranking and lexical-only failure behavior remain available.
|
|
98
|
+
|
|
93
99
|
### Deliverables
|
|
94
100
|
|
|
95
101
|
- A runtime-neutral embedding port; model invocation remains outside core.
|
|
@@ -111,6 +117,8 @@ Semantic retrieval does not replace exact matching. Exact paths, symbols, quoted
|
|
|
111
117
|
|
|
112
118
|
## M17 — Cross-Session Project Memory
|
|
113
119
|
|
|
120
|
+
Status: **implemented on `main` behind `memory.crossSession` for `0.2.0-alpha.3`**. Discovery remains opt-in and exact trusted project identity is mandatory.
|
|
121
|
+
|
|
114
122
|
### Deliverables
|
|
115
123
|
|
|
116
124
|
- Discovery of canonical Pi session JSONL files associated with the same trusted canonical project identity.
|
|
@@ -131,6 +139,8 @@ Version 0.2.0 does not silently extract new memories from conversation text. A d
|
|
|
131
139
|
|
|
132
140
|
## M18 — Learned Ranking
|
|
133
141
|
|
|
142
|
+
Status: **implemented on `main` for `0.2.0-beta.1` with `off`, aggregate-only `shadow`, and promotion-gated `active` modes**. Static ranking remains authoritative for missing, corrupt, incompatible, unpromoted or regressing artifacts.
|
|
143
|
+
|
|
134
144
|
### Deliverables
|
|
135
145
|
|
|
136
146
|
- A bounded feature schema based on metadata such as source kind, exact/FTS/vector scores, recency, branch relation, symbol relation, classification eligibility, token cost and prior selection outcome.
|
|
@@ -153,6 +163,8 @@ If the gate is not met, 0.2.0 ships shadow mode but keeps static ranking active.
|
|
|
153
163
|
|
|
154
164
|
## M19 — Runtime Adapter Kit
|
|
155
165
|
|
|
166
|
+
Status: **implemented on `main` for `0.2.0-beta.2`**. Core ships `runtime-adapter-v1` plus a framework-neutral conformance runner; Pi exposes contract capability diagnostics, and the separately packaged callback/JSONL reference adapter passes all seven conformance cases.
|
|
167
|
+
|
|
156
168
|
### Deliverables
|
|
157
169
|
|
|
158
170
|
- A documented adapter contract for canonical history snapshots, model limits, tool atomicity, trusted project roots, completion, privacy enforcement and lifecycle shutdown.
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
# Runtime Adapter Kit
|
|
2
|
+
|
|
3
|
+
M19 defines `runtime-adapter-v1`, a runtime-neutral boundary between DS4 policy and an agent host. The kit lives in `ds4-context-core/adapter/*`; the non-Pi implementation is published separately as `ds4-context-reference-adapter`. Core imports no runtime SDK.
|
|
4
|
+
|
|
5
|
+
## Dependency and state boundary
|
|
6
|
+
|
|
7
|
+
```text
|
|
8
|
+
native agent runtime / provider SDK
|
|
9
|
+
↓
|
|
10
|
+
runtime adapter package
|
|
11
|
+
↓
|
|
12
|
+
ds4-context-core/adapter/runtime-adapter
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
An adapter owns native history conversion, trusted-root discovery, provider completion, final privacy enforcement, optional runtime capabilities, and shutdown. Core owns contract types, deterministic capability negotiation, canonical tool-group validation, and the framework-neutral conformance runner.
|
|
16
|
+
|
|
17
|
+
The runtime's native history remains canonical. A `RuntimeHistorySnapshot` is a read-only projection with:
|
|
18
|
+
|
|
19
|
+
- `runtimeId`, `sessionId`, schema version, and deterministic source revision;
|
|
20
|
+
- one exact trusted canonical project root;
|
|
21
|
+
- ordered `CanonicalMessage` values with stable source-entry provenance;
|
|
22
|
+
- complete tool call/result atomic groups derived from canonical blocks.
|
|
23
|
+
|
|
24
|
+
Applying a DS4 context plan must not write provider-facing synthetic messages back into canonical history. Rebuild deletes or discards only adapter/DS4 projections and reproduces the snapshot from the native source.
|
|
25
|
+
|
|
26
|
+
## Contract
|
|
27
|
+
|
|
28
|
+
`RuntimeAdapter` requires:
|
|
29
|
+
|
|
30
|
+
| Method | Responsibility | Failure rule |
|
|
31
|
+
|---|---|---|
|
|
32
|
+
| `snapshotHistory()` | Project the active canonical history and tool relations. | Reject an invalid, corrupt, identity-mismatched, or untrusted source. Never invent history. |
|
|
33
|
+
| `rebuildDerivedState()` | Discard adapter caches/projections and replay canonical state. | Preserve canonical files and the previous valid source. |
|
|
34
|
+
| `currentModel()` | Return provider/model limits through `ModelDescriptor`. | Return `undefined` when no model is selected. |
|
|
35
|
+
| `trustedProjectRoot()` | Return the runtime-approved canonical root. | Reject untrusted roots; do not broaden them. |
|
|
36
|
+
| `enforcePrivacy()` | Sanitize a provider payload immediately before transport. | Fail closed and do not invoke transport on error. |
|
|
37
|
+
| `complete()` | Invoke the runtime/provider boundary with the sanitized payload. | Return an explicit fallback result for invalid input, privacy failure, transport failure, or closed lifecycle. |
|
|
38
|
+
| `capabilityDeclarations()` / `negotiateCapabilities()` | Version and independently enable optional host features. | Missing or malformed declarations are unsupported, not fatal to other features. |
|
|
39
|
+
| `diagnostics()` | Return bounded metadata-only state. | Never include prompts, history, credentials, payloads, cache handles, or provider output. |
|
|
40
|
+
| `shutdown()` | Release adapter resources idempotently. | Further writes/completions fall back; history reads are rejected. |
|
|
41
|
+
|
|
42
|
+
Completion output remains runtime-owned and is not automatically canonical. An adapter must append a final runtime-native message through its ordinary canonical history API if the host chooses to persist it.
|
|
43
|
+
|
|
44
|
+
## Tool atomicity
|
|
45
|
+
|
|
46
|
+
`buildCanonicalToolAtomicGroups()` connects every canonical `toolCall` block to all matching `toolResult` blocks. Calls sharing one assistant message form one component, so parallel tool batches cannot be split. `validateRuntimeHistorySnapshot()` rejects missing, overlapping, unknown, or mismatched groups. An incomplete live call is represented by a group with `complete: false`; it cannot be treated as a complete selectable exchange.
|
|
47
|
+
|
|
48
|
+
## Capability negotiation
|
|
49
|
+
|
|
50
|
+
The v1 registry is fixed and additive contracts must use a later contract version:
|
|
51
|
+
|
|
52
|
+
- `compaction`;
|
|
53
|
+
- `provider-continuation`;
|
|
54
|
+
- `embeddings`;
|
|
55
|
+
- `local-kv-reuse`.
|
|
56
|
+
|
|
57
|
+
A supported capability requires a non-empty implementation version. Unsupported capabilities require a bounded reason. `negotiateRuntimeCapabilities()` evaluates each request independently:
|
|
58
|
+
|
|
59
|
+
- a supported requested capability is enabled;
|
|
60
|
+
- an unsupported optional capability is disabled with an informational diagnostic;
|
|
61
|
+
- an unsupported required capability is disabled with a warning;
|
|
62
|
+
- a duplicate, missing, or unversioned declaration is malformed and disabled;
|
|
63
|
+
- no failure in one capability disables canonical history, privacy, completion fallback, or another valid capability.
|
|
64
|
+
|
|
65
|
+
M19 only negotiates `local-kv-reuse`; M20 defines its eligibility and handle lifecycle. KV handles are never part of canonical history or these diagnostics.
|
|
66
|
+
|
|
67
|
+
Pi advertises versioned compaction, OpenAI Responses continuation, and embedding-port support. It explicitly reports local KV reuse as unavailable. `/context adapter` shows the complete negotiation; `/context status` shows aggregate enabled/disabled counts.
|
|
68
|
+
|
|
69
|
+
## Reusable conformance kit
|
|
70
|
+
|
|
71
|
+
The conformance runner has no Vitest/Jest dependency. Adapter packages provide a factory that maps a versioned fixture and injected completion transport into their native runtime:
|
|
72
|
+
|
|
73
|
+
```ts
|
|
74
|
+
import {
|
|
75
|
+
assertRuntimeAdapterConformance,
|
|
76
|
+
runRuntimeAdapterConformance,
|
|
77
|
+
} from "ds4-context-core/adapter/conformance";
|
|
78
|
+
|
|
79
|
+
const report = await runRuntimeAdapterConformance({
|
|
80
|
+
name: "my-runtime",
|
|
81
|
+
async create(fixture, transport) {
|
|
82
|
+
// Create native canonical history from fixture.messages.
|
|
83
|
+
// Inject transport at the final provider boundary.
|
|
84
|
+
return { adapter, expectedProjectRoot, cleanup };
|
|
85
|
+
},
|
|
86
|
+
});
|
|
87
|
+
assertRuntimeAdapterConformance(report);
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
The seven checks cover:
|
|
91
|
+
|
|
92
|
+
1. adapter/contract identity, model limits, and trusted root;
|
|
93
|
+
2. complete capability declarations and isolated unsupported diagnostics;
|
|
94
|
+
3. ordered canonical history and tool atomicity;
|
|
95
|
+
4. deterministic rebuild from canonical state;
|
|
96
|
+
5. remote privacy filtering plus synthetic sanitizer failure before observed transport;
|
|
97
|
+
6. safe transport failure with native fallback still available;
|
|
98
|
+
7. idempotent shutdown and closed-state behavior.
|
|
99
|
+
|
|
100
|
+
Reports contain case IDs, booleans, and fixed failure codes only. The private marker and credential probes never appear in a report. Package smoke tests install core, Pi, and reference tarballs in a clean consumer and rerun reference conformance from compiled exports.
|
|
101
|
+
|
|
102
|
+
## Reference-adapter compatibility spike
|
|
103
|
+
|
|
104
|
+
M19 compared three reference targets:
|
|
105
|
+
|
|
106
|
+
| Candidate | Strength | M19 risk |
|
|
107
|
+
|---|---|---|
|
|
108
|
+
| another full agent SDK | realistic lifecycle | adds fast-moving SDK/version coupling and obscures which behavior belongs to DS4 versus the SDK |
|
|
109
|
+
| provider-client-only adapter | realistic completion | has no canonical branch, tool-group, or lifecycle contract to validate |
|
|
110
|
+
| callback runtime with append-only JSONL | exercises every adapter responsibility with no vendor SDK | intentionally minimal; not a production orchestration framework |
|
|
111
|
+
|
|
112
|
+
The callback JSONL target was selected because it covers the full contract while keeping the example inspectable and dependency-neutral. `ds4-context-reference-adapter` is therefore a non-Pi executable boundary example, not a claim of production support for a specific third-party agent framework.
|
|
113
|
+
|
|
114
|
+
Its `ds4-runtime-session-v1` file is canonical and append-only. The header binds runtime ID, session ID, and canonical project root. Message records contain DS4 canonical messages. `createReferenceHistory()` refuses overwrite, `appendReferenceHistoryMessage()` checks provenance before append, and `rebuildDerivedState()` discards only the in-memory snapshot. File size and message count are bounded. Files are mode `0600` where supported.
|
|
115
|
+
|
|
116
|
+
The reference adapter provides a callback completion transport, enabled fail-closed privacy by default, optional `EmbeddingPort`, and explicit unsupported declarations for native compaction, provider continuation, and local KV state.
|
|
117
|
+
|
|
118
|
+
## Packaging rules
|
|
119
|
+
|
|
120
|
+
All release packages use the same version.
|
|
121
|
+
|
|
122
|
+
- `ds4-context-core` has no runtime SDK dependency.
|
|
123
|
+
- `ds4-context-engine` contains the Pi SDK boundary and depends exactly on matching core.
|
|
124
|
+
- `ds4-context-reference-adapter` contains no Pi SDK and depends exactly on matching core.
|
|
125
|
+
- Adapter source is not bundled into the core tarball; core source is not bundled into adapter tarballs.
|
|
126
|
+
- Core and reference TypeScript compile to ESM JavaScript and declarations before packing.
|
|
127
|
+
- Publish core first, then reference, then Pi.
|
|
128
|
+
|
|
129
|
+
Use:
|
|
130
|
+
|
|
131
|
+
```bash
|
|
132
|
+
npm run check
|
|
133
|
+
npm run pack:check
|
|
134
|
+
npm pack --dry-run --workspace ds4-context-core
|
|
135
|
+
npm pack --dry-run --workspace ds4-context-reference-adapter
|
|
136
|
+
npm pack --dry-run
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
## Limitations and rollback
|
|
140
|
+
|
|
141
|
+
The reference adapter is intentionally synchronous-history/callback-completion infrastructure: it does not implement streaming, native compaction, branch editing, provider continuation, or KV reuse. Unsupported features remain disabled and visible rather than emulated.
|
|
142
|
+
|
|
143
|
+
Removing the reference package does not affect Pi or core. A runtime can roll back its adapter by stopping it and returning to native history/context behavior; no canonical migration or SQLite downgrade is required. Deleting adapter caches is safe. Never delete the runtime-owned JSONL file as part of DS4 rollback.
|