Skip to content

release: v0.2.0 — the work outlives the session - #81

Merged
AetherAI3 merged 5 commits into
mainfrom
release/v0.2.0
Aug 19, 2026
Merged

release: v0.2.0 — the work outlives the session#81
AetherAI3 merged 5 commits into
mainfrom
release/v0.2.0

Conversation

@AetherAI3

Copy link
Copy Markdown
Owner

Stacked on #80. Everything here is packaging: no behaviour changes.

Why

npm still serves 0.1.0, published 2026-06-11. Every npm i -g aether-agents today predates agent dev sessions, the durable media history, doctor v2, and the whole of #80. Publishing is release-triggered (.github/workflows/release.yml), so cutting the tag is what ships it.

README first screen

The old hero led with the category — "a coding agent for your terminal" — which is true of every tool on the shelf. It now leads with the two things specific to this one, both reproducible from a clean checkout:

Start a task on one model. Finish it on another, on another machine.
Your tests decide when it's done.

Below it: the install command, a runnable handoff example, and npm run demo:handoff. Model tables, pricing, and platform links stay where they are, below the fold.

Two claims corrected, not restated

  • The README credited the local brain to the Unlimited Context engine. That engine is a separate Python package the npm tarball does not carry; the shipped offline brain talks to Ollama directly. Both are now described for what they are, with the Python one shown as the AETHER_LOCAL_BRAIN=python opt-in it is.
  • --test-cmd was documented as defaulting to pytest -q. It has no default — a run without one ends unverified, and never ok.

The old hero paragraph also claimed QOPC memory made the agent "measurably better the more you use it". That is a server-side claim the client cannot demonstrate, so it is out of the first screen.

Version

0.1.00.2.0 in package.json and src/version.ts (the lockstep test covers both), plus the pinned-version examples in README.md and install.sh.

test/production_hardening.test.ts asserted the literal v0.1.0. It reads package.json now — a version bump is a release step, not a reason for the release gate to go red.

Release notes

RELEASE_NOTES.md gains the dated v0.2.0 entry; docs/releases/2026-08-19.md carries the long form and is indexed in docs/releases/README.md.

Verification

  • npm run typecheck — clean
  • version + production_hardening — 9 tests green at 0.2.0, including the pack → global install → aether --versionaether --help smoke against the real tarball
  • npm pack --dry-runaether-agents-0.2.0.tgz, 416 files, 2.0 MB unpacked, zero runtime dependencies

Not done here

Cutting the GitHub release (and therefore the npm publish) is deliberately left to a human — the draft text is ready in docs/releases/2026-08-19.md.

@AetherAI3
AetherAI3 changed the base branch from feat/growth-release to main August 19, 2026 11:33
@AetherAI3

Copy link
Copy Markdown
Owner Author

Retargeted to main so CI actually runs: the workflow triggers on pull_request against main only, so while this pointed at feat/growth-release it reported no checks at all.

Until #80 merges, this PR's diff shows both commits. Merge #80 first and this reduces to the release-packaging commits alone.

`aether resume` could replay a prior session's transcript to the screen, but
the brain never saw a byte of it: continuing meant re-typing the story so far,
and only ever on the machine where the work started. This makes the resume path
mean what it says.

A handoff (core/handoff.ts) is the machine-facing half of a session log — a
small JSON document distilled from one run: the task, the model that ran it,
the verify gate's verdict, the failing-test count, the files it changed, the
verification command, and the repository identity (origin remote, branch, HEAD).

- `aether agent --resume <id>` now prepends a continuation brief built from
  that record to the task the brain receives, so a different model picks the
  thread up with the project context in hand. With no new task, the run
  continues the original one (it used to fail with "nothing to do").
- `aether resume export [id] [--out <file>]` writes the handoff to a file.
  Nothing in it is keyed to an absolute path, so it can be copied to another
  checkout, machine, or OS, and `aether agent --resume <file>` continues there.
  A file reference is deliberately not workspace-scoped; a session id still is.
- The handoff is a summary, not a transcript: no file contents, no shell
  commands, no credential-shaped values. Untrusted files are validated field by
  field on the way back in, and one written by a newer Agent is refused with an
  upgrade hint rather than half-read.

Three fixes the above needed, each a bug in its own right:

