@intutic/cli 2.8.0 → 2.8.1
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/README.md +11 -5
- package/dist/cli.js +77 -50
- package/dist/cli.js.map +1 -1
- package/dist/commands/budget.d.ts.map +1 -1
- package/dist/commands/budget.js +6 -7
- package/dist/commands/budget.js.map +1 -1
- package/dist/commands/doctor.d.ts +4 -0
- package/dist/commands/doctor.d.ts.map +1 -1
- package/dist/commands/doctor.js +30 -14
- package/dist/commands/doctor.js.map +1 -1
- package/dist/commands/exec.js +1 -1
- package/dist/commands/exec.js.map +1 -1
- package/dist/commands/init.d.ts.map +1 -1
- package/dist/commands/init.js +5 -2
- package/dist/commands/init.js.map +1 -1
- package/dist/commands/setup.d.ts.map +1 -1
- package/dist/commands/setup.js +7 -2
- package/dist/commands/setup.js.map +1 -1
- package/dist/commands/status.js +2 -2
- package/dist/commands/status.js.map +1 -1
- package/dist/config/paths.d.ts +17 -1
- package/dist/config/paths.d.ts.map +1 -1
- package/dist/config/paths.js +25 -4
- package/dist/config/paths.js.map +1 -1
- package/dist/lib/onboarding.d.ts.map +1 -1
- package/dist/lib/onboarding.js +4 -2
- package/dist/lib/onboarding.js.map +1 -1
- package/package.json +5 -5
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# @intutic/cli
|
|
2
2
|
|
|
3
|
-
> AI governance
|
|
3
|
+
> AI governance for developer workspaces.
|
|
4
4
|
|
|
5
5
|
Intutic intercepts agent-to-LLM traffic, enforces SOPs, detects anomalies, and tracks costs — all without changing how your team codes.
|
|
6
6
|
|
|
@@ -21,6 +21,7 @@ intutic start # Run the proxy standalone — no account needed
|
|
|
21
21
|
intutic traces list # See governance verdicts
|
|
22
22
|
```
|
|
23
23
|
|
|
24
|
+
<!-- UNRELEASED:cloud
|
|
24
25
|
**With a control plane:**
|
|
25
26
|
|
|
26
27
|
```bash
|
|
@@ -29,6 +30,7 @@ intutic init # Detect harnesses, record them for sync
|
|
|
29
30
|
intutic connect # Start sync daemon — writes harness rules and gates
|
|
30
31
|
intutic traces list # See governance verdicts
|
|
31
32
|
```
|
|
33
|
+
-->
|
|
32
34
|
|
|
33
35
|
## Commands
|
|
34
36
|
|
|
@@ -36,15 +38,17 @@ intutic traces list # See governance verdicts
|
|
|
36
38
|
|---------|-------------|
|
|
37
39
|
| `intutic init` | Initialize workspace — detect harnesses, record them in `~/.intutic/config.json` |
|
|
38
40
|
| `intutic start` | Start the proxy standalone — no account or control plane needed (`--port`, `--upstream-url`) |
|
|
39
|
-
| `intutic login` | Authenticate with control plane (`--api-key`, `--control-plane-url`, `--dev`) |
|
|
40
|
-
| `intutic logout` | Clear stored credentials |
|
|
41
41
|
| `intutic status` | Show workspace status — auth, harnesses, sync state |
|
|
42
|
-
| `intutic whoami` | Show current authenticated identity |
|
|
43
|
-
| `intutic connect` | Start sync daemon — bidirectional config sync (`--interval`) |
|
|
44
42
|
| `intutic disconnect` | Undo `intutic connect` — restore the harness configs it changed, remove its services, log out (`--harness`, `--dry-run`, `--keep-login`) |
|
|
45
43
|
| `intutic doctor` | Diagnose workspace health — proxy, auth, daemon, configs, logs |
|
|
46
44
|
| `intutic traces list` | List execution traces (`--limit`, `--since`, `--action` with a control plane, `--verdict` without one, `--model`, `--json`) |
|
|
47
45
|
| `intutic traces inspect <id>` | Show full detail of a single trace |
|
|
46
|
+
<!-- UNRELEASED:cloud
|
|
47
|
+
| `intutic login` | Authenticate with control plane (`--api-key`, `--control-plane-url`, `--dev`) |
|
|
48
|
+
| `intutic logout` | Clear stored credentials |
|
|
49
|
+
| `intutic whoami` | Show current authenticated identity |
|
|
50
|
+
| `intutic connect` | Start sync daemon — bidirectional config sync (`--interval`) |
|
|
51
|
+
-->
|
|
48
52
|
|
|
49
53
|
## Supported Harnesses
|
|
50
54
|
|
|
@@ -98,6 +102,7 @@ Credentials are stored at `~/.intutic/credentials.json` (mode `0600`).
|
|
|
98
102
|
| `INTUTIC_DEV` | `1` targets the local control plane (`http://localhost:3001`), like `--dev` |
|
|
99
103
|
| `INTUTIC_PROXY_URL` | Local proxy URL; its port is the proxy port (default `4000`) |
|
|
100
104
|
|
|
105
|
+
<!-- UNRELEASED:cloud
|
|
101
106
|
For non-interactive auth, use `intutic login --api-key vk_...`.
|
|
102
107
|
|
|
103
108
|
### Development Mode
|
|
@@ -109,6 +114,7 @@ intutic login --dev
|
|
|
109
114
|
intutic connect --dev
|
|
110
115
|
intutic traces list --dev
|
|
111
116
|
```
|
|
117
|
+
-->
|
|
112
118
|
|
|
113
119
|
## Documentation
|
|
114
120
|
|
package/dist/cli.js
CHANGED
|
@@ -9,8 +9,9 @@
|
|
|
9
9
|
*
|
|
10
10
|
* @module
|
|
11
11
|
*/
|
|
12
|
-
import { Command } from 'commander';
|
|
12
|
+
import { Command, Option } from 'commander';
|
|
13
13
|
import { createRequire } from 'node:module';
|
|
14
|
+
import { CLOUD_RELEASED, CONTROL_PLANE_PRODUCT_RELEASED, HOSTED_CONTROL_PLANE_URL, SELF_HOST_RELEASED, } from '@intutic/shared-types';
|
|
14
15
|
import { DEFAULT_SANDBOX_IMAGE } from './lib/sandbox/image.js';
|
|
15
16
|
// Read the version from package.json rather than repeating it here. The literal
|
|
16
17
|
// that used to live below said 1.6.0 for three releases running, so
|
|
@@ -20,13 +21,37 @@ import { DEFAULT_SANDBOX_IMAGE } from './lib/sandbox/image.js';
|
|
|
20
21
|
// but JSON imports still need an assertion on older runtimes.
|
|
21
22
|
const { version } = createRequire(import.meta.url)('../package.json');
|
|
22
23
|
const program = new Command();
|
|
24
|
+
// Release flags (packages/shared-types/src/release.ts). A command that only
|
|
25
|
+
// works against a control plane, or only in the self-hosted distribution, is
|
|
26
|
+
// left out of help until that product is released. Hidden is all it is: the
|
|
27
|
+
// command still parses and runs, so staging and existing users are unaffected.
|
|
28
|
+
const needsControlPlane = { hidden: !CONTROL_PLANE_PRODUCT_RELEASED };
|
|
29
|
+
const needsSelfHost = { hidden: !SELF_HOST_RELEASED };
|
|
30
|
+
/** An option of a visible command that only does anything against a control plane. */
|
|
31
|
+
function controlPlaneOption(flags, description) {
|
|
32
|
+
const option = new Option(flags, description);
|
|
33
|
+
return CONTROL_PLANE_PRODUCT_RELEASED ? option : option.hideHelp();
|
|
34
|
+
}
|
|
35
|
+
// A command that needs a control plane, run with none configured, throws
|
|
36
|
+
// NoControlPlaneError (config/paths.ts) from an async action. Say that plainly
|
|
37
|
+
// rather than as an unhandled rejection with a stack; anything else still
|
|
38
|
+
// crashes as before.
|
|
39
|
+
process.on('unhandledRejection', (err) => {
|
|
40
|
+
if (err instanceof Error && err.name === 'NoControlPlaneError') {
|
|
41
|
+
console.error(err.message);
|
|
42
|
+
process.exit(1);
|
|
43
|
+
}
|
|
44
|
+
throw err;
|
|
45
|
+
});
|
|
23
46
|
// Positional options: `--version` and `--help` belong to the program only when
|
|
24
47
|
// they come before a subcommand. Without this, commander matches program
|
|
25
48
|
// options anywhere on the line, so a subcommand option named `--version` would
|
|
26
49
|
// print the CLI version and exit before its command ever saw it.
|
|
27
50
|
program
|
|
28
51
|
.name('intutic')
|
|
29
|
-
.description(
|
|
52
|
+
.description(CONTROL_PLANE_PRODUCT_RELEASED
|
|
53
|
+
? 'Intutic CLI — AI governance control plane for developer workspaces'
|
|
54
|
+
: 'Intutic CLI — open-core AI governance for developer workspaces: a local proxy, gates and policy for coding agents')
|
|
30
55
|
.version(version)
|
|
31
56
|
.enablePositionalOptions();
|
|
32
57
|
program
|
|
@@ -49,7 +74,7 @@ program
|
|
|
49
74
|
await runSetup(opts);
|
|
50
75
|
});
|
|
51
76
|
const judgeCmd = program
|
|
52
|
-
.command('judge')
|
|
77
|
+
.command('judge', needsSelfHost)
|
|
53
78
|
.description('Configure the LLM-as-judge path');
|
|
54
79
|
judgeCmd
|
|
55
80
|
.command('configure')
|
|
@@ -60,7 +85,7 @@ judgeCmd
|
|
|
60
85
|
await runJudgeConfigure(opts);
|
|
61
86
|
});
|
|
62
87
|
program
|
|
63
|
-
.command('login')
|
|
88
|
+
.command('login', needsControlPlane)
|
|
64
89
|
.description('Authenticate with the Intutic control plane')
|
|
65
90
|
.option('--api-key <key>', 'Authenticate with an API key (vk_*)')
|
|
66
91
|
.option('--control-plane-url <url>', 'Control plane to log in to (e.g. a self-hosted one); saved for every later command')
|
|
@@ -80,7 +105,7 @@ program
|
|
|
80
105
|
await runDisconnect({ harness: opts.harness, dryRun: opts.dryRun, keepLogin: opts.keepLogin });
|
|
81
106
|
});
|
|
82
107
|
program
|
|
83
|
-
.command('logout')
|
|
108
|
+
.command('logout', needsControlPlane)
|
|
84
109
|
.description('Clear stored credentials')
|
|
85
110
|
.action(async () => {
|
|
86
111
|
const { runLogout } = await import('./commands/logout.js');
|
|
@@ -111,7 +136,9 @@ program
|
|
|
111
136
|
});
|
|
112
137
|
const budgetCmd = program
|
|
113
138
|
.command('budget')
|
|
114
|
-
.description(
|
|
139
|
+
.description(CONTROL_PLANE_PRODUCT_RELEASED
|
|
140
|
+
? 'Check remaining daily/monthly budget and list active loops; set workspace, key and member budgets'
|
|
141
|
+
: 'Check the local spending cap and what this machine has spent today')
|
|
115
142
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|
|
116
143
|
.option('--watch', 'Continuously print machine-local and workspace spend, one line per tick')
|
|
117
144
|
.option('--interval <seconds>', 'Tick interval in seconds for --watch', String(5))
|
|
@@ -125,7 +152,7 @@ const budgetCmd = program
|
|
|
125
152
|
await runBudget(opts);
|
|
126
153
|
});
|
|
127
154
|
budgetCmd
|
|
128
|
-
.command('set')
|
|
155
|
+
.command('set', needsControlPlane)
|
|
129
156
|
.description("Set the workspace's daily and monthly caps, alert threshold and whether each cap refuses requests (OWNER, ADMIN)")
|
|
130
157
|
.option('--daily <usd>', 'Daily cap in USD (0: no daily cap; default: back to the $100 default)')
|
|
131
158
|
.option('--monthly <usd>', 'Monthly cap in USD (0: no monthly cap; default: back to the $500 default)')
|
|
@@ -141,7 +168,7 @@ budgetCmd
|
|
|
141
168
|
await runBudgetSet(cmd.optsWithGlobals());
|
|
142
169
|
});
|
|
143
170
|
budgetCmd
|
|
144
|
-
.command('keys')
|
|
171
|
+
.command('keys', needsControlPlane)
|
|
145
172
|
.description("Every virtual key's spend budgets, rate limit and spend today and this month")
|
|
146
173
|
.option('--json', 'Output as JSON')
|
|
147
174
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|
|
@@ -150,7 +177,7 @@ budgetCmd
|
|
|
150
177
|
await runBudgetKeys(cmd.optsWithGlobals());
|
|
151
178
|
});
|
|
152
179
|
budgetCmd
|
|
153
|
-
.command('key <keyId>')
|
|
180
|
+
.command('key <keyId>', needsControlPlane)
|
|
154
181
|
.description("Set a virtual key's spend budgets and rate limit (OWNER, ADMIN)")
|
|
155
182
|
.option('--daily <usd>', 'Day budget in USD, or none to remove it')
|
|
156
183
|
.option('--monthly <usd>', 'Month budget in USD, or none to remove it')
|
|
@@ -165,7 +192,7 @@ budgetCmd
|
|
|
165
192
|
await runBudgetKey(keyId, cmd.optsWithGlobals());
|
|
166
193
|
});
|
|
167
194
|
budgetCmd
|
|
168
|
-
.command('members')
|
|
195
|
+
.command('members', needsControlPlane)
|
|
169
196
|
.description("The default member budget, and each member's budgets and spend (Biz Org+)")
|
|
170
197
|
.option('--json', 'Output as JSON')
|
|
171
198
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|
|
@@ -174,7 +201,7 @@ budgetCmd
|
|
|
174
201
|
await runBudgetMembers(cmd.optsWithGlobals());
|
|
175
202
|
});
|
|
176
203
|
budgetCmd
|
|
177
|
-
.command('member <memberId>')
|
|
204
|
+
.command('member <memberId>', needsControlPlane)
|
|
178
205
|
.description("Set a member's spend budgets, or the default member budget with `default` (OWNER, ADMIN; Biz Org+)")
|
|
179
206
|
.option('--daily <usd>', 'Day budget in USD, or none to remove it')
|
|
180
207
|
.option('--monthly <usd>', 'Month budget in USD, or none to remove it')
|
|
@@ -187,7 +214,7 @@ budgetCmd
|
|
|
187
214
|
await runBudgetMember(memberId, cmd.optsWithGlobals());
|
|
188
215
|
});
|
|
189
216
|
program
|
|
190
|
-
.command('predict-cost')
|
|
217
|
+
.command('predict-cost', needsControlPlane)
|
|
191
218
|
.description('Pre-flight cost estimate for a prompt/task before it runs (requires `intutic login`). ' +
|
|
192
219
|
"Estimates output tokens from the workspace's recorded usage and prices them with the same " +
|
|
193
220
|
'rate table as every other cost figure the control plane reports.')
|
|
@@ -201,7 +228,7 @@ program
|
|
|
201
228
|
await runPredictCost(opts);
|
|
202
229
|
});
|
|
203
230
|
const sopsCmd = program
|
|
204
|
-
.command('sops')
|
|
231
|
+
.command('sops', needsControlPlane)
|
|
205
232
|
.description('Manage local and global SOP rules');
|
|
206
233
|
sopsCmd
|
|
207
234
|
.command('push <name>')
|
|
@@ -249,7 +276,7 @@ sopsCmd
|
|
|
249
276
|
});
|
|
250
277
|
// ── SOP Optimizer approval mode ──────────────────────────────────────────
|
|
251
278
|
const optimizerCmd = program
|
|
252
|
-
.command('optimizer')
|
|
279
|
+
.command('optimizer', needsControlPlane)
|
|
253
280
|
.description("Read and set the SOP Optimizer's approval mode (whether it may auto-apply strengthening proposals)");
|
|
254
281
|
optimizerCmd
|
|
255
282
|
.command('settings')
|
|
@@ -273,9 +300,9 @@ optimizerCmd
|
|
|
273
300
|
});
|
|
274
301
|
const policyCmd = program
|
|
275
302
|
.command('policy')
|
|
276
|
-
.description('WASM rules and the policy snapshot');
|
|
303
|
+
.description(CONTROL_PLANE_PRODUCT_RELEASED ? 'WASM rules and the policy snapshot' : 'WASM rules: compile, test and install them locally');
|
|
277
304
|
policyCmd
|
|
278
|
-
.command('snapshot')
|
|
305
|
+
.command('snapshot', needsControlPlane)
|
|
279
306
|
.description('Compile workspace policy to ~/.intutic/hooks/policy-snapshot.rules — the file every gate reads.\n' +
|
|
280
307
|
'\n' +
|
|
281
308
|
' Does only that. \'intutic connect\' writes it too, but as one step of\n' +
|
|
@@ -298,10 +325,10 @@ policyCmd
|
|
|
298
325
|
.command('compile')
|
|
299
326
|
.description('Compile an AssemblyScript rule to WASM (wraps asc)')
|
|
300
327
|
.option('--src <path>', 'Rule source entry file (default: assembly/index.ts)')
|
|
301
|
-
.option('--out <path>',
|
|
328
|
+
.option('--out <path>', `Output .wasm path (default: build/rule.wasm${CONTROL_PLANE_PRODUCT_RELEASED ? ', or build/<candidate>.wasm with --candidate' : ''})`)
|
|
302
329
|
.option('--debug', 'Include debug info and source maps')
|
|
303
|
-
.
|
|
304
|
-
.
|
|
330
|
+
.addOption(controlPlaneOption('--candidate <id>', 'Compile a rule candidate from its source of record on the control plane (fetched and hash-verified; not with --src)'))
|
|
331
|
+
.addOption(controlPlaneOption('--upload', 'With --candidate: upload the bundle to the candidate with its source hash and print the gate results'))
|
|
305
332
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|
|
306
333
|
.action(async (opts) => {
|
|
307
334
|
const { runPolicyCompile } = await import('./commands/policy.js');
|
|
@@ -325,7 +352,7 @@ policyCmd
|
|
|
325
352
|
await runPolicyListLocal();
|
|
326
353
|
});
|
|
327
354
|
policyCmd
|
|
328
|
-
.command('replay <ruleId>')
|
|
355
|
+
.command('replay <ruleId>', needsControlPlane)
|
|
329
356
|
.description("Replay a rule (installed or not) against this workspace's own recent traffic and report " +
|
|
330
357
|
'what it would have done, without touching enforcement.')
|
|
331
358
|
.option('--limit <n>', 'Max sampled contexts to replay against (default 500, capped at 5000)')
|
|
@@ -371,7 +398,7 @@ rulesCmd
|
|
|
371
398
|
// `intutic sops` is files on disk; this namespace is the cited guardrails
|
|
372
399
|
// extracted from policy documents and their shadow -> promote lifecycle.
|
|
373
400
|
const guardrailsCmd = program
|
|
374
|
-
.command('guardrails')
|
|
401
|
+
.command('guardrails', needsControlPlane)
|
|
375
402
|
.description('Policy documents, cited clauses and the guardrails compiled from them');
|
|
376
403
|
const guardrailsSourcesCmd = guardrailsCmd
|
|
377
404
|
.command('sources')
|
|
@@ -614,7 +641,7 @@ guardrailsCmd
|
|
|
614
641
|
await runGuardrailsPull(opts);
|
|
615
642
|
});
|
|
616
643
|
program
|
|
617
|
-
.command('whoami')
|
|
644
|
+
.command('whoami', needsControlPlane)
|
|
618
645
|
.description('Show current authenticated identity')
|
|
619
646
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|
|
620
647
|
.action(async (opts) => {
|
|
@@ -657,7 +684,7 @@ for (const [action, desc] of [
|
|
|
657
684
|
});
|
|
658
685
|
}
|
|
659
686
|
enforceCmd
|
|
660
|
-
.command('report')
|
|
687
|
+
.command('report', needsControlPlane)
|
|
661
688
|
.description('Report locally recorded enforcement state (firewall/CA-trust/system-hooks) to the control plane. ' +
|
|
662
689
|
'No privilege needed — for when apply/remove ran elevated and could not reach stored credentials.')
|
|
663
690
|
.action(async () => {
|
|
@@ -670,7 +697,7 @@ enforceCmd
|
|
|
670
697
|
// tools/scripts/intutic-enterprise-install.sh, an unrelated air-gapped
|
|
671
698
|
// docker-compose installer. Does not touch the host firewall; see `enforce`.
|
|
672
699
|
const enterpriseCmd = program
|
|
673
|
-
.command('enterprise')
|
|
700
|
+
.command('enterprise', needsControlPlane)
|
|
674
701
|
.description('Enterprise fleet rollout: CA trust, Cursor system hooks, MDM manifests');
|
|
675
702
|
enterpriseCmd
|
|
676
703
|
.command('install')
|
|
@@ -709,7 +736,7 @@ envCmd
|
|
|
709
736
|
await runEnvClear();
|
|
710
737
|
});
|
|
711
738
|
program
|
|
712
|
-
.command('connect')
|
|
739
|
+
.command('connect', needsControlPlane)
|
|
713
740
|
.description('Start sync daemon — bidirectional config sync with control plane (requires an account)')
|
|
714
741
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|
|
715
742
|
.option('--interval <ms>', 'Poll interval in milliseconds', '30000')
|
|
@@ -721,7 +748,7 @@ program
|
|
|
721
748
|
await runConnect(opts);
|
|
722
749
|
});
|
|
723
750
|
program
|
|
724
|
-
.command('sync-context')
|
|
751
|
+
.command('sync-context', needsControlPlane)
|
|
725
752
|
.description('Record the Git branch and commit in .intutic/git-context.json, which a running `intutic connect` reports')
|
|
726
753
|
.option('--git', 'Read the branch and commit from the repository (for any not given below)')
|
|
727
754
|
.option('--branch <name>', 'Current Git branch name')
|
|
@@ -731,7 +758,7 @@ program
|
|
|
731
758
|
await runSyncContext(opts);
|
|
732
759
|
});
|
|
733
760
|
program
|
|
734
|
-
.command('decisions-log-refresh')
|
|
761
|
+
.command('decisions-log-refresh', needsControlPlane)
|
|
735
762
|
.description('One-shot refresh of the governed decisions log (.intutic/DECISIONS.md, and the recent ' +
|
|
736
763
|
'entries in each governed harness\'s instructions file) — no-ops if decisionsLogEnabled is off. Invoked by the optional ' +
|
|
737
764
|
'post-merge Git hook `intutic init` installs; safe to run manually.')
|
|
@@ -833,7 +860,7 @@ traces
|
|
|
833
860
|
});
|
|
834
861
|
// ── Findings (detector_findings adjudication) ───────────────────────────────
|
|
835
862
|
const findings = program
|
|
836
|
-
.command('findings')
|
|
863
|
+
.command('findings', needsControlPlane)
|
|
837
864
|
.description('Query and adjudicate detector findings — the TP/FP labeling surface');
|
|
838
865
|
findings
|
|
839
866
|
.command('list')
|
|
@@ -880,7 +907,7 @@ findings
|
|
|
880
907
|
});
|
|
881
908
|
// ── Governance incidents ───────────────────────────────────────────────────
|
|
882
909
|
const incidentsCmd = program
|
|
883
|
-
.command('incidents')
|
|
910
|
+
.command('incidents', needsControlPlane)
|
|
884
911
|
.description('Governance incidents, as on Findings › Incidents (OWNER, ADMIN, EM)');
|
|
885
912
|
incidentsCmd
|
|
886
913
|
.command('list')
|
|
@@ -907,7 +934,7 @@ incidentsCmd
|
|
|
907
934
|
});
|
|
908
935
|
// ── Trace integrity ────────────────────────────────────────────────────────
|
|
909
936
|
const integrity = program
|
|
910
|
-
.command('integrity')
|
|
937
|
+
.command('integrity', needsControlPlane)
|
|
911
938
|
.description('Verify sealed trace roots — list, re-derive, walk the root chain, and walk the config snapshot chain');
|
|
912
939
|
integrity
|
|
913
940
|
.command('roots')
|
|
@@ -950,7 +977,7 @@ integrity
|
|
|
950
977
|
});
|
|
951
978
|
// ── Routing reports ─────────────────────────────────────────────────────────
|
|
952
979
|
const routing = program
|
|
953
|
-
.command('routing')
|
|
980
|
+
.command('routing', needsControlPlane)
|
|
954
981
|
.description('Read-only reports for the routing subsystem');
|
|
955
982
|
routing
|
|
956
983
|
.command('adoption-report')
|
|
@@ -989,7 +1016,7 @@ function defineDaemonInstall(cmd) {
|
|
|
989
1016
|
' Use \'intutic daemon stop\' or \'intutic daemon uninstall\'.')
|
|
990
1017
|
.option('--workspace-id <id>', 'Workspace ID (e.g. wk_xxxx) — required unless --proxy')
|
|
991
1018
|
.option('--api-key <key>', 'Workspace API key (e.g. vk_xxxx) — required unless --proxy')
|
|
992
|
-
.option('--control-plane-url <url>',
|
|
1019
|
+
.option('--control-plane-url <url>', `Control plane the daemon connects to (default: $INTUTIC_CONTROL_PLANE_URL, then a workspace set up with \`intutic init --dev\`, then the URL saved by \`intutic login\`${CLOUD_RELEASED ? `, then ${HOSTED_CONTROL_PLANE_URL}` : ''})`)
|
|
993
1020
|
.option('--binary-path <path>', 'Path to intutic CLI binary (defaults to current process); with --proxy, absolute path to intutic-proxy')
|
|
994
1021
|
.option('--dry-run', 'Print what would be done without writing files')
|
|
995
1022
|
.option('--system', 'Install as a system-level service (LaunchDaemon on macOS, systemd system unit on Linux)')
|
|
@@ -1122,7 +1149,7 @@ skillCmd
|
|
|
1122
1149
|
});
|
|
1123
1150
|
// ── Loop commands ──────────────────────────────────────────────────────────
|
|
1124
1151
|
const loopCmd = program
|
|
1125
|
-
.command('loop')
|
|
1152
|
+
.command('loop', needsControlPlane)
|
|
1126
1153
|
.description('Manage and execute recursive agent loops with budget limits');
|
|
1127
1154
|
loopCmd
|
|
1128
1155
|
.command('start')
|
|
@@ -1190,7 +1217,7 @@ loopCmd
|
|
|
1190
1217
|
// module doc for why `intutic loop review` was never the right command for
|
|
1191
1218
|
// this — it addresses a different id space (Loop Runs, not decisions).
|
|
1192
1219
|
const decisionCmd = program
|
|
1193
|
-
.command('decision')
|
|
1220
|
+
.command('decision', needsControlPlane)
|
|
1194
1221
|
.description('Approve or reject a decision (e.g. a review_before hold) held for human review');
|
|
1195
1222
|
decisionCmd
|
|
1196
1223
|
.command('approve <holdId>')
|
|
@@ -1216,7 +1243,7 @@ decisionCmd
|
|
|
1216
1243
|
// hand-written curl against services/control-plane/src/routes/gateways.ts —
|
|
1217
1244
|
// see commands/gateway.ts's module doc.
|
|
1218
1245
|
const gatewayCmd = program
|
|
1219
|
-
.command('gateway')
|
|
1246
|
+
.command('gateway', needsControlPlane)
|
|
1220
1247
|
.description('Manage self-hosted gateway registrations (Docker / Kubernetes / bare metal)');
|
|
1221
1248
|
gatewayCmd
|
|
1222
1249
|
.command('register')
|
|
@@ -1314,7 +1341,7 @@ gatewayCmd
|
|
|
1314
1341
|
// Provision a workspace's own upstream provider keys — the BYO-key wizard's
|
|
1315
1342
|
// API, previously dashboard-only. See commands/credentials.ts's module doc.
|
|
1316
1343
|
const credentialsCmd = program
|
|
1317
|
-
.command('credentials')
|
|
1344
|
+
.command('credentials', needsControlPlane)
|
|
1318
1345
|
.description('Manage this workspace\'s own upstream provider API keys (BYO-key)');
|
|
1319
1346
|
credentialsCmd
|
|
1320
1347
|
.command('list')
|
|
@@ -1358,7 +1385,7 @@ credentialsCmd
|
|
|
1358
1385
|
// "CLI mints, dashboard audits": this is the mint/inspect half. See
|
|
1359
1386
|
// commands/attenuate.ts's module doc.
|
|
1360
1387
|
const attenuateCmd = program
|
|
1361
|
-
.command('attenuate')
|
|
1388
|
+
.command('attenuate', needsControlPlane)
|
|
1362
1389
|
.description('Attenuate one of your API keys to a child key with narrower scopes (and an optional TTL)')
|
|
1363
1390
|
.option('--parent-key <keyId>', 'Parent API key ID to attenuate')
|
|
1364
1391
|
.option('--caps <scopes>', 'Comma-separated API key scopes for the child key (e.g. gateway:use,traces:read); each must be granted by the parent key')
|
|
@@ -1378,7 +1405,7 @@ attenuateCmd
|
|
|
1378
1405
|
});
|
|
1379
1406
|
// ── API keys and their scopes ────────────────────────────────────────────
|
|
1380
1407
|
const keysCmd = program
|
|
1381
|
-
.command('keys')
|
|
1408
|
+
.command('keys', needsControlPlane)
|
|
1382
1409
|
.description('List, create, re-scope and revoke your API keys');
|
|
1383
1410
|
keysCmd
|
|
1384
1411
|
.command('list')
|
|
@@ -1423,7 +1450,7 @@ keysCmd
|
|
|
1423
1450
|
});
|
|
1424
1451
|
// ── Org signup + team management ─────────────────────────────────────────
|
|
1425
1452
|
const orgCmd = program
|
|
1426
|
-
.command('org')
|
|
1453
|
+
.command('org', needsControlPlane)
|
|
1427
1454
|
.description('Create and manage orgs');
|
|
1428
1455
|
orgCmd
|
|
1429
1456
|
.command('create')
|
|
@@ -1438,7 +1465,7 @@ orgCmd
|
|
|
1438
1465
|
await runOrgCreate(opts);
|
|
1439
1466
|
});
|
|
1440
1467
|
const teamCmd = program
|
|
1441
|
-
.command('team')
|
|
1468
|
+
.command('team', needsControlPlane)
|
|
1442
1469
|
.description('Manage teams and workspaces under an org');
|
|
1443
1470
|
teamCmd
|
|
1444
1471
|
.command('list')
|
|
@@ -1487,7 +1514,7 @@ teamCmd
|
|
|
1487
1514
|
// route. Previously dashboard-only. See commands/apiCommand.ts for the shape
|
|
1488
1515
|
// they share.
|
|
1489
1516
|
const settingsCmd = program
|
|
1490
|
-
.command('settings')
|
|
1517
|
+
.command('settings', needsControlPlane)
|
|
1491
1518
|
.description('Read and change workspace settings (MCP policy, budgets, group policy, config content upload, ...)');
|
|
1492
1519
|
settingsCmd
|
|
1493
1520
|
.command('get [key]')
|
|
@@ -1509,7 +1536,7 @@ settingsCmd
|
|
|
1509
1536
|
await runSettingsSet(key, value, opts);
|
|
1510
1537
|
});
|
|
1511
1538
|
const mcpCmd = program
|
|
1512
|
-
.command('mcp')
|
|
1539
|
+
.command('mcp', needsControlPlane)
|
|
1513
1540
|
.description('Review the MCP servers the workspace\'s MCP proxies have seen, and decide on them');
|
|
1514
1541
|
mcpCmd
|
|
1515
1542
|
.command('list')
|
|
@@ -1550,7 +1577,7 @@ for (const [action, enabled, desc] of [
|
|
|
1550
1577
|
});
|
|
1551
1578
|
}
|
|
1552
1579
|
const notificationsCmd = program
|
|
1553
|
-
.command('notifications')
|
|
1580
|
+
.command('notifications', needsControlPlane)
|
|
1554
1581
|
.description('Manage notification rules: which events go to Slack, email, a webhook or PagerDuty');
|
|
1555
1582
|
function ruleOptions(cmd) {
|
|
1556
1583
|
return cmd
|
|
@@ -1612,7 +1639,7 @@ notificationsCmd
|
|
|
1612
1639
|
await runNotificationsRotateSecret(ruleId, opts);
|
|
1613
1640
|
});
|
|
1614
1641
|
const siemCmd = program
|
|
1615
|
-
.command('siem')
|
|
1642
|
+
.command('siem', needsControlPlane)
|
|
1616
1643
|
.description('Manage SIEM export destinations and the event sources each receives');
|
|
1617
1644
|
function destinationOptions(cmd) {
|
|
1618
1645
|
return cmd
|
|
@@ -1687,7 +1714,7 @@ siemCmd
|
|
|
1687
1714
|
await runSiemRotateSecret(destinationId, opts);
|
|
1688
1715
|
});
|
|
1689
1716
|
const tasksCmd = program
|
|
1690
|
-
.command('tasks')
|
|
1717
|
+
.command('tasks', needsControlPlane)
|
|
1691
1718
|
.description('Manage task-management connections (Jira Cloud, Linear, PagerDuty) that attach ticket context to sessions');
|
|
1692
1719
|
tasksCmd
|
|
1693
1720
|
.command('list')
|
|
@@ -1732,7 +1759,7 @@ tasksCmd
|
|
|
1732
1759
|
await runTasksRemove(connectionId, opts);
|
|
1733
1760
|
});
|
|
1734
1761
|
const complianceCmd = program
|
|
1735
|
-
.command('compliance')
|
|
1762
|
+
.command('compliance', needsControlPlane)
|
|
1736
1763
|
.description('Compliance framework reports and the evidence archive');
|
|
1737
1764
|
complianceCmd
|
|
1738
1765
|
.command('coverage <framework_id>')
|
|
@@ -1777,7 +1804,7 @@ complianceCmd
|
|
|
1777
1804
|
await runComplianceVerify(file, opts);
|
|
1778
1805
|
});
|
|
1779
1806
|
const usageCmd = program
|
|
1780
|
-
.command('usage')
|
|
1807
|
+
.command('usage', needsControlPlane)
|
|
1781
1808
|
.description('LLM usage across the fleet, by member, team, branch, commit or pull request');
|
|
1782
1809
|
for (const [view, handler, desc] of [
|
|
1783
1810
|
['members', 'runUsageMembers', 'Usage per member'],
|
|
@@ -1808,7 +1835,7 @@ usageCmd
|
|
|
1808
1835
|
await runUsagePullRequests(opts);
|
|
1809
1836
|
});
|
|
1810
1837
|
const githubWebhookCmd = program
|
|
1811
|
-
.command('github')
|
|
1838
|
+
.command('github', needsControlPlane)
|
|
1812
1839
|
.description('GitHub integration for cost per pull request')
|
|
1813
1840
|
.command('webhook')
|
|
1814
1841
|
.description('The pull-request webhook: payload URL and signing secret');
|
|
@@ -1831,7 +1858,7 @@ githubWebhookCmd
|
|
|
1831
1858
|
await runGithubWebhookRotateSecret(opts);
|
|
1832
1859
|
});
|
|
1833
1860
|
const inventoryCmd = program
|
|
1834
|
-
.command('inventory')
|
|
1861
|
+
.command('inventory', needsControlPlane)
|
|
1835
1862
|
.description('AI harnesses, MCP servers and skills on connected developer machines, governed or not');
|
|
1836
1863
|
inventoryCmd
|
|
1837
1864
|
.command('summary')
|
|
@@ -1893,7 +1920,7 @@ inventoryCmd
|
|
|
1893
1920
|
await runInventoryDisconnects(opts);
|
|
1894
1921
|
});
|
|
1895
1922
|
program
|
|
1896
|
-
.command('gate-liveness')
|
|
1923
|
+
.command('gate-liveness', needsControlPlane)
|
|
1897
1924
|
.description('Whether each installed harness\'s gate is reporting, and any open silent-gate alert')
|
|
1898
1925
|
.option('--json', 'Output as JSON')
|
|
1899
1926
|
.option('--dev', 'Use local control plane (http://localhost:3001)')
|