Repository navigation
release: v0.3.0 - #3
tiago (tiagodocouto) wants to merge 1 commit into
Conversation
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 43dd01fbf4
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "Codex (@codex) review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "Codex (@codex) address that feedback".
| # out", and the collapse ended that — the leg IS plugin/, so nothing is copied and | ||
| # nothing is scrubbed. Refused rather than merely unused, so the dead provenance | ||
| # cannot reappear silently. | ||
| $2 !~ /^(core-as-is|release-support)$/ { exit 1 } |
There was a problem hiding this comment.
Update the retired core-class assertions
After this line rejects every core-scrubbed entry, the same awk program still requires as_is == 12 && scrubbed == 15, while the revised inventory contains 27 core-as-is and zero core-scrubbed rows. Running bash tests/manifest-test.sh therefore exits here with release inventory does not account for the 12/15 core cut; update this count and the closed expected class lists below so the repository gate can pass.
Useful? React with 👍 / 👎.
| NOTT.md core-scrubbed plugin/NOTT.md 100644 | ||
| PRD.md core-scrubbed plugin/PRD.md 100644 | ||
| NOTT.md core-as-is plugin/NOTT.md 100644 | ||
| PRD.md core-as-is plugin/PRD.md 100644 |
There was a problem hiding this comment.
Reconcile the release inventory with the committed tree
This commit deletes PRD.md and SPEC.md but leaves both in the inventory, while omitting all eight added files under hooks/ and roles/. Consequently the exact file-set comparison near the end of tests/manifest-test.sh must fail even after the earlier class assertion is repaired, preventing the release gates from accepting this candidate; remove the deleted entries and add every new shipped file with its correct class and mode.
Useful? React with 👍 / 👎.
| # The newest handoff capsule id is the thing we bind. Absent → nothing to bind. | ||
| handoff_id=$(printf '%s' "$dg" | jq -r '.handoff[0].id // empty' 2>/dev/null) || return 0 | ||
| [ -n "$handoff_id" ] || return 0 |
There was a problem hiding this comment.
Bind only the current session's handoff
When the current turn does not create a handoff—explicitly permitted by the reminder's “nothing substantial changed” clause, or simply because the advisory instruction is not followed—.handoff[0] is merely the newest store/project-wide handoff and can belong to another concurrent session. The subsequent relate then permanently attaches that stale or foreign handoff to the declared or newest open epic; carry the handoff ID produced by this session into the Stop hook, or skip the write when session ownership cannot be established.
Useful? React with 👍 / 👎.
| scope_args=() | ||
| [ -n "${NMEMORY_PROJECT:-}" ] && scope_args=(--project-prefix "$NMEMORY_PROJECT") | ||
|
|
||
| out="$(timeout 5 "$BIN" digest ${scope_args[@]+"${scope_args[@]}"} 2>/dev/null)" || exit 0 |
There was a problem hiding this comment.
Provide a portable timeout implementation
On stock macOS—the repository's macos-latest portable target—GNU timeout is not available, and the workflow installs only Gitleaks rather than Coreutils or another timeout command. This invocation therefore returns status 127 and the fail-open branch silently disables the newly registered session digest; the same dependency also disables prompt recall, dispatch recall, and effort binding. Use a portable timeout mechanism or explicitly provide and validate the platform-appropriate command in the runtime contract and tests.
Useful? React with 👍 / 👎.
| require_text PRIVACY.md 'Your prompt text is never recorded, the' | ||
| require_text PRIVACY.md 'transcript path is never recorded' | ||
| require_text PRIVACY.md 'at most the last 240 bytes of the closing paragraph' | ||
| require_text PRIVACY.md 'There is no opt-in variable and no way to turn' |
There was a problem hiding this comment.
Align all public privacy guidance with the shipped hook
These new assertions acknowledge that voice lint is always on and records a session ID plus assistant-text evidence, but the shipped README still says the default hooks store nothing, voice lint is opt-in, and retention is capped at 200 records; RUNBOOK.md repeats the same obsolete configuration and schema. Users relying on those documents receive materially false privacy and operational guidance because the implementation now writes an unbounded, default-enabled ledger and ignores block mode behaviorally; update every public guide and make this test reject the obsolete claims.
Useful? React with 👍 / 👎.
| [ "${NOTT_SESSION_DIGEST:-}" = off ] && exit 0 | ||
| BIN="$(command -v nmemory 2>/dev/null)" || exit 0 | ||
| [ -n "$BIN" ] && [ -x "$BIN" ] || exit 0 |
There was a problem hiding this comment.
Honor the documented nMEMORY override in hooks
The documented installation path allows nmemory to live outside PATH via NOTT_NMEMORY_BIN, and bin/nmemory-mcp validates and uses that override, but every newly added hook resolves only command -v nmemory. For users following RUNBOOK.md and setting the override to a non-PATH executable, the MCP server starts successfully while session digest, both recall hooks, and effort binding all silently disable themselves; resolve the binary through the same override contract as the launcher.
Useful? React with 👍 / 👎.
| scope_args=() | ||
| [ -n "${NMEMORY_PROJECT:-}" ] && scope_args=(--project-prefix "$NMEMORY_PROJECT") | ||
|
|
||
| out="$(timeout 5 "$BIN" digest ${scope_args[@]+"${scope_args[@]}"} 2>/dev/null)" || exit 0 |
There was a problem hiding this comment.
Keep automatic memory reads inside the plugin project
The shipped MCP configuration scopes nMEMORY to project nott with --project nott, but this globally registered hook defaults to an unscoped nmemory digest whenever NMEMORY_PROJECT is unset, which is the normal plugin configuration because the MCP argument does not set that environment variable. A session in any unrelated repository can therefore receive store-wide handoffs and efforts, and the two recall hooks and Stop binding use the same unscoped default; default these automatic operations to the plugin's configured project rather than exposing or mutating foreign-project memory.
Useful? React with 👍 / 👎.
| printf 'STALE MAIN TREE — nott-main-autosync has refused the fast-forward %s consecutive times since %s. /nott/monorepo is NOT advancing, so this session may be running a stale canon, stale hooks and a stale plugin. Reconcile the working tree before trusting plugin/NOTT.md; run `git -C /nott/monorepo status --short` and `git -C /nott/monorepo merge --ff-only origin/main` to see what collides.\n\n' \ | ||
| "$count" "${since:-an unknown time}" |
There was a problem hiding this comment.
Remove private host paths from the public hook
Running the repository's first release gate, bash tools/hygiene-lint.sh ., now fails deterministically with HOST_PATH hooks/session-digest.sh because this public hook embeds /nott/monorepo in its warning text (and repeats it in the drift warning). The release workflow invokes hygiene before the remaining gates, so no candidate containing this internal autosync path can pass; remove the monorepo-specific warning from the public hook or express remediation without a private absolute path.
Useful? React with 👍 / 👎.
| A role is a CHECKLIST, because a checklist item is answerable and red-testable while a | ||
| persona degrades with context. A role is NOT a persona, NOT a tone instruction, and NOT | ||
| extra authority: a role MUST NEVER widen the dispatched agent's tools, scope, or grant. |
There was a problem hiding this comment.
Declare normative scope for every new mandatory document
This new role contract uses MUST, MUST NOT, and NEVER without the normative-scope declaration required by tools/doc-lint.sh. Running the actual document gate reports the same failure for this catalog, all four role files, agents/executor.md, decisions.md, wiki.md, and the modified brainstorm, readback, and plan skills, so the release stops before manifest tests; add the required declaration to each normative document or remove mandatory language where it is not intended as law.
Useful? React with 👍 / 👎.
| **The senior bar is a NUMBER and a MECHANISM, never an adjective** (owner law 2026-08-01, ledger record `cap-1120`). The bar is a pull request the most sceptical reviewer at a bank approves. "Keep functions small" is worthless — it is unfalsifiable, so it is not a rule, it is a mood. Every clause below carries a threshold a tool measures and a named place the measurement runs. | ||
|
|
||
| 1. **The thresholds are the Rust community's, not invented here.** Clippy already ships curated complexity lints — `cognitive_complexity`, `too_many_lines`, `too_many_arguments`, `excessive_nesting`, `type_complexity`, `large_enum_variant` — and every one is `allow` by default. A repo that does not switch them on has no complexity bar, only an opinion about one. They MUST be enabled at their default thresholds or tighter, and a threshold MUST NOT be loosened to admit existing code. | ||
| 2. **Over the threshold is an EXCEPTION, and an exception carries an owner, a reason and an expiry.** The shape already exists in `quality/matrix.toml` and MUST be reused rather than reinvented: an exception NEVER expires into truth, `expires` is the date somebody MUST look again, and an expired exception FAILS the gate. Debt admitted this way is visible and dated; debt admitted by loosening a threshold is invisible forever. |
There was a problem hiding this comment.
Remove citations to non-shipping internal machinery
The imported canon now cites internal artifacts that do not exist in this repository, including quality/matrix.toml, slices/wi-000/..., .codex/hooks/ban-md-births.sh, .claude/hooks/ban-md-births.sh, and several absent tools and decision slugs. Running tools/citation-lint.sh over the candidate reports these independently of the already-stale PRD/SPEC and role paths, so the mandatory citation gate cannot pass; either ship the cited authorities or rewrite the public canon so every recognized citation resolves within this tree.
Useful? React with 👍 / 👎.
|
Closed: this candidate was held red by its own hygiene gate and never merged, so nothing was published from it. The n-soul leg goes straight to v0.3.1 — hardened, documented, and candidate-green — which opens its own release PR. Nothing here is lost; the work moved forward. |
Release v0.3.0.
Assembled from monorepo
b140210bb295cb45aa7a035f3b3cca9e9dd206fdbytools/assemble-mirror-candidate.sh, on top of this repository's published tip. Authorized by the owner merging the release request in the monorepo.Every fence ran before this branch existed: strip manifest, published-tip ancestry, and mirror parity (
mirror-only=0— this release drops no published path).