- `aether agent --local "<task>"` spawned the separately-installed Python brain
  unconditionally, so a plain `npm i -g aether-agents` could only ever answer
  `spawn python ENOENT`. The one-shot offline path now drives the Ollama brain
  that ships inside the package — the same one the REPL's `--local` turns
  already used. `AETHER_LOCAL_BRAIN=python` opts back in, and the choice is a
  pure decision in core/backend.ts beside chooseBackend.
- The session log's credential filter matched `pat` as a substring, so `path`
  (and PATH, patch, pattern) was stored as "[REDACTED]". Every log could say a
  file changed but not which one. `pat` is now anchored to a whole segment;
  pat, gh_pat and pat_token are still redacted.
- The Ollama brain reported a placeholder `remaining: 1` on any unsuccessful
  run, so an unreachable-Ollama turn printed "1 test failing" when no test had
  run. The failing count comes only from the host's own verify run.

`npm run demo:handoff` (scripts/handoff-demo.ts, docs/demo/handoff.md) is the
end-to-end proof and takes about five seconds: it builds a throwaway git repo
with two genuinely failing tests, runs the real CLI on model A until half the
work is done, exports the handoff, creates a second checkout at a different
path, deletes the first checkout AND its logs, then finishes the job on model B
with `--resume <file>` and no restated task. The model — and only the model —
is a scripted local stub so the run is deterministic and needs no download or
account; AETHER_DEMO_REAL=1 runs the identical script against real Ollama
models. It asserts that session B's prompt carried the brief, that `node --test`
is green when run independently of the agent, and that the verify gate exited 0,
so it works as a CI gate as well as a demo.
…log once

Cleanup pass over the handoff feature. No intended behaviour change except
where a reused helper is strictly better than the hand-rolled version — those
are called out below.

Reuse:
- `writeHandoff` uses `atomicWriteFile` (core/durable_store.ts), the same
  write-then-rename every other durable file in this CLI already uses. An
  interrupted `resume export` can no longer destroy a good handoff or leave
  half a JSON document, and `--out reports/handoff.json` now creates the
  missing parent instead of failing with ENOENT.
- `readHandoff` uses `readJsonFile`, which already distinguishes missing from
  unreadable from corrupt — so the hand-rolled ENOENT check is gone and an
  empty file reads as "corrupt", the codebase's word for it, rather than
  "Unexpected end of JSON input".
- Untrusted strings go through `sanitizeTerm` (ui/text.ts) and `clipCodePoints`
  (ui/theme.ts) instead of a local clipper. A handoff arrives from another
  machine and its strings are BOTH printed and prepended to the brain's prompt,
  so it was the only untrusted-input surface in the CLI not passing through the
  terminal sanitizer. `clipCodePoints` also stops a truncation from cutting a
  surrogate pair in half.
- `wroteFile()` is now the one definition of "the run changed a file", called
  by both a handoff's `filesTouched` and cmdCode's live blast-radius set, which
  had the predicate written out twice.

`isHandoffPath` had a real defect: its separator class held only a forward
slash, so `--resume C:\work\handoff` (no .json) was classified as a session id
and died as "invalid session id". It now inverts `requireOpaqueId` — the same
rule `loadSession` enforces a moment later — so the two branches provably
partition the input, and Windows separators, `..`, and `~/` fall out for free.

Read the session log once. `resolveHandoff` loaded the session, distilled it,
and threw it away; `replaySession` then re-derived the file-vs-id decision and
loaded the same session again to render it. `resolveResume` returns
`{handoff, session}` and `resumeReplayLines` renders from it — one read, one
decision, and `replaySession`'s `ref`/`cwd` parameters disappear. On a
2000-event log that is 2000 fewer JSON parses and decodes per resume.

`aether resume` dispatches on argv like every other subcommand-bearing command
in main.ts, instead of joining `rest` into a string and re-splitting it by
prefix. `cmdResumeExport` is its own exported function. Side effect: `aether
resume abc def` reports `no such session: abc` rather than looking up the id
`"abc def"`.

Smaller: `summarizeEvents` bounds `highlights` as it goes rather than growing
to N and slicing to 40, and uses a Set for `filesTouched`; `parseHandoff`
bounds arrays before clipping them, so a hostile file with 10k highlights costs
40 clips rather than 10k; one `repoFrom` and one `asObject` replace two
spellings each; the demo's two model scripts are one shape with two
substitutions; the demo header no longer restates docs/demo/handoff.md.

