instar 1.2.7 → 1.2.9
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/dist/cli.js +20 -2
- package/dist/cli.js.map +1 -1
- package/dist/commands/nuke.d.ts +28 -0
- package/dist/commands/nuke.d.ts.map +1 -1
- package/dist/commands/nuke.js +318 -0
- package/dist/commands/nuke.js.map +1 -1
- package/package.json +1 -1
- package/src/data/builtin-manifest.json +31 -31
- package/upgrades/1.2.8.md +69 -0
- package/upgrades/1.2.9.md +57 -0
- package/upgrades/side-effects/feat-nuke-here.md +123 -0
- package/upgrades/side-effects/fix-nuke-here-leftovers.md +98 -0
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
# Upgrade Guide — v1.2.8 (nuke --here for project-local installs)
|
|
2
|
+
|
|
3
|
+
<!-- bump: patch -->
|
|
4
|
+
<!-- patch = bug fixes, refactors, test additions, doc updates -->
|
|
5
|
+
|
|
6
|
+
## What Changed
|
|
7
|
+
|
|
8
|
+
**New: `instar nuke --here` removes a project-local install.**
|
|
9
|
+
|
|
10
|
+
`instar nuke <name>` has always handled standalone agents (the ones
|
|
11
|
+
at `~/.instar/agents/<name>/`). There was no equivalent for the
|
|
12
|
+
project-bound install method — the result of `npx instar setup`
|
|
13
|
+
inside a project directory. Removing one of those required a manual
|
|
14
|
+
multi-path `rm -rf` of `.instar/`, `.claude/` (or `.codex/`),
|
|
15
|
+
`.mcp.json`, and the identity-shadow files, plus the invisible parts:
|
|
16
|
+
the tmux server, the launchd plist, the agent-registry entry, the
|
|
17
|
+
secret backup.
|
|
18
|
+
|
|
19
|
+
`instar nuke --here` collapses that into one command. Run it inside
|
|
20
|
+
the project directory and it:
|
|
21
|
+
|
|
22
|
+
1. Stops the `<projectName>-server` tmux session and any spawned
|
|
23
|
+
`<projectName>-*` sessions.
|
|
24
|
+
2. Removes the launchd / systemd auto-start entry for that project.
|
|
25
|
+
3. Backs up secrets (Telegram token, dashboard PIN, etc.) so a
|
|
26
|
+
subsequent `npx instar setup` in the same directory auto-restores
|
|
27
|
+
them, identical to the standalone reinstall flow.
|
|
28
|
+
4. Unregisters the directory from the agent registry.
|
|
29
|
+
5. Removes filesystem artifacts:
|
|
30
|
+
- Always: `.instar/`, `.claude/`, `.codex/`, `.mcp.json`,
|
|
31
|
+
`instar.config.json`.
|
|
32
|
+
- For `CLAUDE.md`, `AGENTS.md`, `GEMINI.md`: git decides.
|
|
33
|
+
Tracked-clean → kept (pre-existing). Tracked-modified → restored
|
|
34
|
+
to `HEAD`. Untracked → deleted.
|
|
35
|
+
|
|
36
|
+
Safety:
|
|
37
|
+
- Refuses to run inside the instar source repo (checks `package.json`
|
|
38
|
+
name and `src/cli.ts` presence).
|
|
39
|
+
- Refuses to run when `.instar/config.json` is absent.
|
|
40
|
+
- Confirmation prompt by default; bypassed with `--yes`.
|
|
41
|
+
|
|
42
|
+
Spec: `specs/dev-infrastructure/nuke-here.md`.
|
|
43
|
+
ELI16: `specs/dev-infrastructure/nuke-here.eli16.md`.
|
|
44
|
+
Side-effects review: `upgrades/side-effects/feat-nuke-here.md`.
|
|
45
|
+
|
|
46
|
+
## What to Tell Your User
|
|
47
|
+
|
|
48
|
+
If you want to test installing instar a few different ways in a
|
|
49
|
+
project directory, there is now a built-in uninstall mode that runs
|
|
50
|
+
inside the project. It tears down everything instar installed in one
|
|
51
|
+
shot. Files you had committed before the install are kept (or
|
|
52
|
+
restored from git HEAD), so it is safe to run on a repo that already
|
|
53
|
+
had its own identity-shadow files.
|
|
54
|
+
|
|
55
|
+
## Summary of New Capabilities
|
|
56
|
+
|
|
57
|
+
- New CLI mode: `instar nuke --here` (project-local install teardown).
|
|
58
|
+
- Standalone form `instar nuke <name>` unchanged.
|
|
59
|
+
|
|
60
|
+
## Evidence
|
|
61
|
+
|
|
62
|
+
14 new unit tests in `tests/unit/nuke-here.test.ts` cover the source-
|
|
63
|
+
repo refusal check (four cases), the shadow-file classifier (four
|
|
64
|
+
cases of pre-existing-vs-instar-added-vs-untracked-vs-modified), and
|
|
65
|
+
the end-to-end filesystem teardown against tmpdirs (six cases
|
|
66
|
+
including the missing-config refusal path). All pass locally and in CI.
|
|
67
|
+
|
|
68
|
+
Manual end-to-end verification will run against the `instar-codey`
|
|
69
|
+
test clone after publish.
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
# Upgrade Guide — v1.2.9 (nuke --here leftover-artifact fixes)
|
|
2
|
+
|
|
3
|
+
<!-- bump: patch -->
|
|
4
|
+
<!-- patch = bug fixes, refactors, test additions, doc updates -->
|
|
5
|
+
|
|
6
|
+
## What Changed
|
|
7
|
+
|
|
8
|
+
**Fix: `nuke --here` now leaves no leftovers.**
|
|
9
|
+
|
|
10
|
+
End-to-end testing of the v1.2.8 nuke --here flow on a fresh project
|
|
11
|
+
turned up two artifacts the teardown forgot:
|
|
12
|
+
|
|
13
|
+
1. The `.gitignore` instar writes during install was orphaned after
|
|
14
|
+
nuke. Fixed by routing it through the existing identity-shadow
|
|
15
|
+
classifier (tracked-clean keep, tracked-modified restore,
|
|
16
|
+
untracked delete) — same rule we already apply to the identity
|
|
17
|
+
shadow files.
|
|
18
|
+
|
|
19
|
+
2. The `.instar/` directory ghost-revived itself after delete. The
|
|
20
|
+
SafeFsExecutor and SafeGitExecutor audit log lives at
|
|
21
|
+
`.instar/audit/destructive-ops.jsonl`. When `.instar/` was deleted
|
|
22
|
+
early in teardown, every subsequent destructive op wrote an audit
|
|
23
|
+
entry into a freshly-recreated `.instar/audit/`. Fix: reorder
|
|
24
|
+
teardown so `.instar/` is last, and suppress audit logging for
|
|
25
|
+
that single delete via the existing `INSTAR_AUDIT_LOG_DISABLED`
|
|
26
|
+
env contract. The agent dir is going away in the same breath, so
|
|
27
|
+
the suppressed entry has no downstream consumer.
|
|
28
|
+
|
|
29
|
+
Three new unit tests pin the corrected behavior end-to-end against
|
|
30
|
+
tmpdirs: instar-created `.gitignore` is deleted, pre-existing
|
|
31
|
+
tracked `.gitignore` is preserved, and `.instar/` is fully absent
|
|
32
|
+
after nuke (no `audit/` carryover).
|
|
33
|
+
|
|
34
|
+
Spec: `specs/dev-infrastructure/nuke-here-leftovers.md`.
|
|
35
|
+
ELI16: `specs/dev-infrastructure/nuke-here-leftovers.eli16.md`.
|
|
36
|
+
Side-effects review: `upgrades/side-effects/fix-nuke-here-leftovers.md`.
|
|
37
|
+
|
|
38
|
+
## What to Tell Your User
|
|
39
|
+
|
|
40
|
+
Uninstall now actually leaves the project the way it was before
|
|
41
|
+
instar was installed. There is no orphaned per-machine ignores file
|
|
42
|
+
and no ghost configuration directory left behind. If you run the
|
|
43
|
+
install/uninstall/reinstall loop a dozen times in a row, each cycle
|
|
44
|
+
starts from the same clean state as the first.
|
|
45
|
+
|
|
46
|
+
## Summary of New Capabilities
|
|
47
|
+
|
|
48
|
+
No new capabilities. Behavior fix on top of v1.2.8.
|
|
49
|
+
|
|
50
|
+
## Evidence
|
|
51
|
+
|
|
52
|
+
Reproduction prior: ran `npx instar@1.2.8 init <name> --framework
|
|
53
|
+
codex-cli` followed by `npx instar@1.2.8 nuke --here --yes`. On-disk
|
|
54
|
+
state after nuke: `.gitignore` present with instar's per-machine
|
|
55
|
+
ignores; `.instar/` present containing
|
|
56
|
+
`audit/destructive-ops.jsonl`. Three explicit unit tests now cover
|
|
57
|
+
both observations and fail on v1.2.8, pass on v1.2.9.
|
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
# Side-effects review — `instar nuke --here`
|
|
2
|
+
|
|
3
|
+
Per L6. Seven dimensions.
|
|
4
|
+
|
|
5
|
+
## 1. Over-block / under-block
|
|
6
|
+
|
|
7
|
+
Before: UNDER — project-bound installs had no uninstall command at all;
|
|
8
|
+
operators had to manually `rm -rf` the install artifacts (and forget the
|
|
9
|
+
tmux server / launchd plist / registry entry / secret backup).
|
|
10
|
+
|
|
11
|
+
After: precisely targeted. The new mode requires explicit `--here`, runs
|
|
12
|
+
only when `.instar/config.json` exists in the target dir, and refuses
|
|
13
|
+
to run inside the instar source repo. No over-block: the standalone
|
|
14
|
+
form is unchanged, and operators who never pass `--here` see no
|
|
15
|
+
behavior change.
|
|
16
|
+
|
|
17
|
+
## 2. Level-of-abstraction fit
|
|
18
|
+
|
|
19
|
+
`nukeHere(options)` is a sibling function to the existing `nukeAgent`
|
|
20
|
+
in the same file. Both share the same Step 1-4 shape (tmux teardown,
|
|
21
|
+
auto-start removal, secret backup, registry unregister) and the same
|
|
22
|
+
SafeFsExecutor / SafeGitExecutor helpers for the filesystem half. The
|
|
23
|
+
new git-tracked-vs-untracked decision for identity-shadow files
|
|
24
|
+
delegates to `git ls-files --error-unmatch` + `git status --porcelain`
|
|
25
|
+
— the existing single source of truth for tracking state. No new
|
|
26
|
+
abstraction layer.
|
|
27
|
+
|
|
28
|
+
## 3. Signal vs Authority compliance
|
|
29
|
+
|
|
30
|
+
- The `--here` flag is the operator-intent SIGNAL.
|
|
31
|
+
- `.instar/config.json` presence is the AUTHORITY for "is there an
|
|
32
|
+
install here to remove."
|
|
33
|
+
- `package.json` `name === "instar"` + `src/cli.ts` presence is the
|
|
34
|
+
AUTHORITY for "is this the instar source repo (refuse)."
|
|
35
|
+
- For identity-shadow files (`CLAUDE.md`, `AGENTS.md`, `GEMINI.md`):
|
|
36
|
+
- `git ls-files --error-unmatch <file>` is the AUTHORITY for
|
|
37
|
+
"tracked at HEAD."
|
|
38
|
+
- `git status --porcelain <file>` is the AUTHORITY for "has working-
|
|
39
|
+
tree diff."
|
|
40
|
+
No new heuristic is invented; existing git tooling is the single
|
|
41
|
+
source of truth.
|
|
42
|
+
|
|
43
|
+
## 4. Interactions with adjacent systems
|
|
44
|
+
|
|
45
|
+
- **Standalone `nuke <name>`** — unchanged. Same function, same flags,
|
|
46
|
+
same prompts. The CLI route was changed from `nuke <name>` (required)
|
|
47
|
+
to `nuke [name]` (optional) plus a `--here` flag — when `--here` is
|
|
48
|
+
set, the positional is ignored; when `--here` is not set and no name
|
|
49
|
+
is given, usage is printed and the command exits 1.
|
|
50
|
+
|
|
51
|
+
- **`uninstallAutoStart(projectName)`** in `src/commands/setup.ts` —
|
|
52
|
+
reused as-is. The function is already idempotent and project-name-
|
|
53
|
+
scoped; the new mode hands it the same `projectName` the install
|
|
54
|
+
wrote into `.instar/config.json`.
|
|
55
|
+
|
|
56
|
+
- **`SecretManager.backupFromConfig`** — reused exactly as
|
|
57
|
+
`nukeAgent` does, with the same field mapping (Telegram token, chat
|
|
58
|
+
id, authToken, dashboardPin, tunnel token). This means a subsequent
|
|
59
|
+
`npx instar setup` in the same directory will auto-restore secrets,
|
|
60
|
+
matching the standalone reinstall flow.
|
|
61
|
+
|
|
62
|
+
- **`unregisterAgent(dir)`** — reused. Operates on the absolute
|
|
63
|
+
directory path, identical contract.
|
|
64
|
+
|
|
65
|
+
- **`SafeFsExecutor.safeRmSync`** — used for every delete. The recent
|
|
66
|
+
source-tree-guard carve-out (PR #294) for `<root>/.instar/` runtime
|
|
67
|
+
artifacts means `.instar/` deletions inside an agent's project dir
|
|
68
|
+
do not trip the guard.
|
|
69
|
+
|
|
70
|
+
- **`SafeGitExecutor`** — used for `ls-files`, `status`, and
|
|
71
|
+
`checkout HEAD --`. All three are already allow-listed git ops; the
|
|
72
|
+
audit trail records the new operations under
|
|
73
|
+
`src/commands/nuke.ts:nukeHere-*`.
|
|
74
|
+
|
|
75
|
+
- **Tmux session naming** (`<projectName>-server`, `<projectName>-*`) —
|
|
76
|
+
identical to `nukeAgent`. The new function uses the same
|
|
77
|
+
`isTmuxSessionRunning` helper that already exists in the file.
|
|
78
|
+
|
|
79
|
+
## 5. Rollback cost
|
|
80
|
+
|
|
81
|
+
Trivial. One new exported function in `src/commands/nuke.ts`, one
|
|
82
|
+
modified CLI registration in `src/cli.ts`, one unit test, one ELI16
|
|
83
|
+
+ spec + this artifact. `git revert` restores the prior CLI surface;
|
|
84
|
+
no other surface depends on `--here`. Standalone nuke users see no
|
|
85
|
+
change either way.
|
|
86
|
+
|
|
87
|
+
## 6. Backwards compatibility / drift surface
|
|
88
|
+
|
|
89
|
+
Fully backwards-compatible.
|
|
90
|
+
|
|
91
|
+
- `instar nuke <name>` still works (positional became optional, but
|
|
92
|
+
passing a name still routes to `nukeAgent`).
|
|
93
|
+
- `instar nuke` with no arguments now prints usage and exits 1 —
|
|
94
|
+
before, commander would error out with a "missing required argument"
|
|
95
|
+
message. Same exit-1 outcome, slightly clearer error.
|
|
96
|
+
- `instar nuke --here` is a new code path; no prior agent has it, so
|
|
97
|
+
there's nothing to drift against.
|
|
98
|
+
- No config file changes, no template changes, no hook changes, no
|
|
99
|
+
built-in skill changes — therefore no `PostUpdateMigrator` work
|
|
100
|
+
needed (Migration Parity Standard not triggered: this is a CLI-only
|
|
101
|
+
surface change, not an agent-installed-files change).
|
|
102
|
+
|
|
103
|
+
## 7. Authorization / Trust posture
|
|
104
|
+
|
|
105
|
+
No new authority. The command only acts on:
|
|
106
|
+
|
|
107
|
+
- The current working directory (or `--dir` override) — same scope as
|
|
108
|
+
every other instar CLI command that takes a `--dir` flag.
|
|
109
|
+
- The launchd plist / agent registry entry / secret store keyed to
|
|
110
|
+
the **projectName the install itself wrote**. The command cannot
|
|
111
|
+
delete data belonging to a different project name; it reads
|
|
112
|
+
`projectName` from `.instar/config.json` in the target dir.
|
|
113
|
+
|
|
114
|
+
The source-repo refusal check is an additional safety floor that
|
|
115
|
+
exists only to protect the instar development checkout — a one-way
|
|
116
|
+
guardrail with no positive authority.
|
|
117
|
+
|
|
118
|
+
## Outcome
|
|
119
|
+
|
|
120
|
+
Ship. Closes the project-local uninstall gap, matches the standalone
|
|
121
|
+
flow's safety posture, no new authority, no migration work, and
|
|
122
|
+
removes the manual-rm-rf trap operators hit today during install
|
|
123
|
+
testing.
|
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
# Side-effects review — Nuke --here leftover-artifact fixes
|
|
2
|
+
|
|
3
|
+
Per L6. Seven dimensions.
|
|
4
|
+
|
|
5
|
+
## 1. Over-block / under-block
|
|
6
|
+
|
|
7
|
+
Before: UNDER on two specific paths.
|
|
8
|
+
- `.gitignore` survived nuke entirely (orphaned instar artifact).
|
|
9
|
+
- `.instar/` resurrected itself via audit-log writes immediately after
|
|
10
|
+
delete, leaving an empty `.instar/audit/` directory behind.
|
|
11
|
+
|
|
12
|
+
After: precisely targeted. `.gitignore` joins the existing identity-
|
|
13
|
+
shadow classifier (same three-way disposition: keep / restore /
|
|
14
|
+
delete). `.instar/` is now the last destructive op, with audit logging
|
|
15
|
+
suppressed for that single call so it doesn't recreate itself. No
|
|
16
|
+
over-block: the keep-pre-existing-`.gitignore` path means a project
|
|
17
|
+
that had its own `.gitignore` before instar was installed gets that
|
|
18
|
+
file preserved.
|
|
19
|
+
|
|
20
|
+
## 2. Level-of-abstraction fit
|
|
21
|
+
|
|
22
|
+
Fix 1 adds one string to an existing array
|
|
23
|
+
(`PROJECT_LOCAL_IDENTITY_SHADOWS`); no new classifier, no new
|
|
24
|
+
disposition. The existing `classifyShadowFile` already handles
|
|
25
|
+
`.gitignore` correctly.
|
|
26
|
+
|
|
27
|
+
Fix 2 partitions an existing array (`PROJECT_LOCAL_ALWAYS_REMOVE`)
|
|
28
|
+
into "everything except `.instar`" and "`.instar`". The audit
|
|
29
|
+
suppression uses an existing public env var
|
|
30
|
+
(`INSTAR_AUDIT_LOG_DISABLED`) documented in
|
|
31
|
+
`src/core/SafeGitExecutor.ts:auditLogPath`. No new authority, no new
|
|
32
|
+
API surface.
|
|
33
|
+
|
|
34
|
+
## 3. Signal vs Authority compliance
|
|
35
|
+
|
|
36
|
+
- The git-tracked-vs-untracked decision for `.gitignore` delegates
|
|
37
|
+
exactly as it does for other shadow files: `git ls-files
|
|
38
|
+
--error-unmatch` + `git status --porcelain` are the AUTHORITY.
|
|
39
|
+
- The audit-log suppression honors the existing
|
|
40
|
+
`INSTAR_AUDIT_LOG_DISABLED` env contract — the env var IS the
|
|
41
|
+
documented signal for "skip audit." No new signal invented.
|
|
42
|
+
|
|
43
|
+
## 4. Interactions with adjacent systems
|
|
44
|
+
|
|
45
|
+
- **`SafeFsExecutor.safeRmSync` / `SafeGitExecutor.execSync` audit
|
|
46
|
+
paths** — unchanged. They continue to write to
|
|
47
|
+
`<cwd>/.instar/audit/destructive-ops.jsonl` whenever
|
|
48
|
+
`INSTAR_AUDIT_LOG_DISABLED` is not set. The only suppression is
|
|
49
|
+
inside `nukeHere`, around the final `.instar` delete, and is
|
|
50
|
+
scoped to that single op.
|
|
51
|
+
|
|
52
|
+
- **`classifyShadowFile` callers** — none other than `nukeHere`. The
|
|
53
|
+
function's signature is unchanged.
|
|
54
|
+
|
|
55
|
+
- **Other CLI commands that touch `.gitignore`** — `instar init`
|
|
56
|
+
writes it, `instar setup` does not touch it. No reader of
|
|
57
|
+
`.gitignore` depends on it being absent. Removing it during nuke
|
|
58
|
+
has no cascading effect.
|
|
59
|
+
|
|
60
|
+
- **Reinstall flow** — `instar init` regenerates `.gitignore` from
|
|
61
|
+
scratch. The fix re-aligns the install/uninstall contract:
|
|
62
|
+
whatever `init` writes, `nuke --here` removes.
|
|
63
|
+
|
|
64
|
+
## 5. Rollback cost
|
|
65
|
+
|
|
66
|
+
Trivial. One array-element addition and one reorder + env-var
|
|
67
|
+
suppress block in `src/commands/nuke.ts`. Three new unit tests.
|
|
68
|
+
`git revert` restores the prior leaky behavior.
|
|
69
|
+
|
|
70
|
+
## 6. Backwards compatibility / drift surface
|
|
71
|
+
|
|
72
|
+
Fully backwards-compatible.
|
|
73
|
+
|
|
74
|
+
- `nuke <name>` (standalone form) untouched.
|
|
75
|
+
- `nuke --here` consumers see strictly more-correct behavior: no
|
|
76
|
+
orphaned `.gitignore`, no ghost `.instar/`.
|
|
77
|
+
- A project that had `.gitignore` tracked in git before instar was
|
|
78
|
+
installed gets it preserved (the new identity-shadow rule) —
|
|
79
|
+
strictly better than the v1.2.8 behavior of leaving instar's
|
|
80
|
+
rewritten version behind. No legitimate caller depends on the
|
|
81
|
+
buggy v1.2.8 leftover state.
|
|
82
|
+
- No config changes, no template changes, no hook changes, no
|
|
83
|
+
migration work needed (CLI-only surface).
|
|
84
|
+
|
|
85
|
+
## 7. Authorization / Trust posture
|
|
86
|
+
|
|
87
|
+
No new authority. The audit-log suppression is scoped to one syscall
|
|
88
|
+
inside one function; the env var is restored in a `finally` block so
|
|
89
|
+
the rest of the process retains the prior audit-log state. The
|
|
90
|
+
shadow classifier already delegates the keep/restore/delete decision
|
|
91
|
+
to git, not to instar.
|
|
92
|
+
|
|
93
|
+
## Outcome
|
|
94
|
+
|
|
95
|
+
Ship. Closes the two leftover-artifact failure modes uncovered by
|
|
96
|
+
end-to-end testing on `instar-codey`. Three unit tests pin the
|
|
97
|
+
corrected behavior. The fix exercises only existing primitives;
|
|
98
|
+
zero new abstraction surface.
|