Factory docs, home
Page navigation

Reference document, shown as written except that local paths appear as placeholders. Where it describes the Factory as intended, read it as design, not current state: only local infrastructure is accepted, no release, customer value or scheduled automation is established, and all 27 customer-value epics remain open. Current state: Factory model.

28 September 2026. Opus 5.5 implements; Astra xhigh independently reviews each increment. Current construction uses Opus high through Claude Code. This is local development, with no remote, CI or production claim.

ModuleCurrent dispositionEvidence
Command journalAccepted local reads and writesAtomic decisions/receipts/events/outbox; real process races and commit-edge crashes; schema corruption, startup contention and monotonic lock retry. Native read-only inspection rejects empty/missing storage without initialising it.
Evidence / AssuranceAccepted for trusted local fixturesImmutable content identity, corruption, concurrent publication, crash durability, bounded special-file reads and strict provenance.
ExecutionAccepted for trusted local supervisionDurable cancellation shares the Run transaction; stale completion, retry and replay cannot bypass it. Permanent commit-edge crash and competing-controller tests.
Local fixture workerAccepted for fixed trusted fixturesReal bounded processes, environment isolation, cancellation, controller loss and safe quarantine.
Attempt fence / workspaceAccepted for trusted local POSIX fixturesGenuine ownership handles, actual shared readers, zero-wait recovery, identity damage, late-entry rejection and nonrecursive cleanup. A fence proves protected work cannot resume, not process death.
Guarded verification / recoveryAccepted for trusted fixturesDurable preparation, immutable reports, exact ownership, bounded replacement and original legacy contracts. Independent 23-case recovery review plus actual CLI crash recovery.
Confined executorAccepted for the tested stateless macOS boundaryIndependent 15-case API and 8-case fault matrices, native runtime checks, and permanent regressions for launch cancellation and atomic shared capacity. Executor receipt.
Repository sealing / exportAccepted for fresh owned local repositoriesExact prospective commit and manifest; independent corruption, replacement and redirected-path checks; real executor composition. Repository receipt.
Repository integrationAccepted as a local effect primitiveExact guarded ref update, one invocation, truthful unknown effects and read-only reconciliation;36focused tests and8independent groups. Product authority remains separate. Receipt. Native Git lock/unlink concurrency repaired; lock receipt. Git's transient loose-object finalisation link tolerated without weakening ownership guards; nlink receipt.
DashboardAccepted local browser interfaceNeutral API contract, pure projections, HTTP composition and browser presentation; guarded repository refresh, desktop/mobile checks and five independent regressions. Receipt.
Project guidance / AttentionAccepted local domain and browser interfaceRevisioned values, immutable pins, provenance, conflict-safe edits and source-derived action/blocker views; independent review and actual desktop/mobile browser verification. Receipt.
PortfolioAccepted for local metadata registration and sourced factsIdempotent identities, bounded correction history, explicit coverage, globally deduplicated usage and read-only projections. Portfolio receipt.
Producers (Claude / OpenAI)Accepted: provider-neutral producer contract, Claude CLI and OpenAI Responses adapters under independent review (Astra round 9 PASS, 2026-09-28). Live transports unavailable: Claude (rules revision 5 needs re-qualification; 5 built-in agents + 2 plugins lack established inert meaning), OpenAI (no Platform credential). Nothing composes it yet.Proposal-only contract, strict proposal parser, gate admission and consumption, and retention-safe receipts; 397/397 focused offline tests pass locally (344 at qualification time). Astra round 9 PASS (impl-verify-r9.md under <local evidence archive>) after rounds 1–8 FAIL (impl-verify-r1.md–r8.md), each confirming the previous round's fixes; round 9 ran 128/128 read-only tests and 32 in-memory probes, its sandbox blocked the filesystem, process and HTTP tests, and it covers the implementation, not live transport qualification. Live Claude qualification (2026-09-28, rules revision 4; the current rules revision 5 requires re-qualification): under the narrowed argv, the init listed 5 built-in agents and 2 plugins with no established inert meaning, so failed capability-inventory. Call 2 was not run, no commission was written, and spend is unknown. OpenAI: no Platform credential, no live request; its receipt is for rules revision 4, and revision 5 requires re-qualification when a Platform credential exists. Claude receipt, OpenAI receipt.
Repository AssuranceAccepted as step 1, increment 1: pure repository-scope judgement, not composed (Astra high, round 6 PASS, 2026-09-29, with increment 2)Candidate-as-program checks decided by the pinned exit code and stdout digest; the manifest and base listing authenticated before any Evidence counts; only unchanged store records of this Attempt qualify, and every associated record must be supplied; fixture Verdicts and records never relabelled. Report astra-inc12-r6.md under <local evidence archive> after rounds 1–5 FAIL (6, 4, 3, 2 and 1 findings; astra-inc12-r1.md–r5.md, with dispositions), each confirming the previous round's fixes. 16 module tests; 73/73 increment tests and 428/428 full check at review on f5a8991, none skipped. Nothing composed feeds it (the increment-3 collector, accepted, writes its records only in tests), and no receipt exists yet.
Product gate and delivery recordsAccepted as step 1, increment 2: Product authority and admission, not composed (Astra high, round 6 PASS, 2026-09-29, with increment 1)One journal aggregate per Product: admissions linearised against revocation in real processes; ownership only by fence proof (6,000 racing and 6,000 idle takeovers, 70 dead successors); integration admitted only on a Verdict re-derived inside the decision and a Candidate inside the Slice's frozen scope (round 5's finding); one open dispatch and one pending production per Product, and an unknown integration blocks the Product; separate allowance counters; byte budget; corrupt state refused, never repaired. Create-once ledger whose replays re-validate the stored record; Verdict-first Assessment derivation that re-judges the supplied records. Same Astra report and counts as Repository Assurance. After merging main at d7e4001: 851/851 full check, none skipped; at that merge one boundary assertion was narrowed so the Producers module may import its own contract (not independently reviewed). Nothing composes it; the collector is accepted but not composed, the delivery composition, CLI and the live Slice are not built, and no receipt exists yet.
Repository collectorAccepted as step 1, increment 3: runs a sealed Candidate's frozen checks under the Confined executor and stores one repository-scope Evidence record per run; not composed (Astra high, round 2 PASS, 2026-09-29)Real owned bare stores, sealed Candidates run as the executor's program, a real Evidence store and fence hold: B fails and M passes judged Verified; a plausible bug judged Failed; a hostile Candidate denied the answer key, stores, fence and writes, with no canary in any record and a forged header left inside stdout; protected paths the profile can read refused at setup and again before every launch, by name and by device and inode (Data-volume and /.vol spellings, links that do not resolve, .. after a link); pins the sealed Candidate was not sealed under refused before anything runs; a full root, a wrong runtime pin, a missing entry, a timeout, an output overflow, an abort, an unattributable, relabelled or unresolved run, a gate refusal, a passed deadline, a gate that does not answer before an abort or the deadline, and an oversized input each Inconclusive, never a fallback; a failed write or an ended hold stores nothing further; Candidate bytes changed after sealing change nothing that runs. Snapshot store: write-once, re-verified on read, corrupt entries never repaired. 20 module tests and 6 independent adversarial tests; the adversarial pass's four defects fixed test-first, each fix shown necessary by a mutation run. Report astra-inc3-r2.md under <local evidence archive> after round 1 FAIL (1 finding: placement not checked at setup); focused 50/50 and full check 881/881, none skipped (logs astra-inc3-tests.log, inc3-fix/). No receipt or reference review yet.
Repository integration guard seamAccepted as step 1, increment 3b, on independent implementation review (Astra round 1 FAIL, one finding; round 2 PASS); not composedinvokeOnce(prepared, guard): only the claim holder awaits the caller's trusted check, after the claim and immediately before the target update; anything but exactly {proceed: true} (a refusal, a throw, a malformed answer, or none within the Git time bound, measured by the monotonic clock after the answer so that a guard holding the thread past the bound and then allowing is withheld) starts no update and returns withheld with the claim, which every later read reports as unknown; without a guard nothing changes. 56/56 focused repository tests (six new rows; every existing test unchanged); eight source mutations each fail the new rows. Seam receipt.
IntelligenceAccepted: registry and pure selector (Astra high, implementation round 2 PASS, 29 September 2026; merged at 298726b). Lifecycle increment 0 (branch factory/lifecycle) changes it and passed its own independent review (Astra round 2 PASS, after round 1 FAIL); increments 1 and 2 and the merge with main change it furtherOne registry of where a model takes part, and a selector that refuses rather than substitutes; report astra-impl-r2.md under <local evidence archive>. Increment 0 of the proposed lifecycle design adds nine planned module declarations with five extension tasks and the three Astra tasks declared blocked until codex-cli's audit, since no effort is established on it, refuses an efficient task until its own measured comparison, pins the weekly search to a separate, unavailable research profile, enforces spec §5's per-call input bounds, adds a discovery-window allowance, and makes codex-cli OpenAI's one route, declared unqualified (decision 3's default), so the accepted OpenAI Responses adapter is kept but unpinned. An independent adversarial pass found eight defects and Astra round 1 one more, all fixed (<local evidence archive>); round 2 PASS (astra-r2.md there). The six earlier tasks' policy digests are byte-identical before and after; every task still refuses. 34/34 Intelligence tests (15 new) and a 918/918 full check, none skipped. No model is qualified and nothing dispatches. Receipt. Lifecycle increment 1 (branch factory/lifecycle-schedule) moves the lifecycle-schedule declaration into the accepted list with its one file, unchanged otherwise, and passed independent review with that module (Astra round 4 PASS; its receipt). Lifecycle increment 2 (branch factory/lifecycle-sources) moves the discovery-sources declaration into the accepted list with its two files, unchanged otherwise, so that receipt's hash of src/intelligence.ts no longer matches; every task's policy digest is byte-identical before and after (logs under <local evidence archive>), and the change passed independent review with that module (Astra round 5 PASS, astra-r5.md in the same directory). Merging increments 0–2 with main (branch factory/lifecycle-merge) keeps only the declarations whose code exists in the README table (19 rows, a 24-line section) and renders the three step-planned ones in the Intelligence reference with a new renderPlannedIntelligenceTable(), so the accepted 25-line cap holds; the README test names three tables instead of two, and no declaration, task or policy digest changes. Independent review: the highest-numbered astra-r*.md under <local evidence archive>. Merge receipt. Merging service access increment 1 with main (branch factory/service-access-merge) adds the service-access declaration (none, no tasks) as a hoisted function, so no line the lifecycle cites moves; the README table gains its row (20 rows, a 25-line section, at the cap), no other declaration, task or policy digest changes, and the lifecycle merge receipt's hash of src/intelligence.ts no longer matches. Independent review of that merge: pending. Service access merge receipt.
Lifecycle scheduleImplemented as lifecycle increment 1 (branch factory/lifecycle-schedule): occurrence identity, the discovery-window ledger and deferral on fixtures; an independent adversarial pass found 12 defects, all fixed; the fixed revision passed Astra round 4 (rounds 1-3 FAIL, every finding fixed; report astra-r4.md)One journal aggregate over an injected clock, each transition its own command with an identical retry replaying its receipt. Day, week (the 53-week 2026) and DST boundaries in Europe/London, Berlin and Tokyo; a restart gives one occurrence, including six racing processes and a runner killed mid-call; missed occurrences coalesce; a usage limit defers and resumes the same occurrence with one settlement and no re-sent unknown call; paid overage fails closed; the week's ceiling refuses and is never raised; corrupt state is refused. The adversarial fixes: a reconciled segment keeps a limit's reset, the owner blocker and the night's deadline; a deferral's retry replays after a resume; a moved full night never re-admits its week; nothing is due before a lane joined; a refusal reporting tokens used is an unknown effect; a closed usage window stops the segment; stored watermark and ledger defects are corrupt; retries of pruned records replay from history. Astra round 1 then added: usage-window and sign-in blocks held per account across Products; a reconciled segment resumes at the lane's slot after the reset; a coalesced weekly occurrence is never admitted later; paid overage recorded whatever its reset. Round 2: a sign-in record is compared with the refusal, not the deferral; a call admission is identified by its request (attempt) and replays after its call ended. Round 3: a replayed admission licenses no contact (dispatch only on a fresh one; an uncertain dispatch ends as lost); account stops only move forward; decisions read the clock inside the journal transaction; an overage observation with a usable closed reset also closes the window. Tests first (red run logged); 50 implementer tests and 12 adversarial ones. Every commission value is a proposal; no LaunchAgent is written or loaded, and nothing composes it. Logs under <local evidence archive>. Receipt.
Discovery sourcesAccepted as lifecycle increment 2 (branch factory/lifecycle-sources) on independent implementation review (Astra high, round 5 PASS, 29 September 2026); not composedThe deterministic collector of the proposed lifecycle (§8): allow-listed https Sources only, robots.txt first, fixed headers with no cookies, credentials or redirects; bodies over 2 MiB, pages over 100 items and items over 4 KiB refused, never truncated; content hashes, SimHash novelty with cross-domain duplicates, 15-word Citations that re-verify from a 35-day cache and are then unverifiable; drift marked, never rewritten; request, byte and deadline Budgets that end an occurrence partial. Written test-first (red run 37 of 38 failing). An independent adversarial pass then wrote 17 tests that all failed (Citations re-labelled, re-dated or fabricated; unspaced over-long quotes; invisible characters; implied head ends; plain text parsed as markup; percent-encoded robots paths; page text in validators; drift over refused items and earlier collections; late occurrences lost to novelty; unpruned cache; reserved IPv6; the README row); all 17 are fixed, none weakened (<local evidence archive>). Independent review: Astra round 1 FAIL with five findings (a Budget renewed by racing or retried attempts, inherited entity names decoded as text, prefixed Atom feeds read as zero, deadline-cut exchanges recorded as unavailable, a receipt older than the files) and round 2 FAIL with three (a feed with one unplaced entry read as partial but exact, drift reading an extractor change as gone, a chunk overrunning both the fetch limit and the byte Budget settling complete) round 3 FAIL with one (feed names cut at a dot, lower-cased and read without default namespaces) and round 4 FAIL with one (HTML raw-text skipping applied to XML, so a self-closing <script/> swallowed a feed), all fixed; round 5 PASS on the fixed revision (report astra-r5.md), confirming round 4 resolved. 76/76 offline tests (17 the adversary's) against a loopback corpus, none reaching the web; its HTTPS transport has never fetched a real page. Logs: <local evidence archive>. Receipt. No reference review yet.
Service access (increment 1)Provisionally accepted — Fable 5.1 (max) round 1; Astra review pending (Codex usage limit until 2026-10-03 18:00). Increment 1 on test-made fixtures, not composed. Astra high round 1 FAIL (eight findings, all fixed with their classes), round 2 stopped at the usage limit without a verdict; Fable 5.1 (max) interim round 1 PASS (fable-verify/fable-r1.md); from 3 October 2026 the highest-numbered astra-r*.md under <local evidence archive> holds the verdictNames-only catalogue of eleven Service kinds, deny-first tree scanning, listing and sign-in parsing, the Service map fold, exclusive store bindings (real racing processes), declarations, confirmations, route pins and readiness. Canary suite with a negative control; an adversarial pass whose fourteen tests each found a defect, all fixed with the adversarial suite unchanged, and a regression suite closing each class the adversary and the review opened, each class shown necessary by a source mutation. No live source is read and nothing composes it. Receipt.

Last accepted full verification (guidance increment over 8ada02a, including native Git-lock repair): strict typecheck and 350/350 tests pass, none skipped; actual check exit 0. Frontend build and actual desktop/mobile browser checks pass. The executor runs one Node process against read-only snapshots, with protected startup checks, no writable path, network or child processes. Candidate output cannot establish its own verification. Launcher binaries, static non-system runtime closure and OS build are pinned; named public runtime directories remain readable. Hard memory/disk limits, hard CPU termination and automatic recovery after executor-controller loss are not established. Controllers sharing an executor root must use one commissioned capacity value. Full API and limits: local development.

Repository verification: strict typecheck and 26/26 focused tests pass (21 permanent, five independent). Root replacement and redirected internal paths were reproduced, repaired and retained as permanent regressions. These additions are included in the passing full check.

Observed interface repairs: executor cancellation could be lost between spawn and collection; a state recheck now prevents admission. Two controllers could overbook capacity; exclusive slot reservation now enforces the shared cap. Unknown reservations are retained. Both independent reproductions now pass and are permanent tests. Native limits are checked through the actual executor path; a handled CPU-limit signal is explicitly not treated as a hard stop.

Existing-store command opening: CommandJournal.openExisting(path, options?) uses SQLite mode=rw; removal immediately before opening cannot create a replacement database. Empty/foreign/unsupported stores and missing required tables or columns fail before persistent write configuration. Accepted journals retain WAL/FULL durability. Root verified 41/41 focused tests, including independent regressions. This is not a storage-identity fence; normal SQLite coordination/recovery still applies. Receipt.

Service access, increment 1: a names-only map of a Product's Services and credential locations on test-made fixtures. Discovery opens no deny-listed path, re-validates every scan, listing and sign-in against what its readers write, never reads a value's text as a name (multi-line YAML and dotenv values, manifest strings and comments, expression literals, quoted shell arguments), and claims absence only from conclusive listings and uses whose resolution is known; readiness is presence, never validity, and says when only the owner can act. The receipt records the reviewed files' hashes, every review round and the limits: no live source, a heuristic credential screen, and line grammars that approximate libyaml and a shell. It is provisionally accepted — Fable 5.1 (max) round 1; Astra review pending (Codex usage limit until 2026-10-03 18:00); organisation-level absence (Fable round 1 finding 2) must be closed before increment 2 reads a live repository. Receipt.

Inspection repaired: a native read-only connection now rejects missing, empty, foreign and unsupported state without initialising schema. Commands, including replay, are refused before any transaction or decision callback. Inspection sees committed WAL state and later writer commits without dispatch or settlement. Normal SQLite reader coordination may touch sidecars; no schema/domain mutation occurs. Removal-race, killed-controller and real concurrent-writer regressions are permanent. Inspection receipt.

Earlier recovery demonstrations killed controllers after claim and after report commit. The first used one bounded replacement; the second settled the original Attempt without rerunning. Pins and Budget were preserved. Historical Verdicts remain distinct from current validity, and old /1 missing-report Attempts remain unresolved. Exact prior evidence: continuation receipt. The baseline receipt retains earlier validation and coverage measurements; those coverage percentages are not measurements of the current suite. Process-crash tests do not establish power-loss reliability.

Six local projects are registered, with source-backed local progress and partial builder usage imported; commissioning evidence. Guarded local integration is accepted as an effect primitive. The modular browser dashboard is independently accepted and browser-verified. Editable project values, central required actions and dedicated blocker resolution are accepted locally. Factory has six document-summary values; other products remain unset. Shared Plumb branding and module assets are accepted, and every epic references the guide. Product authority and admission (the Product gate) and repository-scope Assurance are accepted as step 1, increments 1–2, and composed into nothing. Next: the rest of step 1 (collector, delivery composition and CLI, one live useful Slice), qualified producer adapters and bounded evolution; see handover. The Run-briefing baseline is prepared but its improvement is not yet delivered. External pilots, CI, production operation and all 27 customer-value epics remain open.

Source: docs/build-review.md