nobrainer-tech-flow 2.4.1 → 2.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude-plugin/marketplace.json +1 -1
- package/.claude-plugin/plugin.json +1 -1
- package/.codex-plugin/plugin.json +1 -1
- package/README.md +14 -8
- package/docs/INSTALL.md +36 -22
- package/docs/MIGRATION_TO_FLOW.md +14 -0
- package/docs/SKILL_CURATION.md +8 -2
- package/docs/releases/v2.5.0.md +190 -0
- package/docs/releases/v2.6.0.md +73 -0
- package/gemini-extension.json +1 -1
- package/package.json +1 -1
- package/plugin.json +1 -1
- package/scripts/install.py +16 -7
- package/scripts/install.sh +129 -17
- package/scripts/install_personalization.py +51 -16
- package/scripts/install_skills.py +34 -5
- package/scripts/recommend_flow_setup.py +102 -12
- package/scripts/validate_skills.py +2 -1
- package/skills/nobrainer-build/SKILL.md +6 -2
- package/skills/nobrainer-context/SKILL.md +113 -0
- package/skills/nobrainer-context/references/clients.md +115 -0
- package/skills/nobrainer-context/references/consolidate.md +66 -0
- package/skills/nobrainer-context/scripts/context_inventory.py +425 -0
- package/skills/nobrainer-skill-doctor/SKILL.md +4 -4
- package/skills/nobrainer-tech-flow/SKILL.md +3 -3
- package/skills/nobrainer-tech-flow/VERSION +1 -1
- package/skills/nobrainer-tech-flow/references/daily-update.md +5 -2
- package/skills/nobrainer-tech-flow/references/delivery.md +17 -2
- package/skills/nobrainer-tech-flow/references/optional-decisions.md +5 -3
- package/skills/nobrainer-tech-flow/references/routing.md +1 -1
- package/skills/nobrainer-tech-flow/scripts/typed_decisions.py +20 -9
- package/skills/nobrainer-codex-context/SKILL.md +0 -111
- /package/skills/{nobrainer-codex-context → nobrainer-context}/scripts/codex_context.py +0 -0
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
{
|
|
9
9
|
"name": "nobrainer-tech-flow",
|
|
10
10
|
"description": "From task to done. nobrainer-tech-flow is one workflow of 18 modules for AI coding agents: it scopes the task, delegates ready work, checks the result and hands over the evidence, including what was not checked.",
|
|
11
|
-
"version": "2.
|
|
11
|
+
"version": "2.6.0",
|
|
12
12
|
"source": "./",
|
|
13
13
|
"author": {
|
|
14
14
|
"name": "NoBrainer Tech"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nobrainer-tech-flow",
|
|
3
3
|
"description": "From task to done. nobrainer-tech-flow is one workflow of 18 modules for AI coding agents: it scopes the task, delegates ready work, checks the result and hands over the evidence, including what was not checked.",
|
|
4
|
-
"version": "2.
|
|
4
|
+
"version": "2.6.0",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "NoBrainer Tech"
|
|
7
7
|
},
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nobrainer-tech-flow",
|
|
3
3
|
"description": "From task to done. nobrainer-tech-flow is one workflow of 18 modules for AI coding agents: it scopes the task, delegates ready work, checks the result and hands over the evidence, including what was not checked.",
|
|
4
|
-
"version": "2.
|
|
4
|
+
"version": "2.6.0",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "NoBrainer Tech",
|
|
7
7
|
"url": "https://nobrainer.tech"
|
package/README.md
CHANGED
|
@@ -260,8 +260,10 @@ sh ~/.nobrainer-tech-flow/scripts/install.sh --client claude --apply # link th
|
|
|
260
260
|
`--client` is `claude`, `codex`, `opencode` or `copilot`. Cursor, Gemini CLI, Pi and Kimi Code
|
|
261
261
|
use a plugin or extension instead: see their sections in
|
|
262
262
|
[docs/INSTALL.md](docs/INSTALL.md#client-channels). The script links all eighteen skills and adds
|
|
263
|
-
one instruction block, shows the exact text first, refuses anything that is not its own
|
|
264
|
-
|
|
263
|
+
one instruction block, shows the exact text first, refuses anything that is not its own and
|
|
264
|
+
undoes itself with `--undo --apply`. The block lets Flow update itself to verified stable
|
|
265
|
+
releases once a day; `install_personalization.py --no-auto-update` turns that into a
|
|
266
|
+
notification only. No other authorization is granted. To update, run `git pull` in
|
|
265
267
|
`~/.nobrainer-tech-flow` and the same two commands again, or paste the prompt again. With Python,
|
|
266
268
|
`python3 scripts/install.py` takes the same flags.
|
|
267
269
|
|
|
@@ -303,7 +305,8 @@ next command.
|
|
|
303
305
|
`install.py`, like `scripts/install.sh` without Python, links all eighteen skills
|
|
304
306
|
and adds one managed instruction block for `claude`, `codex`, `opencode` or
|
|
305
307
|
`copilot`. The preview shows the exact text it would write, a target that is not
|
|
306
|
-
its own link is refused,
|
|
308
|
+
its own link is refused, the only standing authorization is the default daily Flow
|
|
309
|
+
update (opt out with `install_personalization.py --no-auto-update`), and
|
|
307
310
|
`python3 scripts/install.py --client codex --undo --apply` reverses it. It needs
|
|
308
311
|
symbolic links (Windows: Developer Mode). For a subset, a copy install, the shared
|
|
309
312
|
`agents` folder or another client, use the individual scripts in
|
|
@@ -423,7 +426,7 @@ recurring boundary:
|
|
|
423
426
|
|---|---|---|
|
|
424
427
|
| [`nobrainer-tech-flow`](skills/nobrainer-tech-flow/) | `NBFlow`, `NBF` | Technical entrypoint for end-to-end setup and delivery: one requirements gate, concise progress, bounded execution, recovery, audit and learning |
|
|
425
428
|
| [`nobrainer-auto-fine-tune`](skills/nobrainer-auto-fine-tune/) | `nb-auto-fine-tune` | Read-only capability audit and route calibration: verified host models, effort, context and useful parallelism while MAIN keeps the owner's model |
|
|
426
|
-
| [`nobrainer-
|
|
429
|
+
| [`nobrainer-context`](skills/nobrainer-context/) | `nb-context` | One set of project instructions for every coding agent: what Codex, Claude Code, Gemini CLI, Cursor, Copilot and OpenCode load, size limits, duplicates and contradictions, one source of truth with pointers after approval, and readback |
|
|
427
430
|
| [`nobrainer-skill-doctor`](skills/nobrainer-skill-doctor/) | `nb-skill-doctor` | Cross-project audit of skills, project instructions and task prompts: trigger overlap, excessive process, coverage and minimal portfolio repair planning |
|
|
428
431
|
| [`nobrainer-team`](skills/nobrainer-team/) | `nb-team` | Capability selection and bounded native assignments, installed-skill inventory and safe temporary specialist discovery |
|
|
429
432
|
| [`nobrainer-dispatcher`](skills/nobrainer-dispatcher/) | `nb-dispatcher` | Dependency-aware ready-set scheduling, bounded dispatch, backpressure and audited result routing |
|
|
@@ -531,12 +534,15 @@ prove production. See [Compatibility](docs/COMPATIBILITY.md) for current proof
|
|
|
531
534
|
and [Testing](docs/TESTING.md) for acceptance evidence.
|
|
532
535
|
|
|
533
536
|
|
|
534
|
-
**What's new in 2.
|
|
535
|
-
|
|
537
|
+
**What's new in 2.6.0:** Flow delegates aggressively: independent units of
|
|
538
|
+
substantial work go to parallel native subagents, sized so parallel work pays for its
|
|
539
|
+
start-up cost, verification depth follows how risky and reversible a change is, and one
|
|
540
|
+
line in the instruction block keeps Flow updated by default (`--no-auto-update` opts out).
|
|
541
|
+
See [RELEASE-NOTES.md](RELEASE-NOTES.md).
|
|
536
542
|
|
|
537
|
-
Current source version: **2.
|
|
543
|
+
Current source version: **2.6.0**. Check the
|
|
538
544
|
[latest published GitHub release](https://github.com/nobrainer-tech/nobrainer-tech-flow/releases/latest)
|
|
539
|
-
for distribution and the [2.
|
|
545
|
+
for distribution and the [2.6.0](docs/releases/v2.6.0.md), [2.5.0](docs/releases/v2.5.0.md) and
|
|
540
546
|
[2.4.0 verification records](docs/releases/v2.4.0.md) for
|
|
541
547
|
the current scope, reproducible checks and client-runtime limits. The unchanged command runner keeps its
|
|
542
548
|
[v1.7.0 verification scope](docs/releases/v1.7.0.md). Source publication does not
|
package/docs/INSTALL.md
CHANGED
|
@@ -14,9 +14,9 @@ upgraded merely because the new source is installed nearby.
|
|
|
14
14
|
Node 18+ and Python 3.11+ are prerequisites. Preview the setup first:
|
|
15
15
|
|
|
16
16
|
```sh
|
|
17
|
-
npx nobrainer-tech-flow@2.
|
|
18
|
-
npx nobrainer-tech-flow@2.
|
|
19
|
-
npx nobrainer-tech-flow@2.
|
|
17
|
+
npx nobrainer-tech-flow@2.6.0 --client codex
|
|
18
|
+
npx nobrainer-tech-flow@2.6.0 --client codex --apply
|
|
19
|
+
npx nobrainer-tech-flow@2.6.0 --client codex --undo --apply
|
|
20
20
|
```
|
|
21
21
|
|
|
22
22
|
Use claude for Claude Code, opencode or copilot for those clients. Add --home PATH
|
|
@@ -24,7 +24,7 @@ for an isolated profile. These commands become available once this version is
|
|
|
24
24
|
published on npm; a source candidate is not registry availability.
|
|
25
25
|
|
|
26
26
|
Application copies the release files into the chosen home directory's
|
|
27
|
-
.nobrainer-tech-flow-npm/2.
|
|
27
|
+
.nobrainer-tech-flow-npm/2.6.0 and verifies the copy. That folder sits beside
|
|
28
28
|
~/.nobrainer-tech-flow, where the Git installation suggests a clone, so cleaning
|
|
29
29
|
the clone cannot delete the files the skill links point to. Releases before 2.3.2
|
|
30
30
|
kept their copy in .nobrainer-tech-flow/npm; undo such a setup with the command of
|
|
@@ -106,14 +106,18 @@ flags). The two share the setup record, so either one undoes what the other did.
|
|
|
106
106
|
- Running `--apply` again when nothing needs to change prints `UP TO DATE` and no
|
|
107
107
|
restart hint. `INSTALLED` and the restart hint appear only when a link or the
|
|
108
108
|
instruction file was written.
|
|
109
|
-
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
109
|
+
- The only standing authorization it writes is the default one-line daily update of
|
|
110
|
+
Flow itself to a verified stable release; session rotation still needs its own
|
|
111
|
+
opt-in. When the block in the instruction file is the text of an earlier version,
|
|
112
|
+
both scripts replace it with this version's text, keep everything outside the two
|
|
113
|
+
markers byte for byte and save the file as it was as a `.bak` copy first. Both keep
|
|
114
|
+
the update choice: an existing block updates itself again only when it holds the
|
|
115
|
+
update line as its own line, and a notify-only, edited or unknown update line is
|
|
116
|
+
replaced by the one-line notify-only rule. `install.py` also keeps session-restart
|
|
117
|
+
and wiki-root settings as `--keep-options` keeps them; `install.sh` leaves a block
|
|
118
|
+
that carries one of those options or a preference, or whose markers do not stand on
|
|
119
|
+
lines of their own, exactly as it is and says so. Change options with
|
|
120
|
+
`install_personalization.py`.
|
|
117
121
|
- `--undo` (a preview until `--apply` is added) removes exactly the links the setup
|
|
118
122
|
created and puts the managed block back as it was before the first setup:
|
|
119
123
|
removed, or the block that was there before. The rest of the instruction file
|
|
@@ -213,8 +217,11 @@ shared folder.
|
|
|
213
217
|
## Conflict and migration behavior
|
|
214
218
|
|
|
215
219
|
`install_skills.py` and `install.sh` never overwrite an unknown directory, file
|
|
216
|
-
or symlink. A foreign target at
|
|
217
|
-
`PRESERVED_FOREIGN` and left unchanged without blocking installation.
|
|
220
|
+
or symlink. A foreign target at a retired name such as `nobrainer-reddit` is
|
|
221
|
+
reported as `PRESERVED_FOREIGN` and left unchanged without blocking installation.
|
|
222
|
+
An exact old link into this checkout at a retired name that a setup record lists
|
|
223
|
+
is removed by the next `install.sh` or `install.py` apply (see the
|
|
224
|
+
[migration guide](MIGRATION_TO_FLOW.md) for the 2.5.0 rename). A foreign
|
|
218
225
|
target at a renamed alias such as `nb-flow`, a canonical name or an unresolved
|
|
219
226
|
legacy name such as `nobrainer-fast-audit` still stops installation.
|
|
220
227
|
|
|
@@ -273,17 +280,24 @@ the instructions. A guided setup recorded earlier for the Codex file asks for an
|
|
|
273
280
|
undo before it writes the Claude file. `agents` needs an explicit verified
|
|
274
281
|
`--path`. For a resolved global wiki,
|
|
275
282
|
pass `--wiki-root PATH` pointing at a directory containing `WIKI.md`; this
|
|
276
|
-
records the actual location in the personalization block.
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
283
|
+
records the actual location in the personalization block. Since 2.6.0 the
|
|
284
|
+
block keeps Flow updated by default with one line: once a day on first use,
|
|
285
|
+
update to the latest verified stable release from the canonical source, with a
|
|
286
|
+
backup, changing nothing else. `--no-auto-update` writes a one-line notify-only
|
|
287
|
+
rule instead; `--auto-update` is still accepted and means the default. With
|
|
288
|
+
`--keep-options` an opt-out already in the block stays, and the longer update
|
|
289
|
+
lines written before 2.6.0 become the matching short line (an old grant stays a
|
|
290
|
+
grant, the old notify-only default stays notify-only). An update line that is
|
|
291
|
+
neither recognized grant becomes the notify-only line: updates are never inferred. `--auto-session-restart`
|
|
292
|
+
opts into evidence-gated session rotation. A later run without those flags
|
|
293
|
+
writes the default block again; add `--keep-options` to keep the update choice,
|
|
294
|
+
session-restart and wiki-root settings already in the block (the guided setup
|
|
295
|
+
always does). A grant counts
|
|
282
296
|
only as the exact line the installer writes for it, so wording quoted in a
|
|
283
297
|
`--preferences` value never becomes one, and a preference or wiki path must be
|
|
284
298
|
one printable line. A grant line that was edited is not kept, and the run says so
|
|
285
|
-
and names the flag that grants it again.
|
|
286
|
-
|
|
299
|
+
and names the flag that grants it again. With the
|
|
300
|
+
notify-only line, the first active `nobrainer-tech-flow` use each day checks and
|
|
287
301
|
notifies. Use a scheduler separately if updates must be checked on inactive days.
|
|
288
302
|
|
|
289
303
|
A newer release must be obtained at a verified immutable ref before any
|
|
@@ -98,6 +98,20 @@ until migrated with `install_skills.py --migrate-legacy`. Foreign renamed aliase
|
|
|
98
98
|
such as `nb-flow` and unresolved legacy names still block installation to prevent
|
|
99
99
|
trigger conflicts.
|
|
100
100
|
|
|
101
|
+
In 2.5.0 the module `nobrainer-codex-context` (trigger `nb-codex-context`) became
|
|
102
|
+
`nobrainer-context` (trigger `nb-context`) and covers every coding agent's project
|
|
103
|
+
instructions, not only Codex. The old name and trigger no longer work. When the
|
|
104
|
+
setup record of a Git checkout (`install.sh` or `install.py`) lists the old link,
|
|
105
|
+
the next apply removes that exact link into this checkout and links
|
|
106
|
+
`nobrainer-context`; undo also removes it. The npm setup keeps each release in its
|
|
107
|
+
own folder, so undo an npm setup with the earlier release's command before
|
|
108
|
+
applying 2.5.0, as [INSTALL.md](INSTALL.md) describes. An old link without a record, for example one made by
|
|
109
|
+
`install_skills.py` directly, still blocks until migrated with
|
|
110
|
+
`install_skills.py --migrate-legacy`. A file, folder, copy or link at the old name
|
|
111
|
+
that is not this checkout's link is left unchanged (`PRESERVED_FOREIGN`); remove a
|
|
112
|
+
copy you made of the old module yourself. Plugin installs pick up the new name on
|
|
113
|
+
update.
|
|
114
|
+
|
|
101
115
|
After an update, read back the source commit and package identity, restart the
|
|
102
116
|
client and confirm that `nobrainer-tech-flow` loads once. A version change or an
|
|
103
117
|
installed file alone does not establish runtime compatibility.
|
package/docs/SKILL_CURATION.md
CHANGED
|
@@ -41,14 +41,14 @@ Popularity, file size and prior existence are not admission criteria.
|
|
|
41
41
|
| `nobrainer-decide` | One consequential decision after alternatives, scoring and adversarial attack. |
|
|
42
42
|
| `nobrainer-rca` | Read-only causal diagnosis of an observed failure. |
|
|
43
43
|
| `nobrainer-review` | Final acceptance/bug/release evidence gate and verified actionable findings. |
|
|
44
|
-
| `nobrainer-
|
|
44
|
+
| `nobrainer-context` | One project's instruction files for every coding agent: what each client loads, size limits, duplicates and contradictions, one approved source of truth with pointers, and readback. |
|
|
45
45
|
| `nobrainer-skill-doctor` | Cross-project audit of skills, project instructions and task prompts, with coverage, overlap and minimal portfolio repair planning. |
|
|
46
46
|
|
|
47
47
|
## Boundaries that stay embedded
|
|
48
48
|
|
|
49
49
|
Do not create separate permanent skills for:
|
|
50
50
|
|
|
51
|
-
- planning, autopilot, general NoBrainer setup or correction capture: the Flow entry skill owns the lifecycle;
|
|
51
|
+
- planning, autopilot, general NoBrainer setup or correction capture: the Flow entry skill owns the lifecycle; one project's instruction files belong to `nobrainer-context`;
|
|
52
52
|
- visible goal/TODO progress: Flow owns one canonical plan and its compact view;
|
|
53
53
|
do not add a separate goal, todo or progress skill;
|
|
54
54
|
- KISS, DRY, SOLID, YAGNI, simplification or test safety: Build owns them;
|
|
@@ -109,6 +109,12 @@ targets at that name with `PRESERVED_FOREIGN`. Only exact old links from this
|
|
|
109
109
|
checkout remain migration candidates. Renamed/absorbed aliases retain blocking
|
|
110
110
|
conflict checks.
|
|
111
111
|
|
|
112
|
+
`nobrainer-codex-context` is `RETIRED` in 2.5.0 by owner decision (2026-10-20): its
|
|
113
|
+
boundary grew into `nobrainer-context`, which covers every coding agent's project
|
|
114
|
+
instructions, and the old name keeps no alias or trigger. Foreign targets at the
|
|
115
|
+
old name are preserved like `nobrainer-reddit`; an exact old link that a setup
|
|
116
|
+
record lists is removed by the next setup apply or undo.
|
|
117
|
+
|
|
112
118
|
## Change control
|
|
113
119
|
|
|
114
120
|
Any addition, merge or retirement updates together:
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
# nobrainer-tech-flow 2.5.0: one set of project instructions for every agent
|
|
2
|
+
|
|
3
|
+
Release date: 2026-10-20.
|
|
4
|
+
|
|
5
|
+
The module `nobrainer-codex-context` (`nb-codex-context`) becomes `nobrainer-context`
|
|
6
|
+
(`nb-context`). It now looks at the project instructions of every coding agent in use,
|
|
7
|
+
not only Codex. The old name keeps no alias. The module set stays at eighteen.
|
|
8
|
+
|
|
9
|
+
## What changes
|
|
10
|
+
|
|
11
|
+
- **One inventory for six clients.** `skills/nobrainer-context/scripts/context_inventory.py`
|
|
12
|
+
(Python 3.11+ standard library, read-only) lists, for Codex, Claude Code, Gemini CLI,
|
|
13
|
+
Cursor, GitHub Copilot and OpenCode, the instruction files each one loads in a
|
|
14
|
+
project: at start, on demand, by import or only on some surfaces. It reports bytes,
|
|
15
|
+
lines and words, the Codex `project_doc_max_bytes` budget and truncation, files over
|
|
16
|
+
Claude Code's 200-line or Cursor's 500-line guidance, byte-identical copies, lines
|
|
17
|
+
repeated across files with `file:line` locations, and whether the instructions name
|
|
18
|
+
the current Flow goal file (`NONE`, `POINTED`, `NOT_POINTED`, `STALE_POINTER`).
|
|
19
|
+
`--include-global` adds each client's user-level file. The earlier Codex probe,
|
|
20
|
+
`codex_context.py`, ships unchanged next to it.
|
|
21
|
+
- **Rules from the clients' own documentation.** `references/clients.md` lists what
|
|
22
|
+
each client loads, its documented limit and its readback, with the official pages
|
|
23
|
+
checked on 2026-10-20. Points the pages do not document (a Codex command that prints
|
|
24
|
+
the loaded instructions, the `project_root_markers` default, Cursor's `.cursorrules`
|
|
25
|
+
status, a Copilot character limit, Gemini CLI size limits) are marked `UNVERIFIED`
|
|
26
|
+
and reported as unknown, never as limits.
|
|
27
|
+
- **One source of truth, applied only after approval.** `references/consolidate.md`
|
|
28
|
+
proposes `AGENTS.md` as the source of truth with short pointers, for example
|
|
29
|
+
`@AGENTS.md` in `CLAUDE.md` or `context.fileName` for Gemini CLI. It covers the
|
|
30
|
+
traps the documentation names: a `CLAUDE.md` or `CLAUDE.local.md` stops Claude Code
|
|
31
|
+
from reading `AGENTS.md` directly, imports still load at start, and a sentence that
|
|
32
|
+
only says "read AGENTS.md" is unreliable. Contradictions are reported with
|
|
33
|
+
`file:line` pairs and never resolved by picking one wording. Edits are project-local,
|
|
34
|
+
follow a full preview and an explicit yes, and are read back by running the
|
|
35
|
+
inventory again. Global files and client settings stay untouched unless the owner
|
|
36
|
+
asks for that separately.
|
|
37
|
+
- **Goal pointer only.** When the project keeps a Flow goal file, the module checks
|
|
38
|
+
that instructions name the current one. Goal content and handoff stay with
|
|
39
|
+
`nobrainer-tech-flow` and `nobrainer-sessions`.
|
|
40
|
+
- **Clean update from the old name.** `nobrainer-codex-context` joins the retired
|
|
41
|
+
names. `install.sh` and `install.py` read the setup record: when it lists
|
|
42
|
+
the old name and the old link is this checkout's exact link, preview shows
|
|
43
|
+
`REMOVE_RETIRED`. Apply links `nobrainer-context` and writes everything else
|
|
44
|
+
first; the old link goes last, just before the record is saved. It is moved into a
|
|
45
|
+
private folder and checked there, so an entry that replaced it after the check is
|
|
46
|
+
put back untouched, and it comes back if the record cannot be saved. Undo of a
|
|
47
|
+
setup made before 2.5.0 removes the old link too. `install_skills.py` gains
|
|
48
|
+
`--recorded-retired NAME`, which stops that link from blocking and never deletes
|
|
49
|
+
it; without a record an exact old link still needs `--migrate-legacy`. A file,
|
|
50
|
+
folder, copy or link at the old name that is not this checkout's link is reported
|
|
51
|
+
as `PRESERVED_FOREIGN` and left unchanged.
|
|
52
|
+
- **TypeSafe key only on request.** `typed_decisions.py` no longer reads
|
|
53
|
+
`TYPESAFE_API_KEY` by itself. `--key-env NAME` names the variable, and the key
|
|
54
|
+
reaches the worker on standard input; the worker's environment carries no
|
|
55
|
+
credential.
|
|
56
|
+
|
|
57
|
+
## Claude plugin directory findings
|
|
58
|
+
|
|
59
|
+
The directory scan of the 2.4.1 plugin ZIP reported four kinds of findings without
|
|
60
|
+
details. A local scan of the built ZIP matched them as follows:
|
|
61
|
+
|
|
62
|
+
- *Uses a credential from the user's machine* (3): `typed_decisions.py` read
|
|
63
|
+
`TYPESAFE_API_KEY`, sent it as a bearer token and copied it into the child process.
|
|
64
|
+
Fixed: the key is read only from a variable the user names with `--key-env`.
|
|
65
|
+
- *Contains a download-and-run command* (2): no shipped script downloads and runs
|
|
66
|
+
anything. The likely matches are instructions in `nobrainer-team` (`npx skills
|
|
67
|
+
find/add/use`, a documented, owner-gated capability search) and `nobrainer-browser`
|
|
68
|
+
(installs `@playwright/cli` at the exact version it read back first). Left as they
|
|
69
|
+
are: both are documented steps an agent runs only under the existing approval
|
|
70
|
+
gates, not executed code.
|
|
71
|
+
- *Image or font file that the plugin's code could run* (3): the ZIP holds exactly
|
|
72
|
+
three images: `assets/nobrainer-tech-logo.svg`, `assets/nobrainer-workflow.svg` and
|
|
73
|
+
`assets/plugin-logo.png`. Neither SVG has a script, event handler, `foreignObject` or
|
|
74
|
+
external reference; the PNG has only standard chunks. No script reads them; the
|
|
75
|
+
manifests reference the logo. Left as they are.
|
|
76
|
+
- *Unrecognized field in plugin.json* (3): `.claude-plugin/plugin.json` passes
|
|
77
|
+
`claude plugin validate --strict`. The fields Claude does not know are in the other
|
|
78
|
+
clients' manifests that the same ZIP carries for the OpenAI upload: `extensions` and
|
|
79
|
+
`$schema` in the root `plugin.json`, `interface` in `.codex-plugin/plugin.json`.
|
|
80
|
+
Left as they are: removing them would break the OpenAI package, and Claude ignores
|
|
81
|
+
unknown fields at load.
|
|
82
|
+
|
|
83
|
+
## Verification record
|
|
84
|
+
|
|
85
|
+
Initial implementation checks (macOS, Python 3.14.5), before the later
|
|
86
|
+
eleven-finding review:
|
|
87
|
+
|
|
88
|
+
- `python3 scripts/validate_skills.py` and `python3 scripts/validate_skills.py --suite`:
|
|
89
|
+
both passed.
|
|
90
|
+
- `python3 -m unittest discover -s tests`: 531 tests ran, all passed except 5
|
|
91
|
+
platform-specific skips. This includes the exported-source run without Git metadata.
|
|
92
|
+
- `tests.test_context_probe`: 14 tests for the inventory and the Codex probe. They
|
|
93
|
+
cover the pointer layout (`CLAUDE.md` with `@AGENTS.md`, `GEMINI.md` with
|
|
94
|
+
`@./AGENTS.md`) reported `CURRENT` without any write; Claude Code reading
|
|
95
|
+
`AGENTS.md` only while no `CLAUDE.md` or `CLAUDE.local.md` exists; byte-identical
|
|
96
|
+
copies, repeated lines with `file:line` locations and the 200-line guidance;
|
|
97
|
+
Cursor `.mdc` modes and an ignored plain `.md`; Copilot path-specific files; the
|
|
98
|
+
Gemini `context.fileName` list and `opencode.json` entries (relative, absolute,
|
|
99
|
+
empty, `~/` and globs, URLs never fetched); imports inside code ignored and import
|
|
100
|
+
loops stopped; `@~/` imports and user-level files; an unreadable file reported as a
|
|
101
|
+
finding; the goal pointer states; Codex truncation; an empty project. 14 of them
|
|
102
|
+
(with `tests.test_typed_decisions`, 22 in all) also passed on Python 3.11.14.
|
|
103
|
+
- A new `tests.test_shell_installer` case starts from a 2.4.1-style setup (a record
|
|
104
|
+
and a link for `nobrainer-codex-context`) and runs under `/bin/sh`, dash, bash in
|
|
105
|
+
POSIX mode, zsh emulating sh and with `install.py`: undo removes all 18 links
|
|
106
|
+
including the dangling old one; apply removes the old link, links
|
|
107
|
+
`nobrainer-context` and records the 18 current names; an old link the record does
|
|
108
|
+
not list still stops apply with exit 3. A new `tests.test_installer` case checks
|
|
109
|
+
that a foreign folder at the old name survives `--recorded-retired`, and that the
|
|
110
|
+
exact old link needs `--migrate-legacy` or `--recorded-retired`.
|
|
111
|
+
- A new `tests.test_typed_decisions` case checks that `TYPESAFE_API_KEY` is not read
|
|
112
|
+
without `--key-env`, that only the named variable is read, and that the worker's
|
|
113
|
+
environment carries no credential.
|
|
114
|
+
- `scripts/build_plugin.py` built a 140-file ZIP with 18 skills, version 2.5.0 and
|
|
115
|
+
`skills/nobrainer-context/` (5 files). `claude plugin validate --strict` (Claude
|
|
116
|
+
Code 2.1.303) passed on the extracted copy, and no file in it reads
|
|
117
|
+
`TYPESAFE_API_KEY` implicitly.
|
|
118
|
+
- On this repository the inventory reports `ATTENTION`: `CLAUDE.md` has 205 lines
|
|
119
|
+
(over the 200-line guidance), `AGENTS.md` and `CLAUDE.md` are byte-identical
|
|
120
|
+
(a test requires the copy), and Copilot's agent surfaces load both, so 107 lines
|
|
121
|
+
reach Copilot twice. This is reported, not changed, in this release.
|
|
122
|
+
- `sh -n` and `dash -n` on `scripts/install.sh`, `shellcheck -S error`,
|
|
123
|
+
`python3 -m py_compile` on every script and test, `git diff --check` and a gitleaks
|
|
124
|
+
scan of the staged changes passed.
|
|
125
|
+
- The initial implementation review found no critical or safety finding; its two
|
|
126
|
+
probe crashes (an unreadable file, an absolute `opencode.json` entry), the missed
|
|
127
|
+
`@~/` imports and user-level locations, the changed `install.sh` error order and a
|
|
128
|
+
record not rewritten after a retire-only run were fixed and tested.
|
|
129
|
+
|
|
130
|
+
### Corrections after the eleven-finding review
|
|
131
|
+
|
|
132
|
+
The later review requested changes for installer races and rollback, hidden
|
|
133
|
+
retirement previews, incorrect or incomplete instruction discovery, JSONC parsing,
|
|
134
|
+
Codex configuration errors, a named credential remaining in the worker environment
|
|
135
|
+
and shifted duplicate-line locations. The corrections keep retirement claims until
|
|
136
|
+
the record is saved, restore them on failure, report broken discovery as attention,
|
|
137
|
+
and preserve the actual source locations. The migration regression also covers a
|
|
138
|
+
home path containing spaces and a run that only retires a recorded link. If claiming
|
|
139
|
+
a later retired link fails, earlier claims are restored before setup rollback.
|
|
140
|
+
JSONC parsing preserves string contents and rejects unterminated comments.
|
|
141
|
+
A follow-up review found two remaining defects, reproduced before correction:
|
|
142
|
+
shell restore could overwrite a concurrent destination, and imports from on-demand
|
|
143
|
+
instructions were counted at startup. Shell recovery now calls the existing native
|
|
144
|
+
no-replace rename helper; when Python or the native operation is unavailable, it
|
|
145
|
+
preserves the recovery claim and reports incomplete rollback instead of falling
|
|
146
|
+
back to an overwriting move. Normal installation still works without Python.
|
|
147
|
+
Imports retain their conditional scope recursively; a startup use takes precedence
|
|
148
|
+
when a file is also imported conditionally.
|
|
149
|
+
|
|
150
|
+
Fresh local verification of the corrections:
|
|
151
|
+
|
|
152
|
+
- 93 tests passed: `tests.test_context_probe` (22),
|
|
153
|
+
`tests.test_typed_decisions` (9), `tests.test_installer` (59), and three focused
|
|
154
|
+
shell cases for the restore race, spaced-home migration and no-Python install.
|
|
155
|
+
- The spaced-home migration case first failed in sh, dash, bash in POSIX mode
|
|
156
|
+
and zsh emulating sh, then passed in all four plus `install.py` after correction.
|
|
157
|
+
- Both structure validators, shell syntax/lint and a redacted scan of the candidate
|
|
158
|
+
diff passed. The 140-file plugin ZIP still has 18 modules, five context-module
|
|
159
|
+
files and no retired module; strict Claude plugin validation passed.
|
|
160
|
+
- The final full run executed 544 tests in 1081.229 seconds and returned exit 1
|
|
161
|
+
(two failures, five skips). Both failures came from an old extracted plugin in
|
|
162
|
+
the ignored backup directory: the curated-tree test found a second set of
|
|
163
|
+
modules, and archive acceptance copied it and failed the same check. The archive
|
|
164
|
+
child executed 544 tests in 521.629 seconds (one failure, six skips).
|
|
165
|
+
- The generated package was moved outside the checkout, preserving all 141 files;
|
|
166
|
+
SHA-256 manifests before and after matched. Only the two failed tests were rerun:
|
|
167
|
+
both passed, exit 0, in 396.922 seconds. This includes the archive acceptance
|
|
168
|
+
test's complete discovery run on the same 544-test source, with its recursion
|
|
169
|
+
guard enabled. No source changed between the failed run and this rerun.
|
|
170
|
+
- The final independent delta review returned `CLEAN` after both follow-up
|
|
171
|
+
corrections. The initial 531-test result above predates these corrections;
|
|
172
|
+
earlier process-control failures do not establish acceptance for them.
|
|
173
|
+
|
|
174
|
+
These checks prove the module's probe, the installer migration and the package
|
|
175
|
+
metadata locally. They do not prove that a live client follows the consolidated
|
|
176
|
+
instructions, a fresh marketplace import, publication or a performance gain.
|
|
177
|
+
|
|
178
|
+
### Further PR review corrections
|
|
179
|
+
|
|
180
|
+
The inventory now returns `NONE` when every discovered goal is complete, while
|
|
181
|
+
still reporting a pointer to a missing goal. With `--include-global`, Claude and
|
|
182
|
+
Gemini user-level imports enter the same recursive discovery, byte totals,
|
|
183
|
+
duplicate detection and goal-pointer scan as project imports. Claude's line
|
|
184
|
+
guidance applies only to directly discovered `CLAUDE.md` files, excluding
|
|
185
|
+
`AGENTS.md` fallbacks and `.claude/rules/*.md` rules.
|
|
186
|
+
|
|
187
|
+
The installer audit also reproduced a blocked recovery: a changed retired entry
|
|
188
|
+
was claimed, then another entry occupied its original path before restore.
|
|
189
|
+
Both installers now fail the run, restore earlier retirement claims and preserve
|
|
190
|
+
the blocked claim for recovery, rather than saving a record and reporting success.
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
# nobrainer-tech-flow 2.6.0: delegate aggressively, verify by risk
|
|
2
|
+
|
|
3
|
+
Release date: 2026-10-23.
|
|
4
|
+
|
|
5
|
+
This release changes workflow guidance and the update line of the instruction block.
|
|
6
|
+
The setup record and the module set (eighteen) do not change.
|
|
7
|
+
|
|
8
|
+
## What changes
|
|
9
|
+
|
|
10
|
+
- **Aggressive delegation as the default.** `skills/nobrainer-tech-flow/SKILL.md` now opens
|
|
11
|
+
substantial work with "Delegate aggressively": independent units run on parallel native
|
|
12
|
+
subagents through team execution, and MAIN integrates, verifies and refills slots.
|
|
13
|
+
`references/delivery.md` adds the reason (delegation is the default route to a faster
|
|
14
|
+
done), keeps only tiny, tightly coupled, gated or shared-state steps in MAIN, and sets a
|
|
15
|
+
cost rule: delegate a unit when parallel work shortens the time to done more than a
|
|
16
|
+
worker's start-up costs, send a short task packet rather than the whole conversation,
|
|
17
|
+
ask for a concise report, and give narrow, mechanical work to a cheaper model under the
|
|
18
|
+
host's policy. No model is named.
|
|
19
|
+
- **Resend only failed units.** When part of a batch fails, only the failed units go out
|
|
20
|
+
again with their new evidence; accepted units are not rerun.
|
|
21
|
+
- **Verification by blast radius.** `references/delivery.md` scales verification to how
|
|
22
|
+
risky and reversible a change is. Reversible, low-risk changes may proceed on green
|
|
23
|
+
automated tests, review and security checks. CI configuration, credentials,
|
|
24
|
+
security-sensitive paths, data migrations and irreversible effects need an independent
|
|
25
|
+
review and remain owner-gated. An agent's approval never counts as the owner's.
|
|
26
|
+
- **Two build rules.** `skills/nobrainer-build/SKILL.md`: before adding complexity for a
|
|
27
|
+
speculative race or security edge case, name the concrete failure, its likelihood and
|
|
28
|
+
the cost; and in user interfaces, taglines, helper text and secondary labels added to
|
|
29
|
+
explain a screen count as slop, so the layout gets fixed instead.
|
|
30
|
+
|
|
31
|
+
## Daily updates by default, in one line
|
|
32
|
+
|
|
33
|
+
The managed instruction block now carries one short update line, on by default for new
|
|
34
|
+
setups: "Once a day on first use, update nobrainer-tech-flow to its latest verified stable
|
|
35
|
+
release from the canonical source, with a backup; change nothing else and ask if unsure."
|
|
36
|
+
`install_personalization.py --no-auto-update` writes the one-line opt-out instead ("tell
|
|
37
|
+
the owner when a newer stable nobrainer-tech-flow release exists; do not update it
|
|
38
|
+
yourself"); `--auto-update` stays accepted and means the default. With `--keep-options`
|
|
39
|
+
(which `install.py` and the guided setup always pass) the longer lines written before 2.6.0
|
|
40
|
+
become the matching short line: an old update grant stays a grant and the old notify-only
|
|
41
|
+
default stays notify-only, so no existing setup starts updating itself without a choice.
|
|
42
|
+
An update line that is neither recognized grant, for example one edited by hand, becomes
|
|
43
|
+
the notify-only line. `install.sh` follows the same rule when it refreshes an earlier block:
|
|
44
|
+
it rewrites the block in this version's text but keeps notifying unless the block held the
|
|
45
|
+
update line as its own line.
|
|
46
|
+
|
|
47
|
+
## Sources
|
|
48
|
+
|
|
49
|
+
The delegation rule is an owner decision (2026-10-23). The other rules were drawn from the
|
|
50
|
+
owner's recent X bookmarks and checked against the replies under each post; ideas that the
|
|
51
|
+
replies credibly disputed (a "canary" line to detect context decay, a viral prompt with a
|
|
52
|
+
false attribution) were left out.
|
|
53
|
+
|
|
54
|
+
## Verification record
|
|
55
|
+
|
|
56
|
+
Local checks (macOS, Python 3.14.5):
|
|
57
|
+
|
|
58
|
+
- `python3 scripts/validate_skills.py` and `python3 scripts/validate_skills.py --suite`: OK.
|
|
59
|
+
- `skills/nobrainer-tech-flow/SKILL.md` stays within the suite budget (239 lines, 1,749
|
|
60
|
+
words; limits 240 and 1,750).
|
|
61
|
+
- `python3 -m unittest tests.test_suite tests.test_delegation_contract
|
|
62
|
+
tests.test_visible_session_rule`: 81 tests OK.
|
|
63
|
+
- `python3 -m unittest tests.test_shell_installer tests.test_personalization
|
|
64
|
+
tests.test_one_command_installer tests.test_guided_onboarding`: OK, including the new
|
|
65
|
+
cases for the default update line, the opt-out, pre-2.6 blocks, edited or unknown update
|
|
66
|
+
lines and preferences that quote the update wording.
|
|
67
|
+
- `sh -n`, `dash -n` and `shellcheck -S error` on `scripts/install.sh`: clean.
|
|
68
|
+
- `git diff --check`: clean.
|
|
69
|
+
- An independent read-only review found four issues in the update-line handling and its
|
|
70
|
+
documentation (an unrecognized notify-only line could turn into an update grant); all
|
|
71
|
+
were fixed and a second review pass confirmed the fixes.
|
|
72
|
+
|
|
73
|
+
The full suite runs in the Validate workflow for the tagged commit.
|
package/gemini-extension.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nobrainer-tech-flow",
|
|
3
3
|
"description": "From task to done. nobrainer-tech-flow is one workflow of 18 modules for AI coding agents: it scopes the task, delegates ready work, checks the result and hands over the evidence, including what was not checked.",
|
|
4
|
-
"version": "2.
|
|
4
|
+
"version": "2.6.0",
|
|
5
5
|
"contextFileName": "GEMINI.md"
|
|
6
6
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nobrainer-tech-flow",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.6.0",
|
|
4
4
|
"description": "From task to done. nobrainer-tech-flow is one workflow of 18 modules for AI coding agents: it scopes the task, delegates ready work, checks the result and hands over the evidence, including what was not checked.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": ".opencode/plugins/nobrainer-tech-skills.js",
|
package/plugin.json
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"$schema": "https://agent-plugins.org/schemas/1.0.0/plugin.schema.json",
|
|
3
3
|
"name": "nobrainer-tech-flow",
|
|
4
4
|
"description": "From task to done. nobrainer-tech-flow is one workflow of 18 modules for AI coding agents: it scopes the task, delegates ready work, checks the result and hands over the evidence, including what was not checked.",
|
|
5
|
-
"version": "2.
|
|
5
|
+
"version": "2.6.0",
|
|
6
6
|
"author": {
|
|
7
7
|
"name": "NoBrainer Tech",
|
|
8
8
|
"url": "https://nobrainer.tech"
|
package/scripts/install.py
CHANGED
|
@@ -4,7 +4,9 @@
|
|
|
4
4
|
Every run is a dry run until --apply. The skills are linked and the managed
|
|
5
5
|
instruction block is written by the same helpers as the manual and guided setups,
|
|
6
6
|
and --undo uses the guided setup's rollback state (as scripts/install.sh does), so
|
|
7
|
-
every path reverses the same way.
|
|
7
|
+
every path reverses the same way. The only standing authorization it writes is the
|
|
8
|
+
default daily update of Flow itself, and an existing block keeps notifying unless it
|
|
9
|
+
already held that update line.
|
|
8
10
|
"""
|
|
9
11
|
|
|
10
12
|
from __future__ import annotations
|
|
@@ -248,11 +250,12 @@ def symlink_help(where: Path | None = None) -> str:
|
|
|
248
250
|
)
|
|
249
251
|
|
|
250
252
|
|
|
251
|
-
def plan_skills(ctx: Context) -> tuple[int, int]:
|
|
252
|
-
"""Dry-run the skill install: (skills to link, skills already linked)."""
|
|
253
|
+
def plan_skills(ctx: Context) -> tuple[int, int, list[str]]:
|
|
254
|
+
"""Dry-run the skill install: (skills to link, skills already linked, retired links due to go)."""
|
|
253
255
|
|
|
254
256
|
code, out, err = run(
|
|
255
|
-
[sys.executable, str(INSTALL_SKILLS), "--client", ctx.client, "--dest", str(ctx.skills)
|
|
257
|
+
[sys.executable, str(INSTALL_SKILLS), "--client", ctx.client, "--dest", str(ctx.skills),
|
|
258
|
+
*ctx.guided.recorded_retired_args(read_record(ctx))]
|
|
256
259
|
)
|
|
257
260
|
if code:
|
|
258
261
|
hint = None
|
|
@@ -271,7 +274,8 @@ def plan_skills(ctx: Context) -> tuple[int, int]:
|
|
|
271
274
|
if to_link and not symlinks_available():
|
|
272
275
|
print(symlink_help(), file=sys.stderr)
|
|
273
276
|
raise Refused(2)
|
|
274
|
-
|
|
277
|
+
retired = [line.split(": ", 1)[1] for line in out.splitlines() if line.startswith("RETIRED_RECORDED: ")]
|
|
278
|
+
return to_link, actions.count("KEEP"), retired
|
|
275
279
|
|
|
276
280
|
|
|
277
281
|
def plan_instructions(ctx: Context) -> list[str]:
|
|
@@ -361,7 +365,7 @@ def unrecorded_path(ctx: Context) -> Path | None:
|
|
|
361
365
|
|
|
362
366
|
|
|
363
367
|
def install(ctx: Context) -> int:
|
|
364
|
-
to_link, kept = plan_skills(ctx)
|
|
368
|
+
to_link, kept, retired = plan_skills(ctx)
|
|
365
369
|
instructions = plan_instructions(ctx)
|
|
366
370
|
# The guided setup's own dry run checks the recorded setup, the paths and the
|
|
367
371
|
# target, so the preview refuses whatever --apply would refuse.
|
|
@@ -371,6 +375,8 @@ def install(ctx: Context) -> int:
|
|
|
371
375
|
if not ctx.apply:
|
|
372
376
|
print(f"{source_line()} for {ctx.label}")
|
|
373
377
|
print(f"SKILLS: {to_link} to link into {ctx.skills} ({kept} already linked)")
|
|
378
|
+
for line in retired:
|
|
379
|
+
print(f"REMOVE_RETIRED: {line}")
|
|
374
380
|
for line in unique(instructions):
|
|
375
381
|
print(line)
|
|
376
382
|
note = ctx.variable_note()
|
|
@@ -394,12 +400,15 @@ def install(ctx: Context) -> int:
|
|
|
394
400
|
# New links and a written instruction file are what a client has to be restarted for.
|
|
395
401
|
# The personalization helper prints APPLIED only for a file it wrote.
|
|
396
402
|
written = re.search(r"^APPLIED: ", out, re.MULTILINE) is not None
|
|
397
|
-
|
|
403
|
+
removed_retired = re.findall(r"^REMOVED_RETIRED: (.+)$", out, re.MULTILINE)
|
|
404
|
+
changed = bool(to_link) or written or bool(removed_retired)
|
|
398
405
|
if changed:
|
|
399
406
|
print(f"INSTALLED: {source_line()} for {ctx.label}")
|
|
400
407
|
else:
|
|
401
408
|
print(f"UP TO DATE: {source_line()} is already installed for {ctx.label}; nothing changed")
|
|
402
409
|
print(f"SKILLS: {linked} linked in {ctx.skills} ({to_link} new)")
|
|
410
|
+
for target in removed_retired:
|
|
411
|
+
print(f"REMOVED_RETIRED: {target}")
|
|
403
412
|
if profile.get("target"):
|
|
404
413
|
backup = profile.get("backup")
|
|
405
414
|
if written and re.search(r"^UPDATE: ", out, re.MULTILINE):
|