@empirical-gauzza/cli 1.0.36 → 1.0.37
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/bin/empirical.js +7 -1
- package/lib/auth.js +16 -2
- package/lib/blueprintCommands.js +23 -3
- package/lib/constants.js +672 -670
- package/lib/empiricalTokensFormat.js +66 -0
- package/lib/help.js +11 -1
- package/lib/http.js +11 -3
- package/lib/installWizard.js +3 -1
- package/lib/installers/coreMemoryBlock.js +2 -1
- package/lib/installers/nativePlugin.js +1 -1
- package/lib/installers/promptBlocks.js +9 -0
- package/lib/memoryCommands.js +3 -1
- package/lib/pluginCommands.js +3 -2
- package/lib/setupCommands.js +574 -31
- package/lib/usageCommands.js +52 -0
- package/package.json +33 -33
package/bin/empirical.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
3
|
'use strict';
|
|
4
4
|
|
|
@@ -25,6 +25,7 @@ const { showVersion } = require('../lib/help');
|
|
|
25
25
|
const { isPluginCommand, runPluginCommand } = require('../lib/pluginCommands');
|
|
26
26
|
const { runPolicyCommand } = require('../lib/policyCommands');
|
|
27
27
|
const { runSetupCommand } = require('../lib/setupCommands');
|
|
28
|
+
const { runUsageCommand } = require('../lib/usageCommands');
|
|
28
29
|
const { runBlueprintCommand } = require('../lib/blueprintCommands');
|
|
29
30
|
const { checkNativePluginUpdates } = require('../lib/pluginUpdateCheck');
|
|
30
31
|
|
|
@@ -112,6 +113,11 @@ async function main() {
|
|
|
112
113
|
return;
|
|
113
114
|
}
|
|
114
115
|
|
|
116
|
+
if (args[0] === 'usage') {
|
|
117
|
+
await runUsageCommand(args.slice(1));
|
|
118
|
+
return;
|
|
119
|
+
}
|
|
120
|
+
|
|
115
121
|
if (args[0] === 'setup') {
|
|
116
122
|
await runSetupCommand(args.slice(1));
|
|
117
123
|
return;
|
package/lib/auth.js
CHANGED
|
@@ -361,7 +361,7 @@ function inspectToken(token) {
|
|
|
361
361
|
// Gathers the same identity/workspace facts `doctor` reports (token presence/type/expiry, plus
|
|
362
362
|
// user + workspace from /api/v1/users/me), formatted for `auth status` / `whoami` as a single
|
|
363
363
|
// JSON object instead of doctor's multi-check report.
|
|
364
|
-
async function gatherAuthStatus() {
|
|
364
|
+
async function gatherAuthStatus({ includeEmpiricalTokens = false } = {}) {
|
|
365
365
|
const token = resolveAccessToken();
|
|
366
366
|
const tokenInfo = inspectToken(token);
|
|
367
367
|
|
|
@@ -398,6 +398,18 @@ async function gatherAuthStatus() {
|
|
|
398
398
|
cliWorkspace = null;
|
|
399
399
|
}
|
|
400
400
|
|
|
401
|
+
// `whoami` / `auth status` add one Empirical Tokens line while they are enforced (spec 8.4).
|
|
402
|
+
// Best effort with a short timeout; doctor does not ask for it.
|
|
403
|
+
let empiricalTokens = null;
|
|
404
|
+
if (includeEmpiricalTokens && token && !error) {
|
|
405
|
+
try {
|
|
406
|
+
const { fetchBillingMe, empiricalTokensLine } = require('./usageCommands');
|
|
407
|
+
empiricalTokens = empiricalTokensLine((await fetchBillingMe(3000)).empiricalTokenUsage);
|
|
408
|
+
} catch (_error) {
|
|
409
|
+
empiricalTokens = null;
|
|
410
|
+
}
|
|
411
|
+
}
|
|
412
|
+
|
|
401
413
|
return {
|
|
402
414
|
authenticated: Boolean(token) && !error && tokenInfo.expired !== true,
|
|
403
415
|
tokenPresent: tokenInfo.present,
|
|
@@ -407,6 +419,8 @@ async function gatherAuthStatus() {
|
|
|
407
419
|
user,
|
|
408
420
|
workspaceId,
|
|
409
421
|
cliWorkspace,
|
|
422
|
+
// Present only while enforced for this account: a dark account's JSON has no such key.
|
|
423
|
+
...(empiricalTokens ? { empiricalTokens } : {}),
|
|
410
424
|
error
|
|
411
425
|
};
|
|
412
426
|
}
|
|
@@ -422,7 +436,7 @@ async function runAuthCommand(args) {
|
|
|
422
436
|
}
|
|
423
437
|
|
|
424
438
|
if (action === 'status' || action === 'whoami') {
|
|
425
|
-
const status = await gatherAuthStatus();
|
|
439
|
+
const status = await gatherAuthStatus({ includeEmpiricalTokens: true });
|
|
426
440
|
log(JSON.stringify(status));
|
|
427
441
|
if (!status.authenticated) {
|
|
428
442
|
process.exitCode = 1;
|
package/lib/blueprintCommands.js
CHANGED
|
@@ -3,7 +3,9 @@
|
|
|
3
3
|
const { httpJson, printApiError } = require('./http');
|
|
4
4
|
const { parseOption } = require('./env');
|
|
5
5
|
const { requireAccessToken, resolveApiBaseUrl, buildApiAuthHeaders } = require('./auth');
|
|
6
|
-
const { warn, log } = require('./ui');
|
|
6
|
+
const { warn, log, createPrompter } = require('./ui');
|
|
7
|
+
const { sanitizeForTerminal } = require('./setupCommands');
|
|
8
|
+
const { confirmCostOrExit, isCostPreview, isInteractiveTerminal } = require('./empiricalTokensFormat');
|
|
7
9
|
|
|
8
10
|
function apiUrl(pathSuffix) {
|
|
9
11
|
return new URL(`/api/v1/blueprints${pathSuffix}`, resolveApiBaseUrl()).toString();
|
|
@@ -61,17 +63,35 @@ async function runClaim(args) {
|
|
|
61
63
|
async function runInstall(args) {
|
|
62
64
|
const blueprintId = args[0] && !args[0].startsWith('--') ? args[0] : '';
|
|
63
65
|
if (!blueprintId) {
|
|
64
|
-
warn('Usage: empirical blueprint install <blueprintId> [--version <v>]');
|
|
66
|
+
warn('Usage: empirical blueprint install <blueprintId> [--version <v>] [--accept-cost]');
|
|
65
67
|
process.exit(1);
|
|
66
68
|
}
|
|
67
69
|
const version = parseOption(args, '--version', '');
|
|
70
|
+
const acceptCost = args.includes('--accept-cost');
|
|
68
71
|
|
|
69
72
|
const detail = await callApi('GET', `/${blueprintId}`, undefined);
|
|
70
73
|
if (!detail.owned && detail.priceModel === 'free') {
|
|
71
74
|
await callApi('POST', `/${blueprintId}/claim`, {});
|
|
72
75
|
}
|
|
73
76
|
|
|
74
|
-
const
|
|
77
|
+
const installBody = { ...(version ? { version } : {}), ...(acceptCost ? { acceptEmpiricalTokenCost: true } : {}) };
|
|
78
|
+
let installResult = await callApi('POST', `/${blueprintId}/install`, installBody);
|
|
79
|
+
if (isCostPreview(installResult)) {
|
|
80
|
+
// A priced blueprint in enforce answers 200 with the cost and starts nothing (no installId yet).
|
|
81
|
+
// Acceptance is sent only from --accept-cost or an explicit y at a real terminal, never for the person.
|
|
82
|
+
const prompter = isInteractiveTerminal() ? createPrompter(process.stderr) : null;
|
|
83
|
+
try {
|
|
84
|
+
await confirmCostOrExit(installResult, { prompter, warn, sanitize: sanitizeForTerminal });
|
|
85
|
+
} finally {
|
|
86
|
+
if (prompter) prompter.close();
|
|
87
|
+
}
|
|
88
|
+
installResult = await callApi('POST', `/${blueprintId}/install`, { ...installBody, acceptEmpiricalTokenCost: true });
|
|
89
|
+
}
|
|
90
|
+
if (!installResult || !installResult.installId) {
|
|
91
|
+
// Never poll /installs/undefined: a reply with no install id is not a started install.
|
|
92
|
+
log(JSON.stringify(installResult, null, 2));
|
|
93
|
+
return;
|
|
94
|
+
}
|
|
75
95
|
const finalStatus = await waitForInstall(installResult.installId);
|
|
76
96
|
log(JSON.stringify(finalStatus, null, 2));
|
|
77
97
|
}
|