ADR-013: fold the forked substrate into alkstore-sqlite — no fourth crate

Operator review of ADR-012's fork design re-litigated §1's crate
identity. alkstore-substrate misdescribed what the code is (unpublished,
path-dep-only, one consumer, SQLite-only — not a family-wide substrate);
the mechanical-diff hope was gone at fork time regardless (port deltas,
renames, re-derived half); and the alksocks F-1 lesson applies — a
vendored region under a second, weaker instruction set is a defect seam.
The fork folds into alkstore-sqlite as a bounded module subtree
(src/substrate/); ADR-012 §3–§6 retained verbatim, §2 retained with its
enforcement re-sited from the crate graph to diff fence + review +
contract-suite equivalence pins. OQ-11 item (1) dissolved.
This commit is contained in:
glm-5.3-flash committed 2026-10-05 11:56:01 +00:00
1 parent 2949612e2c
commit 8e68b44194
10 files changed
+309 -55

No files matched your search

+4 -3
View File
@@ -47,6 +47,7 @@ pending architecture review and OQ resolution.
| [010](decisions/010-queue-semantics-depth.md) | Queue semantics depth — visibility/renewal, backoff curve, dead-letter, no-stranded-rows sweep, schema layout | Accepted |
| [011](decisions/011-sqlite-substrate-fork.md) | SQLite substrate — fork honker-core into owned code | Accepted |
| [012](decisions/012-forked-substrate-design.md) | Forked substrate design — contract-blind boundary, fidelity posture, port deltas | Accepted |
| [013](decisions/013-fold-substrate-into-sqlite.md) | Fold the forked substrate into `alkstore-sqlite` — no fourth crate | Accepted |
## Open Questions
@@ -61,9 +62,9 @@ in suggested resolution order (OQ-04, OQ-09, OQ-05, OQ-06 resolved):
honker-core's lineage, queue ops re-derived on contract v1.
- **OQ-08** (medium): capability-surface shape.
- **OQ-10** (medium): contract versioning across engine crates.
- **OQ-11** (medium): forked-substrate follow-through (scaffold-time
decisions — [ADR-012](decisions/012-forked-substrate-design.md)'s
residue).
- **OQ-11** (medium): forked-substrate follow-through (provenance
register format, cherry-pick procedure; item (1) dissolved by
[ADR-013](decisions/013-fold-substrate-into-sqlite.md)).
Resolved (kept with resolutions): OQ-01 (feature scope), OQ-02
(crate split), OQ-03 (drivers), OQ-07 (extension surface cut),
@@ -38,9 +38,11 @@ The project ships as a **family of crates**:
documentation. No driver dependencies. Compile-lean by construction:
the base crate has no engine machinery to keep out.
2. **`alkstore-sqlite`** — the SQLite engine implementing the core
surface. Single driver: rusqlite + the forked `alkstore-substrate`
lineage ([ADR-003]; ownership per
[ADR-011](011-sqlite-substrate-fork.md)).
surface. Single driver: rusqlite + the forked honker-core
lineage, carried in-tree as the engine crate's substrate module
subtree ([ADR-003]; ownership per
[ADR-011](011-sqlite-substrate-fork.md); folded into the engine
crate per [ADR-013](013-fold-substrate-into-sqlite.md)).
3. **`alkstore-postgres`** — the Postgres engine implementing the core
surface. Single driver: tokio-postgres + deadpool-postgres
([ADR-004]).
@@ -41,7 +41,9 @@ The SQLite engine uses **posture 1**: published `honker-core = 0.5`
as a library dependency over the crate's own rusqlite connections
(`bundled-sqlite` for hermetic builds). *(Ownership superseded
2026-10-05 by [ADR-011](011-sqlite-substrate-fork.md): the substrate
is the forked `alkstore-substrate` lineage crate, not the published
is the forked honker-core lineage, carried in-tree as the engine
crate's substrate module subtree per
[ADR-013](013-fold-substrate-into-sqlite.md), not the published
dependency — the driver, seam, and watcher architecture below are
unchanged.)*
@@ -28,7 +28,7 @@ when a named trigger fires. Per subsystem:
| Subsystem | Posture | Notes |
|---|---|---|
| honker-core (SQLite engine machinery) | published library, `honker-core = 0.5` — **trigger fired 2026-10-05**: forked per [ADR-011] | Fork trigger: the Phase 1 quality read of the watcher/transactional core finds a defect, OR a needed change upstream won't take. OQ-06 tracked the read; the read fired the trigger (published 0.5.0 carries the unreleased-fix-train defect class + ADR-010's queue depth requires engine-owned queue SQL in any posture). |
| rusqlite | published, ~~riding honker-core's pin~~ **pin ours after the fork** | Post-fork ([ADR-011]), the rusqlite generation is moved deliberately in our own substrate crate, not by upstream releases ([ADR-003]'s annotated negative consequence; [ADR-012] ports the substrate onto the family standard). |
| rusqlite | published, ~~riding honker-core's pin~~ **pin ours after the fork** | Post-fork ([ADR-011]), the rusqlite generation is moved deliberately in our own engine crate (the in-tree substrate module — [ADR-013]), not by upstream releases ([ADR-003]'s annotated negative consequence; [ADR-012] ports the substrate onto the family standard). |
| tokio-postgres + deadpool-postgres | published library, as-is | Clean, zero conflicts, actively maintained (POC #2). |
| postgres-notify | **not adopted** (derive-not-adopt) | Lazy reconnect, connect_script skipped at initial connect, unquoted-identifier LISTENs, single maintainer. Hand-rolled forwarder instead ([ADR-004]). Fallback if upstream improves materially. |
| pg-boss queue machinery (pgboss-rs / node pg-boss) | **re-derived** on our driver; schema family as *design reference* only | pgboss-rs brings sqlx (second driver per binary) and has no LISTEN/NOTIFY (verified); the push half is ours either way, so queue-machinery reuse value is the honest comparison point and it loses on that arithmetic. Semantics depth: [queues.md], OQ-05. |
@@ -44,8 +44,9 @@ to this posture.
- Zero vendored code in the tree by default; upgrades are
`cargo update` work, not patch-management work. *(Exception now
live: the [ADR-011] fork is a vendored family crate — the named
trigger, not a posture change.)*
live: the [ADR-011] fork vendors honker-core's machinery into the
tree — carried in-tree inside the engine crate per [ADR-013], not
as a family crate — the named trigger, not a posture change.)*
- The fork triggers are concrete and named *before* the quality read,
so the read produces a decision, not a debate.
- Per-subsystem votes are recorded with evidence, so no future
@@ -87,9 +87,12 @@ Per-scope (the full register with keeps/re-derivations/drops is
lifecycle/failure, savepoint, multiprocess pressure) + the contract-
property tests (no-stranded-rows, dead-visible `get_job`, stamps).
Packaging follows ADR-001's split: the forked substrate is the
SQLite engine crate's dependency — vendored as a workspace-family
crate (provenance + license recorded), not re-published.
Packaging follows ADR-001's split: the forked substrate is the SQLite
engine crate's dependency — vendored as a workspace-family crate
(provenance + license recorded), not re-published. *(Packaging amended
2026-10-05 by [ADR-013](013-fold-substrate-into-sqlite.md): the fork
folds into `alkstore-sqlite` as a bounded module subtree — no fourth
crate; ADR-001's three-crate shape stands.)*
## Consequences
@@ -111,9 +114,12 @@ crate (provenance + license recorded), not re-published.
incremental, but real — the #80/#133 train proves the stream is
alive) must be deliberately cherry-picked rather than inherited by
`cargo update`.
- A vendored workspace-family crate breaks "zero vendored code in the
- Vendored forked code in the tree breaks "zero vendored code in the
tree by default" (ADR-005's positive consequence) — this is the
exception the posture always named, not a renegotiation.
exception the posture always named, not a renegotiation. *(Packaging
since amended by [ADR-013](013-fold-substrate-into-sqlite.md): the
vendored code is carried in-tree inside `alkstore-sqlite`, not as a
workspace-family crate.)*
## References
@@ -3,7 +3,11 @@
## Status
Accepted (2026-10-05, Phase 1 — the design decisions ADR-011's fork
requires; the follow-through of OQ-06's resolution)
requires; the follow-through of OQ-06's resolution). **Amended by
[ADR-013](013-fold-substrate-into-sqlite.md) (2026-10-05)**: §1's
`alkstore-substrate` crate identity is superseded — the fork folds
into `alkstore-sqlite` as a bounded module subtree; §2–§6 are retained
verbatim under that packaging.
## Context
@@ -43,6 +47,12 @@ architecture, and they are decidable now, from decided material:
### 1. Crate identity and location
*(Superseded by [ADR-013](013-fold-substrate-into-sqlite.md): there is
no `alkstore-substrate` crate. The forked substrate is a bounded
module subtree of `alkstore-sqlite` — `alkstore-sqlite/src/substrate/`
— with the provenance register and bundled dual-license notice carried
in-tree. Retained below as the original record.)*
The forked substrate is **`alkstore-substrate`** — a vendored
workspace-family crate in this repository, a path dependency of
`alkstore-sqlite`, not published ([ADR-011]'s packaging, now named).
@@ -84,16 +94,19 @@ Why the boundary sits there, not inside the substrate:
surface ([ADR-011]), and they are new code with contract-derived
names either way.
Dependency graph (downward only):
Dependency graph (downward only; no substrate crate — the forked
machinery is in-tree inside `alkstore-sqlite`, per
[ADR-013](013-fold-substrate-into-sqlite.md)):
```text
consumers
│
alkstore (core: traits, types, errors — no drivers)
────────▲────────
alkstore-sqlite alkstore-postgres
│ (no substrate)
alkstore-substrate (vendored lineage; path dep; unpublished)
alkstore-sqlite alkstore-postgres
(src/substrate/ — (no substrate)
the forked lineage
machinery, in-tree)
```
### 3. API fidelity posture: keep the kept half's names
@@ -102,8 +115,10 @@ Where the fork scope *keeps* upstream machinery ([ADR-011]'s inherited
list), the fork keeps upstream's module structure and internal function
names — including names carrying lineage tokens (`Writer`, `Readers`,
`run_poll_loop`, the `in_savepoint` machinery, the lock/stream/notify
functions). Renames are confined to: crate identity, the table family
(`__alkstore_*`, [ADR-011]), and the hygiene deltas [ADR-011] names.
functions). Renames are confined to: crate identity *(a slot the
fold — [ADR-013](013-fold-substrate-into-sqlite.md) — dissolves;
there is no crate to rename)*, the table family
(`__alkstore_*`, [ADR-011]), and the hygiene deltas [ADR-011] names.
The **re-derived** half ([ADR-011]'s list) is new code; its functions
take contract-derived names naturally.
@@ -201,7 +216,11 @@ owned, tested, contract-ahead fork on maintenance, not on novelty.
## References
- [ADR-011](011-sqlite-substrate-fork.md) — the fork decision this ADR
designs; its scope register and packaging are inputs.
designs; its scope register and packaging are inputs (packaging since
amended by [ADR-013](013-fold-substrate-into-sqlite.md)).
- [ADR-013](013-fold-substrate-into-sqlite.md) — the packaging
amendment (substrate folded into `alkstore-sqlite`; this ADR's
§3–§6 retained verbatim, §2 with its enforcement re-sited).
- [ADR-005](005-dependency-ownership.md) — the posture calculus the
fork's maintenance assumptions inherit.
- [ADR-001](001-crate-split.md) — the dependency direction §2
@@ -0,0 +1,207 @@
# ADR-013: Fold the forked substrate into `alkstore-sqlite`
## Status
Accepted (2026-10-05, Phase 1 — operator review of the fork design;
amends [ADR-012](012-forked-substrate-design.md) §1, superseding the
`alkstore-substrate` crate identity; §3–§6 of ADR-012 are retained
verbatim, §2 is retained with its enforcement re-sited per §2 below)
## Context
ADR-011 fired the fork trigger; ADR-012 designed the fork and named the
crate `alkstore-substrate` — a fourth, vendored, unpublished,
path-dependency-only workspace crate below `alkstore-sqlite`. The design
pillars (ADR-012 §2–§6) survived operator review intact. §1 did not:
the operator flagged the naming and packaging for re-litigation, on two
grounds — `alkstore-substrate` reads as a family-wide foundation crate
in the family listing, which misdescribes what the code is, and since
edits were coming regardless, the "keep the mechanical diff cheap"
consideration that favored a separate fence was never going to pay out
anyway.
Re-litigation from the decided material:
1. **The substrate was never a foundation.** It is unpublished, has a
path-dependency-only, exactly-one-consumer relationship
(`alkstore-sqlite`), is SQLite-only machinery, and its storage
surface was re-owned as `__alkstore_*` at fork time — it is not
shared, not reusable by the Postgres engine, and not a layer
anything else sits on. "Substrate" named the *ride relationship*
correctly in ADR-003's original posture (`honker-rs as the SQLite
substrate`); promoted to a crate name in the family listing
alongside `alkstore`, `alkstore-sqlite`, and `alkstore-postgres`,
it now falsely signals a general foundation layer that a
Postgres-consuming reader might think they need.
2. **The mechanical-diff hope was already gone on day one.** The fork
is born with port deltas (ADR-012 §4), table renames (ADR-011),
dropped regions, family-standard porting, and — in any packaging —
the re-derived half (new code, contract-derived names). No future
point exists where a line-based diff against `/workspace/honker`
stays mechanical. What survives is *cherry-pick* economics, and
that is carried by ADR-012 §3's fidelity posture (keep the kept
half's names), which is packaging-independent.
3. **The alksocks precedent is directly on point — twice.** (a) The
alksocks review's F-1 defect escaped through exactly the seam this
packaging creates: a vendored region governed by a *second, weaker*
instruction set ("verbatim where kept" + an adjustments list)
sitting next to the project's own conventions. The standalone
vendored crate carries the same structural risk — "vendored lineage"
is baked into its identity, and ADR-012 already had to negotiate
exceptions to the family standard inside it. One codebase, one
instruction set closes the seam. (b) alksocks' own resolution
(ADR-013 there) retired the vendor framing and folded the forked
core into the owning crate as a named module tree, keeping the
reference checkout for behavioral differential testing — and that
shape shipped on crates.io without provenance problems.
4. **The separate crate's advantages are weaker than they look, and
the fold has a concrete bonus.**
- *Compiler-enforced contract-blindness* (ADR-012 §2's strongest
structural argument) becomes review-enforced under a fold: nothing
stops substrate code inside `alkstore-sqlite` from importing
alkstore core types that sit in a sibling dependency. This is the
fold's one genuine loss, stated plainly and accepted — weighed
against the misleading crate name, the dead wiring question, and
the second-instruction-set seam, with the diff fence and the
contract suite as the working guards.
- *Dependency-graph hygiene*: ADR-012 §2's concern — "a vendored
lineage crate must not acquire a dependency on our contract crate;
the mirror inverts ADR-001" — becomes structurally impossible
under a fold. There is no crate to carry the edge, and nothing
depends on the folded code.
- *License/provenance hygiene* ships fine in-tree: bundled license
notice + module docs + the git-history fork line, the alksocks
shape, proven.
- *Bonus*: OQ-11 item (1) — the `bundled-sqlite` feature interplay
of a substrate crate's rusqlite dependency with the engine crate's
own — dissolves entirely. One crate, one rusqlite dependency.
- *Restored shape*: ADR-001's split is three crates; ADR-011's
"packaging follows ADR-001's split" line had been quietly
stretched to four. The fold restores the decided shape.
## Decision
### 1. The fork lives inside `alkstore-sqlite`
The forked honker-core machinery is **a bounded module subtree of
`alkstore-sqlite`** — `alkstore-sqlite/src/substrate/` — mirroring
upstream's module structure per ADR-012 §3's fidelity posture. There is
no fourth crate; ADR-001's three-crate shape (`alkstore`,
`alkstore-sqlite`, `alkstore-postgres`) stands unamended. The engine
crate's public API surface carries nothing of the substrate (ADR-012 §2
and ADR-008 §6 unchanged — the contract is the returned trait; no
substrate type or name reaches a consumer signature).
The word "substrate" survives where it reads correctly — as
engine-internal vocabulary for "the SQLite storage machinery this
engine rides" (its origin, ADR-003's sense) — and stops being a crate
name. Specs referencing "the substrate" after this ADR mean the module
subtree, not a dependency.
### 2. ADR-012 §2–§6 are retained (§3–§6 verbatim; §2 re-sited)
- **§2, contract-blind boundary**: retained in substance — the
substrate module takes and returns primitives; the engine layer
resolves contract semantics into primitive arguments exactly as
ADR-012 §2 specifies — but its *enforcement site* moves from the
crate graph to code discipline: the diff fence (lineage-relative
diffs stay confined to the subtree), review, and the contract
suite's equivalence pins, not Cargo.
- **§3, fidelity posture**: retained verbatim — module structure and
internal names of the kept half are upstream's; names are
engine-internal either way, and cherry-pick economics (the posture's
purpose) are packaging-independent.
- **§4, port deltas**: retained verbatim (W-1 backoff, W-2 fallible
spawn, panic-free watcher-fatal death, W-4 keep-RW, W-3 recorded).
- **§5, bootstrap and schema machinery**: retained verbatim (append-
column migrations; the `pragma_table_info` re-key of the duplicate-
column race swallow; stamp columns via the re-derivation; no online
rename migration; inert `_honker_*` orphans).
- **§6, upstream tracking**: retained verbatim — deliberate
cherry-picks recorded in the delta register, evaluated by
port-cost logic; re-adoption keeps quality-read §7's bar.
### 3. Provenance and license, in-tree
At fork-scaffold time `alkstore-sqlite` carries:
- A **provenance register** recording upstream identity —
`/workspace/honker` @ `f4e53c6`, MIT OR Apache-2.0 — and the delta
list. Timing and initial contents are ADR-012 §1's (retained);
location and format are this fold's to place — in-tree, beside the
substrate subtree — and the exact format/granularity is OQ-11 item
(2)'s.
- The **dual license notice, bundled** in the substrate subtree (the
alksocks `src/rfc1928/LICENSE` shape: upstream MIT + Apache text and
copyright, preservation obligation perpetual, plus a fork-point
statement and a modification note). Sublicensing is permitted by
both licenses; the engine crate's license statement covers the
whole crate.
- **Git history is the fork-point record** — the scaffold commits are
the provenance line, exactly as alksocks' extraction-commits window
is.
- `/workspace/honker` @ `f4e53c6` remains the **reference checkout**
for cherry-pick candidates and differential testing; no dependency,
no wiring.
### 4. OQ-11 reshaped
OQ-11's item (1) — the Cargo-workspace layout and the
`bundled-sqlite`/rusqlite interplay of a separate substrate crate — is
**dissolved** by this fold; the provenance register is carried
in-tree beside the substrate subtree (its location settles with the
fold; its format/granularity remains OQ-11 item (2)). Items (2)
(register format and delta-list granularity) and (3) (cherry-pick
procedure in practice) remain, now scoped to the in-tree register.
## Consequences
**Positive**
- The family listing is honest: three crates, and nothing in the crate
table suggests a foundation layer shared across engines.
- One codebase, one instruction set — the alksocks F-1 seam class
(conventions-vs-fidelity gaps in a vendored region) is closed
structurally rather than by vigilance.
- The `bundled-sqlite`/rusqlite wiring question dissolves; the engine
crate has exactly one rusqlite dependency.
- ADR-001's decided shape stands unamended; the fork-scaffold task
shrinks (no fourth crate to wire, version-coordinate, or gate).
- Cherry-pick economics are unaffected: ADR-012 §3's fidelity posture
is packaging-independent.
**Negative (accepted)**
- Contract-blindness is review-enforced, not compiler-enforced:
substrate-module code could import alkstore core types that the
sibling dependency makes available. The guards are the diff fence
(lineage-relative diffs stay confined to the subtree), review, and
the contract suite's equivalence pins. Assessed low-risk — the
module's API takes primitives by design, and the code has no reason
to reach upward.
- Internal-name ambiguity ("substrate" the module vs. the retired
crate name) — mitigated by this ADR being the naming record and by
the specs' references resolving to the module subtree.
## References
- [ADR-012](012-forked-substrate-design.md) — the fork design this ADR
amends (§1 superseded; §3–§6 retained verbatim, §2 re-sited; this
ADR does not reopen any retained question).
- [ADR-011](011-sqlite-substrate-fork.md) — the fork decision and its
scope register; packaging re-read under this ADR.
- [ADR-001](001-crate-split.md) — the three-crate shape restored.
- [ADR-003](003-sqlite-driver.md) — driver, seam, and watcher
architecture; the origin of "substrate" as relationship vocabulary.
- [ADR-008](008-contract-v1-pinning.md) §6 — the contract-is-the-
returned-trait rule the fold preserves.
- OQ-11 (`docs/architecture/open-questions.md`) — residue reshaped by
§4 here.
- alksocks `docs/architecture/decisions/011-inline-vendor.md` and
`013-targeted-fork.md` (@ `/workspace/@alkdev/alksocks`) — the
second-instruction-set finding (F-1) and the fold-into-owning-crate
precedent this decision follows.
- `docs/research/quality-read-honker-core.md` — the fork calculus and
scope register.
- [engine-sqlite.md](../engine-sqlite.md) — the engine spec this ADR's
packaging realizes.
+18 -12
View File
@@ -7,19 +7,22 @@ last_updated: 2026-10-05
The `alkstore-sqlite` engine implements
[core-contract.md](core-contract.md) on rusqlite over the
[forked honker-core substrate](decisions/011-sqlite-substrate-fork.md).
This spec records WHAT the engine is internally (its
connection architecture, seam, and wake plumbing) — not code-level
HOW. Decisions live in ADRs; per-contract obligations live in the core
spec and are not restated here.
[forked honker-core substrate](decisions/011-sqlite-substrate-fork.md) —
carried in-tree as the engine crate's substrate module subtree
([ADR-013](decisions/013-fold-substrate-into-sqlite.md)). This spec
records WHAT the engine is internally (its connection architecture,
seam, and wake plumbing) — not code-level HOW. Decisions live in ADRs;
per-contract obligations live in the core spec and are not restated here.
## Identity and posture
- Single driver: rusqlite, riding the
[forked honker-core substrate](decisions/011-sqlite-substrate-fork.md)
(`alkstore-substrate` — the vendored lineage crate,
[ADR-012](decisions/012-forked-substrate-design.md)) with
`bundled-sqlite` for hermetic builds. No `.so` runtime artifacts
— the forked lineage machinery carried in-tree as this crate's
`src/substrate/` module subtree
([ADR-012](decisions/012-forked-substrate-design.md) design,
[ADR-013](decisions/013-fold-substrate-into-sqlite.md) packaging) —
with `bundled-sqlite` for hermetic builds. No `.so` runtime artifacts
([ADR-003](decisions/003-sqlite-driver.md) for the driver decision;
ownership resolved by
[ADR-011](decisions/011-sqlite-substrate-fork.md) — OQ-06's read
@@ -78,8 +81,9 @@ spec and are not restated here.
- Wake coalescing: bursts inside one poll tick produce one wake;
correctness is preserved by the re-read contract
(POC-pinned: missed-wake stress with correct post-burst re-reads).
- **Deployment note**: the substrate's rusqlite generation
(^0.40.1) has a rustc floor ≥ 1.99; binaries linking this engine
- **Deployment note**: the lineage's rusqlite generation
(^0.40.1) — this engine crate's own dependency — has a rustc floor
≥ 1.99; binaries linking this engine
carry that requirement ([deployment.md](deployment.md) matrix).
- The optimization path, if seam throughput ever demands it: a
dedicated std-thread bridge (one thread owning the writer conn, ops
@@ -92,8 +96,9 @@ The [quality read (OQ-06)](../research/quality-read-honker-core.md) —
this engine's dependency gate — resolved 2026-10-05: ADR-005's fork
trigger **fired** ([ADR-011](decisions/011-sqlite-substrate-fork.md)),
and the fork's design is pinned by
[ADR-012](decisions/012-forked-substrate-design.md): the substrate is
`alkstore-substrate`, a vendored contract-blind lineage crate; the
[ADR-012](decisions/012-forked-substrate-design.md): the substrate is a
vendored contract-blind lineage module folded into this engine crate
([ADR-013](decisions/013-fold-substrate-into-sqlite.md)); the
watcher/connection architecture this spec describes is inherited
verbatim where kept ([ADR-003](decisions/003-sqlite-driver.md)
unchanged in architecture), with the port deltas ADR-012 §4 decides
@@ -119,6 +124,7 @@ family is `__alkstore_*` (ADR-010 §8's naming authorization).
| [010](decisions/010-queue-semantics-depth.md) | Queue depth | semantics pinned; §5/§3a realization resolved by ADR-011 (owned code) |
| [011](decisions/011-sqlite-substrate-fork.md) | Substrate fork | OQ-06's trigger fired; substrate owned, queue ops re-derived on contract v1 |
| [012](decisions/012-forked-substrate-design.md) | Fork design | contract-blind substrate, fidelity posture, port deltas, panic-free watcher death |
| [013](decisions/013-fold-substrate-into-sqlite.md) | Substrate packaging | folded into `alkstore-sqlite` (`src/substrate/`); no fourth crate |
## Open Questions
+27 -18
View File
@@ -18,11 +18,15 @@ fork trigger fired on the published-artifact facts); **the fork
design follow-through** (2026-10-05,
[ADR-012](decisions/012-forked-substrate-design.md) — substrate
boundaries, fidelity posture, port deltas; its substrate-side residue
is OQ-11). Next: OQ-08 (rides the now-pinned trait shape and the
is OQ-11); **the fork packaging folded** (2026-10-05,
[ADR-013](decisions/013-fold-substrate-into-sqlite.md) — no
`alkstore-substrate` crate; the forked machinery is a module subtree of
`alkstore-sqlite`). Next: OQ-08 (rides the now-pinned trait shape and the
ADR-011 substrate fork), OQ-10 (versioning discipline for contract
extensions; note ADR-011 changes its substrate-side facts for SQLite —
the forked crate is versioned in this repository's Cargo workspace, so
the engine/core contract pairing is what the discipline must track), and
the forked machinery lives in-tree inside the engine crate per
[ADR-013](decisions/013-fold-substrate-into-sqlite.md), so the
engine/core contract pairing is what the discipline must track), and
OQ-11 (fork follow-through items — substrate-side, non-consumer-facing).
Resolved questions stay listed with their resolution; they are not
@@ -262,31 +266,36 @@ narrowed to the pinning work its own record already scoped.)*
### OQ-11: Forked-substrate follow-through — scaffold, provenance register, and cherry-pick discipline
- **Origin**: [ADR-012](decisions/012-forked-substrate-design.md)
(the fork design; substrate-side residue), [ADR-011](decisions/011-sqlite-substrate-fork.md)
- **Status**: open
(the fork design; substrate-side residue), [ADR-011](decisions/011-sqlite-substrate-fork.md),
[ADR-013](decisions/013-fold-substrate-into-sqlite.md)
- **Status**: open (reshaped 2026-10-05 by
[ADR-013](decisions/013-fold-substrate-into-sqlite.md) — item (1)
dissolved)
- **Priority**: medium (nothing consumer-facing rides on it; it
resolves within the fork-scaffold task, which it does not gate)
- **Resolution**: open. ADR-012 fixed the *design* (contract-blind
boundary, fidelity posture, port deltas, bootstrap machinery,
upstream-tracking stance) and also pinned the provenance register's
location, timing, and initial contents (§1). The residue is: (1) the
exact Cargo-workspace layout and build wiring of
`alkstore-substrate` in this repository (crate location, feature
gating of the `bundled-sqlite` interplay with the engine crate's own
rusqlite dependency); (2) the provenance register's *format and
delta-list granularity* (per-commit entries vs per-delta-class;
whether cherry-pick records append at adoption time — location,
timing, and initial contents are ADR-012 §1's, not re-opened here);
location, timing, and initial contents (§1, as carried in-tree by
ADR-013). The residue is: (1) **dissolved** by the fold
([ADR-013](decisions/013-fold-substrate-into-sqlite.md)) — there is
no separate substrate crate to wire; the engine crate carries one
rusqlite dependency and no `bundled-sqlite` interplay question;
(2) the provenance register's *format and delta-list granularity*
(per-commit entries vs per-delta-class;
whether cherry-pick records append at adoption time — the register
lives in-tree beside the substrate subtree per
[ADR-013](decisions/013-fold-substrate-into-sqlite.md) §3; its
timing and initial contents are ADR-012 §1's, not re-opened here);
(3) the cherry-pick *procedure* in practice — how a candidate
upstream fix is evaluated, applied, and recorded so ADR-012 §6's
deliberate-work posture stays auditable. These resolve *within* the
fork-scaffold task (its opening section), not before it and not as a
gate on writing it; the scaffold's build wiring depends on (1)'s
outcome.
gate on writing it.
- **Cross-references**: OQ-08 (the contract surface the engine maps
the substrate under), OQ-10 (the substrate is a crate in this
repository's Cargo workspace — its versioning interacts with the
discipline), ADR-011, ADR-012.
the substrate under), OQ-10 (the engine's versioning discipline now
carries the fold's provenance duties in-tree), ADR-011, ADR-012,
ADR-013.
## Deferred / Blocked
+3 -2
View File
@@ -29,7 +29,7 @@ Per [ADR-001](decisions/001-crate-split.md):
| Crate | Contents | Driver dependencies |
|---|---|---|
| `alkstore` (core) | trait surface, types, error model | none (capability flags, if ever, are OQ-08's to add) |
| `alkstore-sqlite` | SQLite engine ([ADR-003](decisions/003-sqlite-driver.md)) | rusqlite, `alkstore-substrate` (the forked honker-core lineage — [ADR-011](decisions/011-sqlite-substrate-fork.md), designed in [ADR-012](decisions/012-forked-substrate-design.md)) |
| `alkstore-sqlite` | SQLite engine ([ADR-003](decisions/003-sqlite-driver.md)) | rusqlite; the forked honker-core lineage rides in-tree as the engine crate's substrate module subtree ([ADR-011](decisions/011-sqlite-substrate-fork.md), designed in [ADR-012](decisions/012-forked-substrate-design.md), folded per [ADR-013](decisions/013-fold-substrate-into-sqlite.md)) |
| `alkstore-postgres` | Postgres engine ([ADR-004](decisions/004-postgres-driver.md)) | tokio-postgres, deadpool-postgres |
| (mem engine, optional) | test convenience, decided at implementation ([ADR-001](decisions/001-crate-split.md)) | none |
@@ -53,7 +53,7 @@ Per [ADR-002](decisions/002-feature-scope.md):
| Doc | Purpose |
|---|---|
| [core-contract.md](core-contract.md) | The unified trait surface: mechanisms, delivery guarantees, tx seam, naming |
| [engine-sqlite.md](engine-sqlite.md) | SQLite engine: mapping the contract onto the forked substrate (`alkstore-substrate`)/rusqlite |
| [engine-sqlite.md](engine-sqlite.md) | SQLite engine: mapping the contract onto the forked substrate module/rusqlite |
| [engine-postgres.md](engine-postgres.md) | Postgres engine: mapping the contract onto tokio-postgres/LISTEN |
| [queues.md](queues.md) | Queue/scheduler/outbox semantics depth (ADR-009/ADR-010 resolved) |
| [deployment.md](deployment.md) | Host capabilities, connection budgets, deployment matrix (OQ-08) |
@@ -76,6 +76,7 @@ Per [ADR-002](decisions/002-feature-scope.md):
| [010](decisions/010-queue-semantics-depth.md) | Queue semantics depth (visibility, backoff, dead-letter, sweep, layout) | Accepted |
| [011](decisions/011-sqlite-substrate-fork.md) | SQLite substrate — fork honker-core into owned code | Accepted |
| [012](decisions/012-forked-substrate-design.md) | Forked substrate design (contract-blind boundary, fidelity, port deltas) | Accepted |
| [013](decisions/013-fold-substrate-into-sqlite.md) | Fold the forked substrate into `alkstore-sqlite` (no fourth crate) | Accepted |
## Non-goals