@integrity-labs/agt-cli 0.28.839 → 0.28.841
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/assets/review/SKILL.md +198 -0
- package/dist/assets/review/post-review-findings.mjs +5 -1
- package/dist/bin/agt.js +5 -5
- package/dist/{chunk-V2JMDOOU.js → chunk-43P6SG7L.js} +4 -4
- package/dist/{chunk-W4KAZQBS.js → chunk-CFLYGZOF.js} +2 -2
- package/dist/{chunk-DUOFKTAD.js → chunk-XBLODN73.js} +17 -11
- package/dist/chunk-XBLODN73.js.map +1 -0
- package/dist/{claude-pair-runtime-A52UZQ6V.js → claude-pair-runtime-XC3AQA4L.js} +2 -2
- package/dist/lib/manager-worker.js +33 -13
- package/dist/lib/manager-worker.js.map +1 -1
- package/dist/mcp/direct-chat-channel.js +752 -635
- package/dist/{persistent-session-N6FIS7UY.js → persistent-session-WLP5YTO2.js} +3 -3
- package/dist/{responsiveness-probe-OBQCSEFT.js → responsiveness-probe-7RYNNHKC.js} +3 -3
- package/dist/{session-auth-dead-LIPEYPBX.js → session-auth-dead-X6B6C3BR.js} +2 -2
- package/package.json +2 -2
- package/dist/chunk-DUOFKTAD.js.map +0 -1
- /package/dist/{chunk-V2JMDOOU.js.map → chunk-43P6SG7L.js.map} +0 -0
- /package/dist/{chunk-W4KAZQBS.js.map → chunk-CFLYGZOF.js.map} +0 -0
- /package/dist/{claude-pair-runtime-A52UZQ6V.js.map → claude-pair-runtime-XC3AQA4L.js.map} +0 -0
- /package/dist/{persistent-session-N6FIS7UY.js.map → persistent-session-WLP5YTO2.js.map} +0 -0
- /package/dist/{responsiveness-probe-OBQCSEFT.js.map → responsiveness-probe-7RYNNHKC.js.map} +0 -0
- /package/dist/{session-auth-dead-LIPEYPBX.js.map → session-auth-dead-X6B6C3BR.js.map} +0 -0
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: pr-review
|
|
3
|
+
description: Review a GitHub pull request's diff and write the findings to a JSON artefact. Use when asked to review a PR, or when a card asks you to review a repo's pull request. Produces the artefact only — it never posts to GitHub.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Reviewing a pull request
|
|
7
|
+
|
|
8
|
+
You are a Ninjafy agent (Ninjafy and Augmented Team are one platform, so you
|
|
9
|
+
answer to the old name too). This skill is how you review a pull request.
|
|
10
|
+
|
|
11
|
+
**You write a file. You post nothing.** Posting is a separate, gated step that
|
|
12
|
+
reads the file this skill produces. Producing the artefact and publishing it are
|
|
13
|
+
deliberately different actions, so a review can be made and read before anybody
|
|
14
|
+
decides it should appear on the PR.
|
|
15
|
+
|
|
16
|
+
You do **not** need a checkout. Everything below comes from the GitHub API via
|
|
17
|
+
`gh`, which is already on your PATH and already authenticated.
|
|
18
|
+
|
|
19
|
+
---
|
|
20
|
+
|
|
21
|
+
## 1. Resolve the PR
|
|
22
|
+
|
|
23
|
+
You need the repository as `owner/name` and the PR number. If you were given
|
|
24
|
+
only a URL, read them off it.
|
|
25
|
+
|
|
26
|
+
```bash
|
|
27
|
+
gh api repos/OWNER/NAME/pulls/NUMBER
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
From the response take `number`, `title`, `state`, `head.sha` and `base.sha`.
|
|
31
|
+
|
|
32
|
+
- **`state` is not `open`** — say so and stop. Reviewing a closed chapter helps
|
|
33
|
+
nobody.
|
|
34
|
+
- **The call fails** — say so and stop. Do not review from memory of the repo.
|
|
35
|
+
|
|
36
|
+
`head.sha` is the commit you are reviewing. Every later step is pinned to it,
|
|
37
|
+
and it is part of the artefact's filename, because a review of one commit says
|
|
38
|
+
nothing about another.
|
|
39
|
+
|
|
40
|
+
## 2. Get the diff — from the API, not from a working tree
|
|
41
|
+
|
|
42
|
+
```bash
|
|
43
|
+
gh api repos/OWNER/NAME/pulls/NUMBER/files --paginate --slurp
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
Each entry has `filename`, `status`, `patch` (a unified diff hunk) and the
|
|
47
|
+
change counts. Read the patches; that is the change.
|
|
48
|
+
|
|
49
|
+
**Use this endpoint and no other.** The step that posts findings anchors each
|
|
50
|
+
one to a line it computes from *these same patches* — the right-hand side of
|
|
51
|
+
each hunk, which is the only place GitHub accepts an inline comment. A line
|
|
52
|
+
number taken from anywhere else (a local `git diff`, a whole-file read, a
|
|
53
|
+
`compare` against a different base) can be perfectly correct about the code and
|
|
54
|
+
still unanchorable, and an unanchorable finding is quietly demoted out of the
|
|
55
|
+
place a reader would look for it.
|
|
56
|
+
|
|
57
|
+
Some entries have **no `patch`** — a binary file, or one too large for GitHub to
|
|
58
|
+
render. Do not guess at their contents. Either fetch the file if you need it, or
|
|
59
|
+
leave it unreviewed and say which files you skipped.
|
|
60
|
+
|
|
61
|
+
### Then check the PR has not moved under you
|
|
62
|
+
|
|
63
|
+
This endpoint returns the diff **as it is now**, not the diff at the `head.sha`
|
|
64
|
+
you read in step 1. If someone pushed while you were reading, you now hold one
|
|
65
|
+
commit's diff about to be filed under another commit's name.
|
|
66
|
+
|
|
67
|
+
So read the head again and compare:
|
|
68
|
+
|
|
69
|
+
```bash
|
|
70
|
+
gh api repos/OWNER/NAME/pulls/NUMBER --jq .head.sha
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
- **Same as step 1** — carry on.
|
|
74
|
+
- **Different** — start again from step 1 against the new head. If it moves a
|
|
75
|
+
second time, stop and write an `incomplete` artefact saying the PR is moving
|
|
76
|
+
faster than you can read it.
|
|
77
|
+
|
|
78
|
+
Do not simply relabel what you already read with the newer sha. That is the
|
|
79
|
+
failure this check exists to prevent, not a way around it: the artefact would be
|
|
80
|
+
a review of code nobody can see any more, indistinguishable from a review of the
|
|
81
|
+
code that is there.
|
|
82
|
+
|
|
83
|
+
## 3. Load the repo's own rules
|
|
84
|
+
|
|
85
|
+
```bash
|
|
86
|
+
gh api repos/OWNER/NAME/contents/CLAUDE.md?ref=HEAD_SHA --jq .content
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
```bash
|
|
90
|
+
gh api repos/OWNER/NAME/contents/docs/reference/review-rules.md?ref=HEAD_SHA --jq .content
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
Both are base64; decode them. Both may 404, which is fine and normal — most
|
|
94
|
+
repos have neither.
|
|
95
|
+
|
|
96
|
+
Where `review-rules.md` exists it **outranks your priors**: a rule saying "this
|
|
97
|
+
is deliberate here, do not flag it" exists because a reviewer already raised
|
|
98
|
+
that exact thing and a human said no. Where it does not exist, review anyway and
|
|
99
|
+
say so in your summary — a repo without one gets a generic review, which is
|
|
100
|
+
worth having and worth labelling as such.
|
|
101
|
+
|
|
102
|
+
Pin both reads to `HEAD_SHA`. Reading the default branch's rules against a
|
|
103
|
+
branch's code compares the change to something it was never written against.
|
|
104
|
+
|
|
105
|
+
## 4. Review
|
|
106
|
+
|
|
107
|
+
Prioritise, in this order:
|
|
108
|
+
|
|
109
|
+
1. **Correctness.** Does it do what it claims? What input makes it wrong?
|
|
110
|
+
|
|
111
|
+
2. **Claims that outrun the code.** A comment, commit message or PR body
|
|
112
|
+
asserting a guard, a threshold or a behaviour the code does not implement.
|
|
113
|
+
These are worse than a missing guard, because they stop the next person
|
|
114
|
+
looking. Read what the change *says about itself*, and check it.
|
|
115
|
+
|
|
116
|
+
3. **Silent failure.** A path where something goes wrong and nothing reports it:
|
|
117
|
+
a swallowed error, a fallback that renders a failed measurement as a
|
|
118
|
+
plausible normal value, an empty result indistinguishable from "nothing to
|
|
119
|
+
report". Ask of every failure branch: *if this fired right now, how would
|
|
120
|
+
anyone know?*
|
|
121
|
+
|
|
122
|
+
4. **Tests that cannot fail.** A test that looks correct and is structurally
|
|
123
|
+
incapable of failing reports coverage it does not provide, and CI will never
|
|
124
|
+
reveal it, because CI only ever runs it green.
|
|
125
|
+
|
|
126
|
+
5. **Security visible in the diff** — a new unauthenticated path, a secret on a
|
|
127
|
+
command line or in an environment variable, an unparameterised query, a taint
|
|
128
|
+
flow from request input to a sink.
|
|
129
|
+
|
|
130
|
+
**Do not spend the review on formatting, naming, or suggesting more cases for
|
|
131
|
+
behaviour already covered.** A review that is 80% nits gets skimmed, and then
|
|
132
|
+
the one real finding in it gets skimmed too.
|
|
133
|
+
|
|
134
|
+
## 5. Say which of the three outcomes you reached
|
|
135
|
+
|
|
136
|
+
They are different states and reporting them identically is the failure this
|
|
137
|
+
skill exists to find in other people's code:
|
|
138
|
+
|
|
139
|
+
- You reviewed the diff and **found nothing**. A legitimate, useful result.
|
|
140
|
+
- You reviewed the diff and **found things**.
|
|
141
|
+
- You **could not finish** — the diff was too large to hold, a file had no
|
|
142
|
+
patch and you needed it, an API call failed. Say that. Never present a partial
|
|
143
|
+
read as a clean one.
|
|
144
|
+
|
|
145
|
+
## 6. Write the artefact
|
|
146
|
+
|
|
147
|
+
One file per PR head, under `.smithers/review/` relative to your working
|
|
148
|
+
directory (create it if absent):
|
|
149
|
+
|
|
150
|
+
```text
|
|
151
|
+
.smithers/review/<pr>-<first 12 chars of head sha>.code.json
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
```json
|
|
155
|
+
{
|
|
156
|
+
"pr": 1234,
|
|
157
|
+
"head": "abc123def456",
|
|
158
|
+
"reviewedAt": "2026-09-07T00:00:00Z",
|
|
159
|
+
"rulesFile": "docs/reference/review-rules.md",
|
|
160
|
+
"status": "reviewed",
|
|
161
|
+
"findings": [
|
|
162
|
+
{
|
|
163
|
+
"file": "packages/api/src/routes/thing.ts",
|
|
164
|
+
"line": 42,
|
|
165
|
+
"severity": "major",
|
|
166
|
+
"category": "correctness",
|
|
167
|
+
"summary": "one sentence stating the defect",
|
|
168
|
+
"why": "the failing case, concretely: these inputs produce this wrong output"
|
|
169
|
+
}
|
|
170
|
+
]
|
|
171
|
+
}
|
|
172
|
+
```
|
|
173
|
+
|
|
174
|
+
**`severity` is `major` or `minor`. Nothing else.** Not `high`, not `critical`,
|
|
175
|
+
not `P1`. The step that posts these filters by severity, and it compares within
|
|
176
|
+
a known vocabulary: a token it does not recognise is kept rather than dropped,
|
|
177
|
+
so an invented level does not vanish — but it does defeat the filter, silently,
|
|
178
|
+
while the filter carries on printing as though it were working. `P1`/`P2`/`P3`
|
|
179
|
+
belong to the separate security review and are not yours to emit here.
|
|
180
|
+
|
|
181
|
+
`category` is one of `correctness`, `claim`, `silent-failure`, `test`,
|
|
182
|
+
`security`.
|
|
183
|
+
|
|
184
|
+
**`status` is `reviewed` or `incomplete`.** `incomplete` takes a `reason`. An
|
|
185
|
+
empty `findings` array on an `incomplete` review must never be read as clean,
|
|
186
|
+
and the posting step refuses to post from one at all — which is the whole point
|
|
187
|
+
of the field. Use it rather than shrinking the review to fit.
|
|
188
|
+
|
|
189
|
+
`line` is a right-hand line number from the patches you read in step 2. Omit it
|
|
190
|
+
if the finding is about the change as a whole rather than one line.
|
|
191
|
+
|
|
192
|
+
## 7. Report, and stop
|
|
193
|
+
|
|
194
|
+
Print counts by severity and category, the artefact path, and whether a rules
|
|
195
|
+
file was found. Then **stop**.
|
|
196
|
+
|
|
197
|
+
Do not post the findings. Do not open a review. Do not comment on the PR. If you
|
|
198
|
+
were asked to review, you have done what was asked.
|
|
@@ -103,7 +103,11 @@ export function buildBody(f, id) {
|
|
|
103
103
|
'',
|
|
104
104
|
f.why ?? f.attack ?? '',
|
|
105
105
|
'',
|
|
106
|
-
|
|
106
|
+
// NOT `/s:code-review`. That is an operator slash command in a Claude Code
|
|
107
|
+
// plugin the managed fleet never installs, so from the moment the `pr-review`
|
|
108
|
+
// skill became a second producer the footer named a thing most readers of it
|
|
109
|
+
// cannot run — a claim outrunning the code, on every comment this bot posts.
|
|
110
|
+
'<sub>Posted by the Obi Wan reviewer. This reviewer never submits a blocking verdict.',
|
|
107
111
|
'Reply if this is deliberate and it becomes a rule in `docs/reference/review-rules.md`.</sub>',
|
|
108
112
|
marker(id),
|
|
109
113
|
].join('\n');
|
package/dist/bin/agt.js
CHANGED
|
@@ -40,12 +40,12 @@ import {
|
|
|
40
40
|
success,
|
|
41
41
|
table,
|
|
42
42
|
warn
|
|
43
|
-
} from "../chunk-
|
|
43
|
+
} from "../chunk-43P6SG7L.js";
|
|
44
44
|
import {
|
|
45
45
|
getProjectDir,
|
|
46
46
|
isSessionResumeDisabled,
|
|
47
47
|
readDirectChatSessionState
|
|
48
|
-
} from "../chunk-
|
|
48
|
+
} from "../chunk-CFLYGZOF.js";
|
|
49
49
|
import {
|
|
50
50
|
AnchorSessionClient,
|
|
51
51
|
CHANNEL_REGISTRY,
|
|
@@ -79,7 +79,7 @@ import {
|
|
|
79
79
|
serializeManifestForSlackCli,
|
|
80
80
|
sessionFileExists,
|
|
81
81
|
sessionTranscriptDir
|
|
82
|
-
} from "../chunk-
|
|
82
|
+
} from "../chunk-XBLODN73.js";
|
|
83
83
|
import "../chunk-XWVM4KPK.js";
|
|
84
84
|
|
|
85
85
|
// src/bin/agt.ts
|
|
@@ -5467,7 +5467,7 @@ import { execFileSync, execSync } from "child_process";
|
|
|
5467
5467
|
import { existsSync as existsSync11, realpathSync as realpathSync2 } from "fs";
|
|
5468
5468
|
import chalk18 from "chalk";
|
|
5469
5469
|
import ora16 from "ora";
|
|
5470
|
-
var cliVersion = true ? "0.28.
|
|
5470
|
+
var cliVersion = true ? "0.28.841" : "dev";
|
|
5471
5471
|
async function fetchLatestVersion() {
|
|
5472
5472
|
const host2 = getHost();
|
|
5473
5473
|
if (!host2) return null;
|
|
@@ -6658,7 +6658,7 @@ function handleError(err) {
|
|
|
6658
6658
|
}
|
|
6659
6659
|
|
|
6660
6660
|
// src/bin/agt.ts
|
|
6661
|
-
var cliVersion2 = true ? "0.28.
|
|
6661
|
+
var cliVersion2 = true ? "0.28.841" : "dev";
|
|
6662
6662
|
var program = new Command();
|
|
6663
6663
|
program.name("agt").description("Augmented CLI \u2014 agent provisioning and management").version(cliVersion2).option("--json", "Emit machine-readable JSON output (suppress spinners and colors)").option("--skip-update-check", "Skip the automatic update check on startup");
|
|
6664
6664
|
program.hook("preAction", async (thisCommand, actionCommand) => {
|
|
@@ -16,7 +16,7 @@ import {
|
|
|
16
16
|
parseEnvIntegrations,
|
|
17
17
|
shellQuote,
|
|
18
18
|
summarizeUnanswerablePane
|
|
19
|
-
} from "./chunk-
|
|
19
|
+
} from "./chunk-CFLYGZOF.js";
|
|
20
20
|
import {
|
|
21
21
|
BIND_FAILURE_QUARANTINE_THRESHOLD,
|
|
22
22
|
INTEGRATIONS_SECTION_END,
|
|
@@ -76,7 +76,7 @@ import {
|
|
|
76
76
|
sessionTranscriptDir,
|
|
77
77
|
worseConnectivityOutcome,
|
|
78
78
|
wrapScheduledTaskPrompt
|
|
79
|
-
} from "./chunk-
|
|
79
|
+
} from "./chunk-XBLODN73.js";
|
|
80
80
|
import {
|
|
81
81
|
parsePsRows
|
|
82
82
|
} from "./chunk-XWVM4KPK.js";
|
|
@@ -6566,7 +6566,7 @@ function exchangeFailureKind(err) {
|
|
|
6566
6566
|
}
|
|
6567
6567
|
|
|
6568
6568
|
// src/lib/api-client.ts
|
|
6569
|
-
var agtCliVersion = true ? "0.28.
|
|
6569
|
+
var agtCliVersion = true ? "0.28.841" : "dev";
|
|
6570
6570
|
var lastConfigHash = null;
|
|
6571
6571
|
function setConfigHash(hash) {
|
|
6572
6572
|
lastConfigHash = hash && hash.length > 0 ? hash : null;
|
|
@@ -10924,4 +10924,4 @@ export {
|
|
|
10924
10924
|
managerInstallSystemUnitCommand,
|
|
10925
10925
|
managerUninstallSystemUnitCommand
|
|
10926
10926
|
};
|
|
10927
|
-
//# sourceMappingURL=chunk-
|
|
10927
|
+
//# sourceMappingURL=chunk-43P6SG7L.js.map
|
|
@@ -18,7 +18,7 @@ import {
|
|
|
18
18
|
rotateDailySession,
|
|
19
19
|
sessionFileExists,
|
|
20
20
|
todayLocalIso
|
|
21
|
-
} from "./chunk-
|
|
21
|
+
} from "./chunk-XBLODN73.js";
|
|
22
22
|
import {
|
|
23
23
|
reapOrphanChannelMcps
|
|
24
24
|
} from "./chunk-XWVM4KPK.js";
|
|
@@ -5326,4 +5326,4 @@ export {
|
|
|
5326
5326
|
stopAllSessionsAndWait,
|
|
5327
5327
|
getProjectDir
|
|
5328
5328
|
};
|
|
5329
|
-
//# sourceMappingURL=chunk-
|
|
5329
|
+
//# sourceMappingURL=chunk-CFLYGZOF.js.map
|
|
@@ -1259,19 +1259,10 @@ call reaches the user; plain text does not. Tools:
|
|
|
1259
1259
|
- **slack.reply** \u2014 reply in a channel/thread
|
|
1260
1260
|
- **slack.react** \u2014 an emoji reaction (sparingly \u2014 see taxonomy)
|
|
1261
1261
|
- **slack_read_thread** / **slack_read_history** \u2014 re-read a thread, or a
|
|
1262
|
-
channel's recent messages
|
|
1262
|
+
channel's recent messages (\xA7 Reading a conversation back)
|
|
1263
1263
|
|
|
1264
1264
|
Inbound gets an automatic \u{1F440}; don't duplicate it. Prefer a reply to a reaction.
|
|
1265
1265
|
|
|
1266
|
-
**Lost the thread? Read it back.** Reach for them on a SYMPTOM, not routinely:
|
|
1267
|
-
the message points at something you cannot see ("as I mentioned", "like we
|
|
1268
|
-
discussed"); you were pulled into a conversation that was already running; a
|
|
1269
|
-
decision was made earlier and you are about to re-ask it; an inbound arrives
|
|
1270
|
-
\`replayed="true"\` and you cannot recall the original. Making someone repeat
|
|
1271
|
-
themselves reads as not listening. Slack-only: Telegram and direct
|
|
1272
|
-
chat have no read-back tool, so there what you were given is all you have \u2014 say
|
|
1273
|
-
so.
|
|
1274
|
-
|
|
1275
1266
|
**Reaction taxonomy (the only emoji for slack.react):**
|
|
1276
1267
|
- \u2705 (\`white_check_mark\`) \u2014 done, and a text reply isn't warranted.
|
|
1277
1268
|
- \u274C (\`x\`) \u2014 **execution failure only**: you tried it and it errored. Never for
|
|
@@ -1283,6 +1274,21 @@ reaction is governed by your Slack MCP server's own instructions; \u274C is alwa
|
|
|
1283
1274
|
wrong. Skipping means writing nothing: the reply-recovery net posts a trailing
|
|
1284
1275
|
stand-down as if it were your reply.
|
|
1285
1276
|
` : ""}
|
|
1277
|
+
## Reading a conversation back
|
|
1278
|
+
|
|
1279
|
+
**On a SYMPTOM, not routinely:** the message points at something
|
|
1280
|
+
you cannot see ("as I mentioned", "like we discussed"); you were
|
|
1281
|
+
pulled into a conversation that was already running; a decision was made
|
|
1282
|
+
earlier and you are about to re-ask it; an inbound arrives \`replayed="true"\`
|
|
1283
|
+
and you cannot recall the original. Making someone repeat themselves reads as
|
|
1284
|
+
not listening. In direct chat use \`direct_chat_read_history\` with the
|
|
1285
|
+
\`session_id\` from the \`<channel>\` tag. **Reading is not answering** \u2014 you
|
|
1286
|
+
still owe the reply.
|
|
1287
|
+
${resolvedChannels?.includes("telegram") ? `
|
|
1288
|
+
**Telegram has no read-back tool** and cannot be given one today: the Bot API
|
|
1289
|
+
cannot fetch a chat's history and nothing keeps a transcript. There, what you
|
|
1290
|
+
were given is all you have \u2014 say so rather than guess.
|
|
1291
|
+
` : ""}
|
|
1286
1292
|
## Governance
|
|
1287
1293
|
|
|
1288
1294
|
This agent is governed by Ninjafy, formerly Augmented Team. Policy, budget
|
|
@@ -13903,4 +13909,4 @@ export {
|
|
|
13903
13909
|
peekCurrentSession,
|
|
13904
13910
|
readDailySessionPin
|
|
13905
13911
|
};
|
|
13906
|
-
//# sourceMappingURL=chunk-
|
|
13912
|
+
//# sourceMappingURL=chunk-XBLODN73.js.map
|