Tests: the four resume-command cases share one `withLogRoot` fixture instead of
pasting the same 10-line prologue and env restore four times, and there are new
cases for the Windows path classification, the sanitizer, the shared write
predicate, and `--out` into a missing directory.

Deliberately not done: collapsing readRepoIdentity's three git spawns into two
(one saved spawn, subtler parsing); `latestSession`'s full-log scan (real, but
pre-existing and outside this diff); rebuilding `summarizeEvents` on top of
`monologueLine` (its tree-rendering shape is not a summary's).
The README's first screen led with the category ("a coding agent for your
terminal"), which is true of every tool on the shelf. It now leads with the two
things that are specific to this one and reproducible from a clean checkout:
the verify gate decides when a run is done, and a run's context can leave the
machine it started on.

- README hero: "Start a task on one model. Finish it on another, on another
  machine. Your tests decide when it's done." — followed by the install command,
  a runnable handoff example, and `npm run demo:handoff`.
- Two claims corrected rather than restated. The local brain was credited to
  the Unlimited Context engine, which lives in a separate Python package the npm
  tarball does not carry; the shipped offline brain talks to Ollama directly,
  and the Python one is now described as the opt-in it is. `--test-cmd` was
  documented as defaulting to `pytest -q`; it has no default, and a run without
  one ends `unverified`, never `ok`.
- The version bumps to 0.2.0. npm still serves 0.1.0 from June, so every
  `npm i -g aether-agents` today predates agent dev sessions, the media history,
  doctor v2, and everything in this release. Publishing is release-triggered
  (.github/workflows/release.yml), so cutting the tag is what ships it.
- The production verifier's test read the expected version from a literal
  "v0.1.0". It reads package.json now: a version bump is a release step, not a
  reason for the release gate to go red.

Release notes in RELEASE_NOTES.md and docs/releases/2026-08-19.md.
@AetherAI3
AetherAI3 merged commit 477f0fc into main Aug 19, 2026
5 checks passed
@AetherAI3
AetherAI3 deleted the release/v0.2.0 branch August 19, 2026 12:27
AetherAI3 added a commit that referenced this pull request Aug 22, 2026
…notes claim

On 2026-08-20 this repository described five different releases at once.
package.json said 0.2.0. package-lock.json still said 0.1.0 — the #81 bump never
touched it. RELEASE_NOTES.md's top entry described a 0.2.0 whose feature list was
written at 477f0fc, before #72 added `aether skills`, `aether capabilities` and
`aether support-bundle`. The npm registry served 0.1.0 and nothing else. And a
packed aether-agents-0.2.0.tgz sat in the repo root from #83 until #90 deleted
it, containing a build with no skills runtime in it at all.

Nothing was lying on purpose. The four statements drifted apart because nothing
compared them.

0.2.0 -> 0.3.0, not 0.2.1
-------------------------
#72 is a backwards-compatible feature addition — a skills runtime, three new CLI
commands, six built-in skills shipped inside the package — that the v0.2.0 notes
never mentioned. Semver makes that a minor bump.

Reusing 0.2.0 was rejected on identity grounds. 0.2.0 already names a specific
dated artifact: the August 19 notes entry, the README availability paragraph,
install.sh's pin example, and that committed tarball. Publishing different
contents under the same version would make two materially different artifacts
answer to one name, which is the defect this release exists to close. 0.2.0 is
retired unused; it will never be published.

Reconciled
----------
- package.json, package-lock.json (both version fields) and src/version.ts all
  say 0.3.0.
- RELEASE_NOTES.md leads with v0.3.0 covering 477f0fc..ed094dc: one feature,
  nine user-visible fixes, three test-only commits, one unwired module (#86 ship
  rail, which no command invokes), one docs commit. The v0.2.0 entry is marked
  superseded rather than rewritten — it is the record of what was written that
  day, not an install instruction.
- README and the release log name 0.3.0, and both still say plainly that
  `npm i -g aether-agents` gives you 0.1.0, because it does.

New gate: test/release_coherence.test.ts
----------------------------------------
Gate A asserts every place that names the release names the same one — including
both package-lock version fields, which is the drift nothing was watching.

Gate B is the load-bearing one: for every feature the release notes claim, the
code behind it must be present in the file list `npm pack` would actually ship,
and the command exposing it must be in the CLI registry. The source checkout's
dist/ is NOT the package — the allowlist is dist/src plus four docs.

Mutation-checked. Adding "!dist/src/commands/skills.js" to the files allowlist
silently drops `aether skills` from the tarball:

  verify:production  ->  {"ok":true, ... "packedFiles":523}   MISSED IT
  release_coherence  ->  FAIL: dist/src/commands/skills.js
                              (agent skills runtime — `aether skills`)

Restored: 7/7 pass, 524 packed files.

New: npm run release:candidate
------------------------------
release.yml only runs after a founder has already tagged and published, so
everything it checks is checked too late to change the decision. This runs the
same sequence, in the same order, before the tag exists — against a detached
git worktree of a specific commit, never the dirty checkout. A dirty tree is
refused unless --allow-dirty, which marks the report commitBound:false rather
than pretending.

Every CLI proof runs the binary npm installed from the packed tarball into a
clean prefix: --version, --help, `skills list`, `capabilities`, and the handoff
demo (the demo harness is not shipped, so it is placed beside the installed
package and resolves the CLI and its imports from the tarball's own dist/src).

Skipped steps are recorded as "not-run" with a reason and can never read as a
green tick — the full npm test suite is release.yml's gate and says so in the
report. No string is handed to a shell: npm is reached through its own JS
entrypoint under node, so every argument stays an argument.

Also
----
- scripts/verify-production.ts exports createPackReport, so a gate reasoning
  about what a user receives asks npm instead of reading the build directory.
- test/release_canaries.test.ts's coverage map said canaries 5 and 7 were
  unwritable. #86 and #87 wrote them two commits later; the excuse outlived the
  condition. The map is now enforced by a test that reads the delegated files.
- docs/releases/OPERATOR-PACKET-v0.3.0.md: the founder-owned publish sequence,
  with what is proven and what is explicitly not.

Gates at this commit:
  npm run typecheck                      exit 0
  release + production test files        21 pass / 0 fail
  npm run verify:production --tag v0.3.0 ok

Full npm test NOT run locally (a tool_executor test does not return on this
Windows box); CI is the authority.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
AetherAI3 added a commit that referenced this pull request Aug 23, 2026
…notes claim (#96)

* release: cut v0.3.0, and make the package prove it contains what the notes claim

On 2026-08-20 this repository described five different releases at once.
package.json said 0.2.0. package-lock.json still said 0.1.0 — the #81 bump never
touched it. RELEASE_NOTES.md's top entry described a 0.2.0 whose feature list was
written at 477f0fc, before #72 added `aether skills`, `aether capabilities` and
`aether support-bundle`. The npm registry served 0.1.0 and nothing else. And a
packed aether-agents-0.2.0.tgz sat in the repo root from #83 until #90 deleted
it, containing a build with no skills runtime in it at all.

Nothing was lying on purpose. The four statements drifted apart because nothing
compared them.

0.2.0 -> 0.3.0, not 0.2.1
-------------------------
#72 is a backwards-compatible feature addition — a skills runtime, three new CLI
commands, six built-in skills shipped inside the package — that the v0.2.0 notes
never mentioned. Semver makes that a minor bump.

Reusing 0.2.0 was rejected on identity grounds. 0.2.0 already names a specific
dated artifact: the August 19 notes entry, the README availability paragraph,
install.sh's pin example, and that committed tarball. Publishing different
contents under the same version would make two materially different artifacts
answer to one name, which is the defect this release exists to close. 0.2.0 is
retired unused; it will never be published.

Reconciled
----------
- package.json, package-lock.json (both version fields) and src/version.ts all
  say 0.3.0.
- RELEASE_NOTES.md leads with v0.3.0 covering 477f0fc..ed094dc: one feature,
  nine user-visible fixes, three test-only commits, one unwired module (#86 ship
  rail, which no command invokes), one docs commit. The v0.2.0 entry is marked
  superseded rather than rewritten — it is the record of what was written that
  day, not an install instruction.
- README and the release log name 0.3.0, and both still say plainly that
  `npm i -g aether-agents` gives you 0.1.0, because it does.

New gate: test/release_coherence.test.ts
----------------------------------------
Gate A asserts every place that names the release names the same one — including
both package-lock version fields, which is the drift nothing was watching.

Gate B is the load-bearing one: for every feature the release notes claim, the
code behind it must be present in the file list `npm pack` would actually ship,
and the command exposing it must be in the CLI registry. The source checkout's
dist/ is NOT the package — the allowlist is dist/src plus four docs.

Mutation-checked. Adding "!dist/src/commands/skills.js" to the files allowlist
silently drops `aether skills` from the tarball:

  verify:production  ->  {"ok":true, ... "packedFiles":523}   MISSED IT
  release_coherence  ->  FAIL: dist/src/commands/skills.js
                              (agent skills runtime — `aether skills`)

Restored: 7/7 pass, 524 packed files.

New: npm run release:candidate
------------------------------
release.yml only runs after a founder has already tagged and published, so
everything it checks is checked too late to change the decision. This runs the
same sequence, in the same order, before the tag exists — against a detached
git worktree of a specific commit, never the dirty checkout. A dirty tree is
refused unless --allow-dirty, which marks the report commitBound:false rather
than pretending.

Every CLI proof runs the binary npm installed from the packed tarball into a
clean prefix: --version, --help, `skills list`, `capabilities`, and the handoff
demo (the demo harness is not shipped, so it is placed beside the installed
package and resolves the CLI and its imports from the tarball's own dist/src).

Skipped steps are recorded as "not-run" with a reason and can never read as a
green tick — the full npm test suite is release.yml's gate and says so in the
report. No string is handed to a shell: npm is reached through its own JS
entrypoint under node, so every argument stays an argument.

Also
----
- scripts/verify-production.ts exports createPackReport, so a gate reasoning
  about what a user receives asks npm instead of reading the build directory.
- test/release_canaries.test.ts's coverage map said canaries 5 and 7 were
  unwritable. #86 and #87 wrote them two commits later; the excuse outlived the
  condition. The map is now enforced by a test that reads the delegated files.
- docs/releases/OPERATOR-PACKET-v0.3.0.md: the founder-owned publish sequence,
  with what is proven and what is explicitly not.

Gates at this commit:
  npm run typecheck                      exit 0
  release + production test files        21 pass / 0 fail
  npm run verify:production --tag v0.3.0 ok

Full npm test NOT run locally (a tool_executor test does not return on this
Windows box); CI is the authority.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* docs(release): fill the operator packet with the commit-bound candidate evidence

Run against a63e1c6 in a detached worktree: commitBound true, ok true, exit 0.
Tarball aether-agents-0.3.0.tgz, 524 entries, 589,829 bytes packed / 2,435,029
unpacked, sha256 25f33524bd866275674eccbf8cfe5706f14e925cb0ba35861dc6bc21a9245a2d.

The digest came out identical from an uncommitted tree and from the detached
worktree, which is recorded as content stability across a docs-only commit and
explicitly NOT as a cross-machine reproducibility claim.

Also records the mutation check: dropping dist/src/commands/skills.js from the
files allowlist leaves verify:production reporting ok:true at 523 files, and
fails release_coherence by name.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* release: cover #98 in the notes, and make the coherence gate bidirectional

The ground moved while PR #96 was open. #98 squash-merged to main, main became
426b124, and the v0.3.0 notes said nothing about it — which is this lane's own
defect arriving from the direction the lane did not gate.

WORK A: the notes now cover #98
-------------------------------
Its user-visible half is three fixes, and the first is the exact failure class
this codebase forbids:

- `aether doctor --live` never received --live. main.ts parses non-strictly, so
  a flag the command had not declared was captured globally and stripped from
  what the command was handed. --live ran the fast configured-only report and
  EXITED 0, presenting a live end-to-end verification that was never performed.
  Unknown rendered as verified. --deep, --dry-run, --no-ui and --only were lost
  the same way, and the whole --fix repair path was unreachable.
- `aether doctor --fix --yes` answered "re-run with --yes" to someone who had
  just passed it, because the global --yes never arrived either.
- Command lookup lowercased the token while dispatch was case-sensitive, so
  `aether Vault` fell past the typo guard into a chat turn and billed a paid
  model call.

The seam itself is announced too: a command now carries its own help metadata,
flag table and loader in one entry, flag collisions are load-time errors, and
reachability is structural rather than a regex over main.ts's source.

Range moves 477f0fc..ed094dc -> 477f0fc..426b124, 16 commits -> 17, across
RELEASE_NOTES.md, docs/releases/2026-08-22.md and the operator packet. Fixed a
miscount while re-deriving: the packet said "9 user-visible fixes" over a list of
ten.

WORK B: the gate now runs both directions
-----------------------------------------
Gate B ran notes -> package: a claim with no code behind it fails. It could not
see the inverse — a user-visible command that ships with NO claim anywhere — and
the inverse is what actually keeps happening, once per lane that lands between
the note being written and the tag being cut.

Gate C: every non-hidden command in the CLI registry must be announced by some
release note, or named in SHIPPED_WITHOUT_A_NOTE with a reason. An explicit list
is fine; silence is not. It is enforced in both directions — a stale entry fails,
and an entry that IS announced fails — so it cannot rot into a permanent bypass
that quietly absorbs the next unannounced command. Every entry must also appear
in the operator packet, because the founder cutting the tag is the person who
needs to know what goes out unannounced. 15 commands are on it today; all predate
the release log or were announced by capability in the June 2026 entry, and none
is new in this release.

Mutation-checked, per the controller's instruction. Added to the registry:

  { name: "teleport", args: "<dest>",
    summary: "beam the working tree somewhere", section: "System" }

  verify:production  -> {"ok":true, ... "packedFiles":527}        MISSED IT
  release_coherence  -> FAIL: no user-visible command ships without either a
                        release note or a named exemption
                        + [ 'teleport — beam the working tree somewhere' ]
                        - []

Registry restored byte-identical (md5 37b3f944…, `git status src/` empty),
10/10 pass. cli_registry.ts is read-only for this lane: it was mutated only in
the working tree, never committed, and the restore is verified by digest.

Also: Gate B now reads the registry by IMPORTING it instead of by regex over its
source. #98 replaced "reachability asserted by a regex over main.ts" for exactly
this reason, and it immediately split the commands across CLI_COMMANDS and
DISPATCH_COMMANDS — a source regex keyed on one array would have silently
stopped covering the other. doctor is in the second one.

Gates at this commit:
  npm run typecheck            exit 0
  release_coherence            10 pass / 0 fail

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* docs(release): re-cut the candidate on the new base, and record the digest change

The base moved to 426b124 (#98), so every number in the packet was taken against
a tree that no longer exists. Re-run, commit-bound, at 22aa021:

  commitBound true, ok true, exit 0
  aether-agents-0.3.0.tgz
  sha256 8c5c119d93cabf49af0c49c97addb055308d508af93f8675a26b6f5c8ecba307
  527 entries, 597,400 packed / 2,459,474 unpacked

The digest CHANGED from the a63e1c6 run (25f33524…, 524 entries), and the packet
now says why that is the correct outcome rather than a discrepancy: #98 added
dist/src/core/command_dispatch.* and rewrote main.js, so the packed content is
genuinely different. A digest that had survived that change would have meant the
pack was not reading the tree.

Both mutation checks were re-measured against this base rather than carried
forward:

  skills drop   verify:production {"ok":true, ... "packedFiles":526}  MISSED IT
                release_coherence FAIL: dist/src/commands/skills.js
                restored -> 527 files, 10/10 pass

  teleport      verify:production {"ok":true, ... "packedFiles":527}  MISSED IT
                release_coherence FAIL: 'teleport — beam the working tree
                somewhere'
                restored -> registry byte-identical, 10/10 pass

I had initially edited the skills figure from 523 to 526 by inference. That is a
number nobody measured, so it was re-run before being written down.

Release-owned suite at this commit: 24 pass / 0 fail.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* release: regenerate the v0.3.0 truth against the merged main

* release: cover #105 in the v0.3.0 notes

* release: bind the v0.3.0 operator packet to the head that carries #105

Regenerates the packet against a845479 (origin/main after #105): base SHA,
evidence commit, tarball digest, packed entry count, the recorded
release-candidate run, and the coverage breakdown.

Two corrections rather than refreshes:

- Section 5 no longer lists the full test suite as unproven. It was run at
  the evidence commit (1464 tests, 1460 pass, 0 fail, 4 skipped); what is
  genuinely unproven is the suite INSIDE the candidate run, which reports
  npm-test as not-run by design.
- Two new unproven entries name the deployed API. The notes' Authentication
  claims are about a server this repository cannot test, and #105 exists
  precisely because `aether agent` does not work end to end against
  production today. Both are marked rather than implied.

* release: record the measured tarball size, not a rounded one

The packed size in the packet header was written from npm's rounded
"740.0 kB" notice rather than measured. The tarball is 739,977 bytes.
A digest and a byte count that disagree are the same class of defect
this packet exists to close.

---------

Co-authored-by: DBarr3 <143002219+DBarr3@users.noreply.github.com>
Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant