Files
alkblobs/docs/architecture/open-questions.md
T
glm-5.3-flash b18521a0e6 docs(architecture): dissolve OQ-09's self-referential deferral
- OQ-09 resolved closed-by-default (deny-unlisted), decided on risk
  asymmetry in hand, not on a first deployment the crate itself must
  create; named reopen condition instead of a parked wait
- delete oq-09-ops-visibility-tracker.md (watch-task for an event the
  crate itself gates — never collapses)
- fix doc-lifecycle circularity: externally-owned OQs no longer block
  a spec's `reviewed` promotion
- gc-and-namespaces: "until a consumer names a requirement" reframed
  as re-entry via a new ADR, not a parked question
- README: state the corollary explicitly — facts this crate must
  create (its own first deployment/consumer) are never deciding inputs

Verified: full-text sweep for stale OQ-09 deferral/tracker references
comes up clean across docs/ and tasks/.
2026-10-02 06:14:09 +00:00

197 lines
8.8 KiB
Markdown

---
status: draft
last_updated: 2026-10-02
---
# Open Questions
Centralized tracker. Theme sections hold OQs; cross-theme status lives
in the Deferred/Blocked index below.
**Deferral policy (the Schrödinger's-code rule).** A *decision this
crate needs before shipping* may not be deferred on a dependency that
is itself waiting for this crate to exist. alkgit is paused mid-Phase-1
*to build* this core; alkfs is pending *that shared base*. "Deciding
input: what alkgit wires first" never collapses into an input, so it is
not one. Two kinds of parked question remain legitimate:
- **deferred(scope)** — the deciding fact exists independently of this
crate (e.g., alkfs Phase 0 outcomes); the crate proceeds on its own
ADRs meanwhile.
- **externally-owned questions** — questions about *how a consumer maps
onto this crate*, which are not decisions this crate needs before
shipping and are not this document's to decide; they are carried here
for visibility, owned by the consumer's own process, and collapse
when that consumer acts (including on an API of this crate that will
exist by then — that is acceptable *only* because the question gates
no decision here; it would be Schrödinger's code if it gated one).
Invalid for either kind: a blocker that is a decision this crate must
make before shipping. Phase 0's residual list was swept under this
rule: every residual either resolved into an ADR (the evidence was
already in hand) or re-owned as below.
**Index of active OQs:** OQ-07, OQ-08 (externally-owned, carried for
visibility). OQ-09 is resolved (recorded below). Promoted Phase 0
questions OQ-BL-01..06 are recorded here with their resolutions for
traceability.
---
## Theme: consumer integration
### OQ-07: How alkgit's object-storage seam consumes alkblobs
- **Origin**: [overview.md](overview.md), [gc-and-namespaces.md](gc-and-namespaces.md)
- **Status**: externally-owned (alkgit) — carried here for visibility;
not a decision this crate must make before shipping
- **Priority**: high (it is why this crate exists) — but not a blocker:
alkblobs builds by its own ADRs; this question maps the *consumer on*.
- **Owner**: alkgit (external)
- **Question**: how do alkgit's reviewed `GitRefs`/`GitPackGen`/`GitPackIngest`
traits (its backend.md, ADR-018) sit over alkblobs — gix-odb-over-pool,
alkblobs-behind-those-traits, or a mixed composition (e.g. refs in the
pool, pack generation still gix)? Which tier serves the loose tier;
does packfile serving (ADR-005) get wanted at all?
- **Resolution**: owned by alkgit's architecture process; it is
answerable on paper against this document tree (backend.md + these
ADRs) whenever alkgit's process acts, and gates nothing here. This
crate's obligations toward it are already fixed: git-oid addressing
(ADR-002), liveness seam (ADR-005), serving surface (ADR-006/store-api).
- **Cross-references**: OQ-08, ADR-002, ADR-005, ADR-006
### OQ-08: alkfs requirement intake
- **Origin**: [overview.md](overview.md), [backends-and-dispatch.md](backends-and-dispatch.md)
- **Status**: externally-owned (alkfs) — carried here for visibility;
alkfs Phase 0 has not run
- **Priority**: medium (alkfs Phase 0 pending; nothing here blocks on it)
- **Owner**: alkfs (external)
- **Question**: what does alkfs's Phase 0 name as requirements on the
shared base — durability tiers, sync/replication seams the store does
not expose, manifest-layer shapes beyond ADR-004's boundary (e.g. the
appfile write-session shape as a consumer concern)?
- **Resolution**: owned by alkfs's Phase 0 (independently obtainable —
it needs no alkblobs artifact). The store's posture toward an unknown
consumer is deliberately permissive: open trait + addresses +
liveness seams (ADR-003/004/005) without baking an alkfs shape in.
- **Cross-references**: OQ-07, ADR-004
---
## Theme: ops surface
### OQ-09: Default visibility of namespaces in network ops
- **Origin**: [ops-surface.md](ops-surface.md)
- **Status**: resolved
- **Resolution**: **closed-by-default** (deny-unlisted namespaces:
no ACL entry ⇒ no read, no write). The deciding fact for this is not
a future deployment (one that can only exist once the ops module
ships is not a deciding input — Schrödinger's-code rule); it is the
risk asymmetry on evidence in hand: an open-by-default store
accidentally exposes content and the exposure is discovered only
after the fact, while a closed-by-default store's failure mode — a
legit access attempt denied until a grant exists — is loud, cheap,
and recoverable at grant time. A conservative default is chosen by
reasoning from the failure modes, not measured against a deployment.
This is a made decision with a deferred cost (an embedder wanting
public read pays one explicit grant), not an unmade decision.
- **Reopen condition** (not a parked question): a concrete use case
names why a namespace needs open read *as a default* — that is a
new requirement naming a new decision (the same shape ADR-006 gives
the chunk-tree question: deferred cost, re-entry at a new ADR if
ever named). "Some future embedder might exist" does not open it.
- **Cross-references**: ADR-001, [ops-surface.md](ops-surface.md)
---
## Theme: promoted Phase 0 register (resolutions recorded)
### OQ-BL-01: Crate scope — store-only, or store + ops surface?
- **Origin**: `docs/research/phase-0.md`
- **Status**: resolved
- **Resolution**: store-only core; ops surface exists as a
feature-gated alkcall-backed module (placement *decided*, not hedged —
Schrödinger's-code rule applied: no waiting on paused consumers).
Full rationale: [ADR-001](decisions/001-substrate-posture-and-ops-placement.md)
(family-pattern conformance record; placement; no-store-layer-wire
invariant).
- **Cross-references**: ADR-001; OQ-09 (its one former residual policy
line, now resolved closed-by-default)
### OQ-BL-02: Multi-backend dispatch
- **Origin**: `docs/research/phase-0.md`
- **Status**: resolved
- **Resolution**: lean `Backend` contract + two shipped backends +
pure-function size routing (pre-threshold buffering for unknown-length
puts); migration eliminated by construction; per-namespace backend
config rejected. Full rationale:
[ADR-003](decisions/003-backend-contract-and-dispatch.md).
- **Cross-references**: ADR-003, ADR-004
### OQ-BL-03: Hash abstraction
- **Origin**: `docs/research/phase-0.md`
- **Status**: resolved
- **Resolution**: canonical git-blob-sha-256; git-blob-sha-1 tolerated;
BLAKE3 excluded from the crate. Key bytes: algorithm-in-key,
fixed-length enum-tagged, tag byte dropped. The declared wire-format
ADR. Full rationale:
[ADR-002](decisions/002-canonical-hash-and-key-encoding.md).
- **Cross-references**: ADR-002, ADR-006
### OQ-BL-04: Verification and chunking
- **Origin**: `docs/research/phase-0.md`
- **Status**: resolved
- **Resolution**: whole-blob verification; range reads carry
out-of-band slice digests; chunk-tree/CDC encodings excluded by
scoping (not deferred — the transfer-encoding consumer cannot be
waited on; re-entry is a new decision at a new layer if ever named).
Full rationale:
[ADR-006](decisions/006-verification-posture-and-transfer-encoding.md).
- **Cross-references**: ADR-006, ADR-001
### OQ-BL-05: Pooling and GC
- **Origin**: `docs/research/phase-0.md`
- **Status**: resolved
- **Resolution**: one pooled CAS; flat bytes + logical namespaces;
store persists no root table; mark-and-sweep with three liveness
sources (registered sources / RAII + batch pins / protect callback
with abort); delete windows close the sweep-vs-put race; explicit
sweep, embedder-owned cadence; packfile serving rides large-blob
range reads if ever wanted. Full rationale:
[ADR-005](decisions/005-pooled-cas-and-gc-mechanism.md).
- **Cross-references**: ADR-005, ADR-003
### OQ-BL-06: POC register
- **Origin**: `docs/research/phase-0.md`
- **Status**: resolved (complete: #1, #3 passed; #2 absorbed; #4
covered in miniature, concurrency half specified as architecture in
ADR-005)
- **Resolution**: register complete; Phase 0 ended; evidence trail in
`docs/research/`.
- **Cross-references**: all ADRs above
---
## Parked index (deciding fact / owner — externally-owned rows are not blockers)
| OQ | Status | Deciding fact / owner |
|---|---|---|
| OQ-07 | externally-owned | alkgit's architecture process (answerable on paper anytime; gates nothing here) |
| OQ-08 | externally-owned | alkfs Phase 0 intake |
OQ-09 was `deferred(scope)` on the first embedded ops deployment — a
deciding fact that could only exist once the ops module ships, i.e. a
wait that never collapses. It resolved to closed-by-default (see its
entry above); its tracker task is deleted.
OQ-07/OQ-08 are owned by other repos' processes and are not alkblobs
tracker tasks (their outcome arrives *through* their owners, not
through any artifact this repo creates).