@agentuity/cli 1.0.7 → 1.0.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.d.ts.map +1 -1
- package/dist/cli.js +32 -4
- package/dist/cli.js.map +1 -1
- package/dist/cmd/ai/claude-code/constants.d.ts +13 -0
- package/dist/cmd/ai/claude-code/constants.d.ts.map +1 -0
- package/dist/cmd/ai/claude-code/constants.js +16 -0
- package/dist/cmd/ai/claude-code/constants.js.map +1 -0
- package/dist/cmd/ai/claude-code/index.d.ts +3 -0
- package/dist/cmd/ai/claude-code/index.d.ts.map +1 -0
- package/dist/cmd/ai/claude-code/index.js +22 -0
- package/dist/cmd/ai/claude-code/index.js.map +1 -0
- package/dist/cmd/ai/claude-code/install.d.ts +3 -0
- package/dist/cmd/ai/claude-code/install.d.ts.map +1 -0
- package/dist/cmd/ai/claude-code/install.js +133 -0
- package/dist/cmd/ai/claude-code/install.js.map +1 -0
- package/dist/cmd/ai/claude-code/uninstall.d.ts +3 -0
- package/dist/cmd/ai/claude-code/uninstall.d.ts.map +1 -0
- package/dist/cmd/ai/claude-code/uninstall.js +105 -0
- package/dist/cmd/ai/claude-code/uninstall.js.map +1 -0
- package/dist/cmd/ai/index.d.ts.map +1 -1
- package/dist/cmd/ai/index.js +6 -0
- package/dist/cmd/ai/index.js.map +1 -1
- package/dist/cmd/build/vite/db-rewrite.d.ts +50 -0
- package/dist/cmd/build/vite/db-rewrite.d.ts.map +1 -0
- package/dist/cmd/build/vite/db-rewrite.js +169 -0
- package/dist/cmd/build/vite/db-rewrite.js.map +1 -0
- package/dist/cmd/build/vite/registry-generator.d.ts.map +1 -1
- package/dist/cmd/build/vite/registry-generator.js +7 -0
- package/dist/cmd/build/vite/registry-generator.js.map +1 -1
- package/dist/cmd/build/vite/server-bundler.d.ts.map +1 -1
- package/dist/cmd/build/vite/server-bundler.js +71 -1
- package/dist/cmd/build/vite/server-bundler.js.map +1 -1
- package/dist/cmd/canary/index.d.ts.map +1 -1
- package/dist/cmd/canary/index.js +3 -1
- package/dist/cmd/canary/index.js.map +1 -1
- package/dist/cmd/cloud/agent/list.d.ts.map +1 -1
- package/dist/cmd/cloud/agent/list.js +17 -4
- package/dist/cmd/cloud/agent/list.js.map +1 -1
- package/dist/cmd/cloud/apikey/list.d.ts.map +1 -1
- package/dist/cmd/cloud/apikey/list.js +3 -0
- package/dist/cmd/cloud/apikey/list.js.map +1 -1
- package/dist/cmd/cloud/db/list.d.ts.map +1 -1
- package/dist/cmd/cloud/db/list.js +2 -1
- package/dist/cmd/cloud/db/list.js.map +1 -1
- package/dist/cmd/cloud/deployment/list.d.ts.map +1 -1
- package/dist/cmd/cloud/deployment/list.js +14 -6
- package/dist/cmd/cloud/deployment/list.js.map +1 -1
- package/dist/cmd/cloud/deployment/remove.js +2 -2
- package/dist/cmd/cloud/deployment/remove.js.map +1 -1
- package/dist/cmd/cloud/deployment/rollback.js +2 -2
- package/dist/cmd/cloud/deployment/rollback.js.map +1 -1
- package/dist/cmd/cloud/deployment/show.js +2 -2
- package/dist/cmd/cloud/deployment/show.js.map +1 -1
- package/dist/cmd/cloud/deployment/undeploy.js +2 -2
- package/dist/cmd/cloud/deployment/undeploy.js.map +1 -1
- package/dist/cmd/cloud/env/list.d.ts.map +1 -1
- package/dist/cmd/cloud/env/list.js +14 -4
- package/dist/cmd/cloud/env/list.js.map +1 -1
- package/dist/cmd/cloud/eval/list.d.ts.map +1 -1
- package/dist/cmd/cloud/eval/list.js +6 -1
- package/dist/cmd/cloud/eval/list.js.map +1 -1
- package/dist/cmd/cloud/eval-run/list.d.ts.map +1 -1
- package/dist/cmd/cloud/eval-run/list.js +6 -1
- package/dist/cmd/cloud/eval-run/list.js.map +1 -1
- package/dist/cmd/cloud/keyvalue/list-namespaces.d.ts.map +1 -1
- package/dist/cmd/cloud/keyvalue/list-namespaces.js +5 -2
- package/dist/cmd/cloud/keyvalue/list-namespaces.js.map +1 -1
- package/dist/cmd/cloud/keyvalue/util.d.ts +1 -1
- package/dist/cmd/cloud/keyvalue/util.d.ts.map +1 -1
- package/dist/cmd/cloud/keyvalue/util.js +3 -2
- package/dist/cmd/cloud/keyvalue/util.js.map +1 -1
- package/dist/cmd/cloud/machine/list.d.ts.map +1 -1
- package/dist/cmd/cloud/machine/list.js +5 -2
- package/dist/cmd/cloud/machine/list.js.map +1 -1
- package/dist/cmd/cloud/queue/list.d.ts.map +1 -1
- package/dist/cmd/cloud/queue/list.js +3 -1
- package/dist/cmd/cloud/queue/list.js.map +1 -1
- package/dist/cmd/cloud/sandbox/execution/list.d.ts.map +1 -1
- package/dist/cmd/cloud/sandbox/execution/list.js +5 -3
- package/dist/cmd/cloud/sandbox/execution/list.js.map +1 -1
- package/dist/cmd/cloud/sandbox/list.d.ts.map +1 -1
- package/dist/cmd/cloud/sandbox/list.js +4 -1
- package/dist/cmd/cloud/sandbox/list.js.map +1 -1
- package/dist/cmd/cloud/sandbox/runtime/list.d.ts.map +1 -1
- package/dist/cmd/cloud/sandbox/runtime/list.js +4 -2
- package/dist/cmd/cloud/sandbox/runtime/list.js.map +1 -1
- package/dist/cmd/cloud/sandbox/snapshot/list.d.ts.map +1 -1
- package/dist/cmd/cloud/sandbox/snapshot/list.js +4 -2
- package/dist/cmd/cloud/sandbox/snapshot/list.js.map +1 -1
- package/dist/cmd/cloud/session/list.d.ts.map +1 -1
- package/dist/cmd/cloud/session/list.js +6 -1
- package/dist/cmd/cloud/session/list.js.map +1 -1
- package/dist/cmd/cloud/storage/list.d.ts.map +1 -1
- package/dist/cmd/cloud/storage/list.js +2 -1
- package/dist/cmd/cloud/storage/list.js.map +1 -1
- package/dist/cmd/cloud/stream/list.d.ts.map +1 -1
- package/dist/cmd/cloud/stream/list.js +5 -2
- package/dist/cmd/cloud/stream/list.js.map +1 -1
- package/dist/cmd/cloud/thread/list.d.ts.map +1 -1
- package/dist/cmd/cloud/thread/list.js +4 -1
- package/dist/cmd/cloud/thread/list.js.map +1 -1
- package/dist/cmd/cloud/vector/list-namespaces.d.ts.map +1 -1
- package/dist/cmd/cloud/vector/list-namespaces.js +5 -2
- package/dist/cmd/cloud/vector/list-namespaces.js.map +1 -1
- package/dist/cmd/cloud/vector/util.d.ts +1 -1
- package/dist/cmd/cloud/vector/util.d.ts.map +1 -1
- package/dist/cmd/cloud/vector/util.js +3 -2
- package/dist/cmd/cloud/vector/util.js.map +1 -1
- package/dist/cmd/dev/index.d.ts.map +1 -1
- package/dist/cmd/dev/index.js +2 -0
- package/dist/cmd/dev/index.js.map +1 -1
- package/dist/cmd/project/add/database.d.ts.map +1 -1
- package/dist/cmd/project/add/database.js +43 -3
- package/dist/cmd/project/add/database.js.map +1 -1
- package/dist/cmd/project/add/storage.d.ts.map +1 -1
- package/dist/cmd/project/add/storage.js +43 -3
- package/dist/cmd/project/add/storage.js.map +1 -1
- package/dist/cmd/upgrade/index.d.ts.map +1 -1
- package/dist/cmd/upgrade/index.js +25 -10
- package/dist/cmd/upgrade/index.js.map +1 -1
- package/dist/cmd/upgrade/npm-availability.d.ts +45 -12
- package/dist/cmd/upgrade/npm-availability.d.ts.map +1 -1
- package/dist/cmd/upgrade/npm-availability.js +73 -26
- package/dist/cmd/upgrade/npm-availability.js.map +1 -1
- package/dist/version-check.d.ts.map +1 -1
- package/dist/version-check.js +15 -2
- package/dist/version-check.js.map +1 -1
- package/package.json +6 -6
- package/src/cli.ts +41 -4
- package/src/cmd/ai/claude-code/constants.ts +26 -0
- package/src/cmd/ai/claude-code/index.ts +23 -0
- package/src/cmd/ai/claude-code/install.ts +181 -0
- package/src/cmd/ai/claude-code/uninstall.ts +122 -0
- package/src/cmd/ai/index.ts +6 -0
- package/src/cmd/build/vite/db-rewrite.ts +189 -0
- package/src/cmd/build/vite/registry-generator.ts +7 -0
- package/src/cmd/build/vite/server-bundler.ts +89 -3
- package/src/cmd/canary/index.ts +3 -1
- package/src/cmd/cloud/agent/list.ts +19 -4
- package/src/cmd/cloud/apikey/list.ts +4 -0
- package/src/cmd/cloud/db/list.ts +2 -1
- package/src/cmd/cloud/deployment/list.ts +16 -6
- package/src/cmd/cloud/deployment/remove.ts +2 -2
- package/src/cmd/cloud/deployment/rollback.ts +2 -2
- package/src/cmd/cloud/deployment/show.ts +2 -2
- package/src/cmd/cloud/deployment/undeploy.ts +2 -2
- package/src/cmd/cloud/env/list.ts +17 -4
- package/src/cmd/cloud/eval/list.ts +7 -1
- package/src/cmd/cloud/eval-run/list.ts +7 -1
- package/src/cmd/cloud/keyvalue/list-namespaces.ts +5 -2
- package/src/cmd/cloud/keyvalue/util.ts +12 -8
- package/src/cmd/cloud/machine/list.ts +5 -2
- package/src/cmd/cloud/queue/list.ts +3 -1
- package/src/cmd/cloud/sandbox/execution/list.ts +11 -3
- package/src/cmd/cloud/sandbox/list.ts +5 -1
- package/src/cmd/cloud/sandbox/runtime/list.ts +4 -2
- package/src/cmd/cloud/sandbox/snapshot/list.ts +4 -2
- package/src/cmd/cloud/session/list.ts +7 -1
- package/src/cmd/cloud/storage/list.ts +2 -1
- package/src/cmd/cloud/stream/list.ts +7 -2
- package/src/cmd/cloud/thread/list.ts +5 -1
- package/src/cmd/cloud/vector/list-namespaces.ts +5 -2
- package/src/cmd/cloud/vector/util.ts +12 -8
- package/src/cmd/dev/index.ts +2 -0
- package/src/cmd/project/add/database.ts +54 -3
- package/src/cmd/project/add/storage.ts +54 -3
- package/src/cmd/upgrade/index.ts +36 -11
- package/src/cmd/upgrade/npm-availability.ts +106 -36
- package/src/version-check.ts +22 -2
|
@@ -69,6 +69,7 @@ export const listSubcommand = createSubcommand({
|
|
|
69
69
|
prefix: z.string().optional().describe('Path prefix to filter files'),
|
|
70
70
|
}),
|
|
71
71
|
options: z.object({
|
|
72
|
+
orgId: z.string().optional().describe('filter by organization id'),
|
|
72
73
|
showCredentials: z
|
|
73
74
|
.boolean()
|
|
74
75
|
.optional()
|
|
@@ -94,7 +95,7 @@ export const listSubcommand = createSubcommand({
|
|
|
94
95
|
message: 'Fetching storage',
|
|
95
96
|
clearOnSuccess: true,
|
|
96
97
|
callback: async () => {
|
|
97
|
-
return listOrgResources(catalystClient, { type: 's3' });
|
|
98
|
+
return listOrgResources(catalystClient, { type: 's3', orgId: opts?.orgId });
|
|
98
99
|
},
|
|
99
100
|
});
|
|
100
101
|
|
|
@@ -74,8 +74,13 @@ export const listSubcommand = createCommand({
|
|
|
74
74
|
|
|
75
75
|
async handler(ctx) {
|
|
76
76
|
const { opts, options, apiClient, project } = ctx;
|
|
77
|
-
|
|
78
|
-
|
|
77
|
+
|
|
78
|
+
if (opts?.orgId && opts?.projectId) {
|
|
79
|
+
tui.fatal('--org-id and --project-id are mutually exclusive. Use one or the other.');
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
// Use explicit projectId flag; only fall back to project context when --org-id is not set
|
|
83
|
+
const projectId = opts.projectId || (opts.orgId ? undefined : project?.projectId);
|
|
79
84
|
|
|
80
85
|
// Parse metadata filter if provided
|
|
81
86
|
let metadataFilter: Record<string, string> | undefined;
|
|
@@ -70,7 +70,11 @@ export const listSubcommand = createSubcommand({
|
|
|
70
70
|
const { logger, auth, project, opts, options, config } = ctx;
|
|
71
71
|
const catalystClient = await getGlobalCatalystAPIClient(logger, auth, config?.name);
|
|
72
72
|
|
|
73
|
-
|
|
73
|
+
if (opts?.orgId && opts?.projectId) {
|
|
74
|
+
tui.fatal('--org-id and --project-id are mutually exclusive. Use one or the other.');
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
const projectId = opts.all || opts.orgId ? undefined : opts.projectId || project?.projectId;
|
|
74
78
|
const orgId = opts.orgId;
|
|
75
79
|
|
|
76
80
|
try {
|
|
@@ -19,14 +19,17 @@ export const listNamespacesSubcommand = createCommand({
|
|
|
19
19
|
{ command: getCommand('vector ns'), description: 'List namespaces (short alias)' },
|
|
20
20
|
],
|
|
21
21
|
schema: {
|
|
22
|
+
options: z.object({
|
|
23
|
+
orgId: z.string().optional().describe('filter by organization id'),
|
|
24
|
+
}),
|
|
22
25
|
response: NamespaceListResponseSchema,
|
|
23
26
|
},
|
|
24
27
|
webUrl: '/services/vector',
|
|
25
28
|
idempotent: true,
|
|
26
29
|
|
|
27
30
|
async handler(ctx) {
|
|
28
|
-
const { options } = ctx;
|
|
29
|
-
const storage = await createStorageAdapter(ctx);
|
|
31
|
+
const { options, opts } = ctx;
|
|
32
|
+
const storage = await createStorageAdapter(ctx, opts?.orgId);
|
|
30
33
|
const namespaces = await storage.getNamespaces();
|
|
31
34
|
|
|
32
35
|
if (!options.json) {
|
|
@@ -4,15 +4,19 @@ import type { AuthData, Config, GlobalOptions, ProjectConfig } from '../../../ty
|
|
|
4
4
|
import { getCatalystUrl } from '../../../catalyst';
|
|
5
5
|
import * as tui from '../../../tui';
|
|
6
6
|
|
|
7
|
-
export function createStorageAdapter(
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
7
|
+
export function createStorageAdapter(
|
|
8
|
+
ctx: {
|
|
9
|
+
logger: Logger;
|
|
10
|
+
auth: AuthData;
|
|
11
|
+
region: string;
|
|
12
|
+
project?: ProjectConfig;
|
|
13
|
+
config: Config | null;
|
|
14
|
+
options: GlobalOptions;
|
|
15
|
+
},
|
|
16
|
+
explicitOrgId?: string
|
|
17
|
+
) {
|
|
15
18
|
const orgId =
|
|
19
|
+
explicitOrgId ??
|
|
16
20
|
ctx.project?.orgId ??
|
|
17
21
|
ctx.options.orgId ??
|
|
18
22
|
(process.env.AGENTUITY_CLOUD_ORG_ID || ctx.config?.preferences?.orgId);
|
package/src/cmd/dev/index.ts
CHANGED
|
@@ -1050,6 +1050,8 @@ export const command = createCommand({
|
|
|
1050
1050
|
}
|
|
1051
1051
|
process.env.PORT = String(opts.port);
|
|
1052
1052
|
process.env.AGENTUITY_PORT = process.env.PORT;
|
|
1053
|
+
process.env.AGENTUITY_BASE_URL =
|
|
1054
|
+
process.env.AGENTUITY_BASE_URL || `http://localhost:${opts.port}`;
|
|
1053
1055
|
|
|
1054
1056
|
if (project) {
|
|
1055
1057
|
// Set environment variables for LLM provider patches
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { z } from 'zod';
|
|
2
|
-
import { listResources } from '@agentuity/server';
|
|
2
|
+
import { listResources, projectEnvUpdate } from '@agentuity/server';
|
|
3
3
|
import { createSubcommand } from '../../../types';
|
|
4
4
|
import * as tui from '../../../tui';
|
|
5
5
|
import { createPrompt } from '../../../tui';
|
|
@@ -7,7 +7,13 @@ import { getCatalystAPIClient } from '../../../config';
|
|
|
7
7
|
import { getCommand } from '../../../command-prefix';
|
|
8
8
|
import { isDryRunMode, outputDryRun } from '../../../explain';
|
|
9
9
|
import { ErrorCode } from '../../../errors';
|
|
10
|
-
import {
|
|
10
|
+
import {
|
|
11
|
+
addResourceEnvVars,
|
|
12
|
+
findExistingEnvFile,
|
|
13
|
+
readEnvFile,
|
|
14
|
+
filterAgentuitySdkKeys,
|
|
15
|
+
splitEnvAndSecrets,
|
|
16
|
+
} from '../../../env-util';
|
|
11
17
|
|
|
12
18
|
export const databaseSubcommand = createSubcommand({
|
|
13
19
|
name: 'database',
|
|
@@ -42,7 +48,7 @@ export const databaseSubcommand = createSubcommand({
|
|
|
42
48
|
},
|
|
43
49
|
|
|
44
50
|
async handler(ctx) {
|
|
45
|
-
const { logger, args, orgId, region, auth, options, projectDir } = ctx;
|
|
51
|
+
const { logger, args, orgId, region, auth, options, projectDir, project } = ctx;
|
|
46
52
|
|
|
47
53
|
if (isDryRunMode(options)) {
|
|
48
54
|
const message = args.name
|
|
@@ -131,6 +137,51 @@ export const databaseSubcommand = createSubcommand({
|
|
|
131
137
|
tui.success(`Linked database: ${tui.bold(selectedDatabase.name)}`);
|
|
132
138
|
tui.info('Environment variables written to .env');
|
|
133
139
|
}
|
|
140
|
+
|
|
141
|
+
// Sync to cloud
|
|
142
|
+
const isHeadless = !process.stdin.isTTY || !process.stdout.isTTY;
|
|
143
|
+
let shouldSync = true;
|
|
144
|
+
|
|
145
|
+
if (!isHeadless && !options.json) {
|
|
146
|
+
shouldSync = await tui.confirm('Sync environment variables to cloud project?', true);
|
|
147
|
+
if (process.stdin.isTTY) {
|
|
148
|
+
process.stdin.pause();
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
if (shouldSync) {
|
|
153
|
+
try {
|
|
154
|
+
const envFilePath = await findExistingEnvFile(projectDir);
|
|
155
|
+
const localEnv = await readEnvFile(envFilePath);
|
|
156
|
+
const filteredEnv = filterAgentuitySdkKeys(localEnv);
|
|
157
|
+
|
|
158
|
+
if (Object.keys(filteredEnv).length > 0) {
|
|
159
|
+
const { env, secrets } = splitEnvAndSecrets(filteredEnv);
|
|
160
|
+
await tui.spinner({
|
|
161
|
+
message: 'Syncing environment variables to cloud',
|
|
162
|
+
clearOnSuccess: true,
|
|
163
|
+
callback: async () => {
|
|
164
|
+
await projectEnvUpdate(catalystClient, {
|
|
165
|
+
id: project.projectId,
|
|
166
|
+
env,
|
|
167
|
+
secrets,
|
|
168
|
+
});
|
|
169
|
+
},
|
|
170
|
+
});
|
|
171
|
+
if (!options.json) {
|
|
172
|
+
tui.success('Environment variables synced to cloud');
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
} catch (error) {
|
|
176
|
+
if (!options.json) {
|
|
177
|
+
tui.warning(
|
|
178
|
+
'Failed to sync environment variables to cloud. You can sync later with: ' +
|
|
179
|
+
tui.bold(getCommand('cloud env push'))
|
|
180
|
+
);
|
|
181
|
+
}
|
|
182
|
+
logger.debug('Failed to sync env to cloud:', error);
|
|
183
|
+
}
|
|
184
|
+
}
|
|
134
185
|
} else {
|
|
135
186
|
if (!options.json) {
|
|
136
187
|
tui.warning(`Database "${selectedDatabase.name}" has no environment variables to add`);
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { z } from 'zod';
|
|
2
|
-
import { listResources } from '@agentuity/server';
|
|
2
|
+
import { listResources, projectEnvUpdate } from '@agentuity/server';
|
|
3
3
|
import { createSubcommand } from '../../../types';
|
|
4
4
|
import * as tui from '../../../tui';
|
|
5
5
|
import { createPrompt } from '../../../tui';
|
|
@@ -7,7 +7,13 @@ import { getCatalystAPIClient } from '../../../config';
|
|
|
7
7
|
import { getCommand } from '../../../command-prefix';
|
|
8
8
|
import { isDryRunMode, outputDryRun } from '../../../explain';
|
|
9
9
|
import { ErrorCode } from '../../../errors';
|
|
10
|
-
import {
|
|
10
|
+
import {
|
|
11
|
+
addResourceEnvVars,
|
|
12
|
+
findExistingEnvFile,
|
|
13
|
+
readEnvFile,
|
|
14
|
+
filterAgentuitySdkKeys,
|
|
15
|
+
splitEnvAndSecrets,
|
|
16
|
+
} from '../../../env-util';
|
|
11
17
|
|
|
12
18
|
export const storageSubcommand = createSubcommand({
|
|
13
19
|
name: 'storage',
|
|
@@ -42,7 +48,7 @@ export const storageSubcommand = createSubcommand({
|
|
|
42
48
|
},
|
|
43
49
|
|
|
44
50
|
async handler(ctx) {
|
|
45
|
-
const { logger, args, orgId, region, auth, options, projectDir } = ctx;
|
|
51
|
+
const { logger, args, orgId, region, auth, options, projectDir, project } = ctx;
|
|
46
52
|
|
|
47
53
|
if (isDryRunMode(options)) {
|
|
48
54
|
const message = args.name
|
|
@@ -131,6 +137,51 @@ export const storageSubcommand = createSubcommand({
|
|
|
131
137
|
tui.success(`Linked storage bucket: ${tui.bold(selectedBucket.bucket_name)}`);
|
|
132
138
|
tui.info('Environment variables written to .env');
|
|
133
139
|
}
|
|
140
|
+
|
|
141
|
+
// Sync to cloud
|
|
142
|
+
const isHeadless = !process.stdin.isTTY || !process.stdout.isTTY;
|
|
143
|
+
let shouldSync = true;
|
|
144
|
+
|
|
145
|
+
if (!isHeadless && !options.json) {
|
|
146
|
+
shouldSync = await tui.confirm('Sync environment variables to cloud project?', true);
|
|
147
|
+
if (process.stdin.isTTY) {
|
|
148
|
+
process.stdin.pause();
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
if (shouldSync) {
|
|
153
|
+
try {
|
|
154
|
+
const envFilePath = await findExistingEnvFile(projectDir);
|
|
155
|
+
const localEnv = await readEnvFile(envFilePath);
|
|
156
|
+
const filteredEnv = filterAgentuitySdkKeys(localEnv);
|
|
157
|
+
|
|
158
|
+
if (Object.keys(filteredEnv).length > 0) {
|
|
159
|
+
const { env, secrets } = splitEnvAndSecrets(filteredEnv);
|
|
160
|
+
await tui.spinner({
|
|
161
|
+
message: 'Syncing environment variables to cloud',
|
|
162
|
+
clearOnSuccess: true,
|
|
163
|
+
callback: async () => {
|
|
164
|
+
await projectEnvUpdate(catalystClient, {
|
|
165
|
+
id: project.projectId,
|
|
166
|
+
env,
|
|
167
|
+
secrets,
|
|
168
|
+
});
|
|
169
|
+
},
|
|
170
|
+
});
|
|
171
|
+
if (!options.json) {
|
|
172
|
+
tui.success('Environment variables synced to cloud');
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
} catch (error) {
|
|
176
|
+
if (!options.json) {
|
|
177
|
+
tui.warning(
|
|
178
|
+
'Failed to sync environment variables to cloud. You can sync later with: ' +
|
|
179
|
+
tui.bold(getCommand('cloud env push'))
|
|
180
|
+
);
|
|
181
|
+
}
|
|
182
|
+
logger.debug('Failed to sync env to cloud:', error);
|
|
183
|
+
}
|
|
184
|
+
}
|
|
134
185
|
} else {
|
|
135
186
|
if (!options.json) {
|
|
136
187
|
tui.warning(
|
package/src/cmd/upgrade/index.ts
CHANGED
|
@@ -5,6 +5,7 @@ import { z } from 'zod';
|
|
|
5
5
|
import { ErrorCode, createError, exitWithError } from '../../errors';
|
|
6
6
|
import * as tui from '../../tui';
|
|
7
7
|
import { $ } from 'bun';
|
|
8
|
+
import { tmpdir } from 'node:os';
|
|
8
9
|
import { getInstallationType, type InstallationType } from '../../utils/installation-type';
|
|
9
10
|
|
|
10
11
|
const UpgradeOptionsSchema = z.object({
|
|
@@ -70,18 +71,35 @@ export async function fetchLatestVersion(): Promise<string> {
|
|
|
70
71
|
}
|
|
71
72
|
|
|
72
73
|
/**
|
|
73
|
-
* Upgrade the CLI using bun global install
|
|
74
|
+
* Upgrade the CLI using bun global install.
|
|
75
|
+
* Retries on transient resolution errors caused by npm CDN propagation delays.
|
|
74
76
|
*/
|
|
75
|
-
async function performBunUpgrade(
|
|
77
|
+
async function performBunUpgrade(
|
|
78
|
+
version: string,
|
|
79
|
+
onRetry?: (attempt: number, delayMs: number) => void
|
|
80
|
+
): Promise<void> {
|
|
76
81
|
// Remove 'v' prefix for npm version
|
|
77
82
|
const npmVersion = version.replace(/^v/, '');
|
|
78
83
|
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
84
|
+
const { installWithRetry } = await import('./npm-availability');
|
|
85
|
+
|
|
86
|
+
try {
|
|
87
|
+
await installWithRetry(
|
|
88
|
+
async () => {
|
|
89
|
+
// Use bun to install the specific version globally
|
|
90
|
+
// Run from tmpdir to avoid interference from any local package.json/node_modules
|
|
91
|
+
const result = await $`bun add -g @agentuity/cli@${npmVersion}`
|
|
92
|
+
.cwd(tmpdir())
|
|
93
|
+
.quiet()
|
|
94
|
+
.nothrow();
|
|
95
|
+
return { exitCode: result.exitCode, stderr: result.stderr };
|
|
96
|
+
},
|
|
97
|
+
{ onRetry }
|
|
98
|
+
);
|
|
99
|
+
} catch (error) {
|
|
100
|
+
throw new Error(
|
|
101
|
+
`Failed to install @agentuity/cli@${npmVersion}: ${error instanceof Error ? error.message : String(error)}`
|
|
102
|
+
);
|
|
85
103
|
}
|
|
86
104
|
}
|
|
87
105
|
|
|
@@ -192,8 +210,9 @@ export const command = createCommand({
|
|
|
192
210
|
callback: async () => {
|
|
193
211
|
const { waitForNpmAvailability } = await import('./npm-availability');
|
|
194
212
|
return await waitForNpmAvailability(latestVersion, {
|
|
195
|
-
maxAttempts:
|
|
196
|
-
initialDelayMs:
|
|
213
|
+
maxAttempts: 10,
|
|
214
|
+
initialDelayMs: 5000,
|
|
215
|
+
maxDelayMs: 15000,
|
|
197
216
|
});
|
|
198
217
|
},
|
|
199
218
|
});
|
|
@@ -242,8 +261,14 @@ export const command = createCommand({
|
|
|
242
261
|
|
|
243
262
|
// Perform the upgrade using bun
|
|
244
263
|
await tui.spinner({
|
|
264
|
+
type: 'logger',
|
|
245
265
|
message: `Installing @agentuity/cli@${normalizedLatest}...`,
|
|
246
|
-
callback: async () =>
|
|
266
|
+
callback: async (log) =>
|
|
267
|
+
await performBunUpgrade(latestVersion, (attempt, delayMs) => {
|
|
268
|
+
log(
|
|
269
|
+
`Package not yet available on CDN, retrying in ${Math.round(delayMs / 1000)}s (attempt ${attempt})...`
|
|
270
|
+
);
|
|
271
|
+
}),
|
|
247
272
|
});
|
|
248
273
|
|
|
249
274
|
// Verify the upgrade
|
|
@@ -1,62 +1,51 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* npm registry availability checking utilities.
|
|
3
|
-
* Used to verify a version is available
|
|
3
|
+
* Used to verify a version is available via bun's resolver before attempting upgrade.
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
|
|
7
|
-
|
|
6
|
+
import { $ } from 'bun';
|
|
7
|
+
import { tmpdir } from 'node:os';
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
const QUICK_CHECK_TIMEOUT_MS = 1000;
|
|
11
|
-
|
|
12
|
-
/** Default timeout for explicit upgrade command */
|
|
13
|
-
const EXPLICIT_CHECK_TIMEOUT_MS = 5000;
|
|
14
|
-
|
|
15
|
-
export interface CheckNpmOptions {
|
|
16
|
-
/** Timeout in milliseconds (default: 5000 for explicit, 1000 for quick) */
|
|
17
|
-
timeoutMs?: number;
|
|
18
|
-
}
|
|
9
|
+
const PACKAGE_SPEC = '@agentuity/cli';
|
|
19
10
|
|
|
20
11
|
/**
|
|
21
|
-
* Check if a specific version of @agentuity/cli is
|
|
22
|
-
* Uses
|
|
12
|
+
* Check if a specific version of @agentuity/cli is resolvable by bun.
|
|
13
|
+
* Uses `bun info` to verify bun's own resolver/CDN can see the version,
|
|
14
|
+
* which avoids the race where npm registry returns 200 but bun's CDN
|
|
15
|
+
* has not yet propagated the version.
|
|
23
16
|
*
|
|
24
17
|
* @param version - Version to check (with or without 'v' prefix)
|
|
25
|
-
* @param options - Optional configuration
|
|
26
18
|
* @returns true if version is available, false otherwise
|
|
27
19
|
*/
|
|
28
|
-
export async function isVersionAvailableOnNpm(
|
|
29
|
-
version: string,
|
|
30
|
-
options: CheckNpmOptions = {}
|
|
31
|
-
): Promise<boolean> {
|
|
32
|
-
const { timeoutMs = EXPLICIT_CHECK_TIMEOUT_MS } = options;
|
|
20
|
+
export async function isVersionAvailableOnNpm(version: string): Promise<boolean> {
|
|
33
21
|
const normalizedVersion = version.replace(/^v/, '');
|
|
34
|
-
const url = `${NPM_REGISTRY_URL}/${encodeURIComponent(PACKAGE_NAME)}/${normalizedVersion}`;
|
|
35
|
-
|
|
36
22
|
try {
|
|
37
|
-
const
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
}
|
|
44
|
-
|
|
23
|
+
const result = await $`bun info ${PACKAGE_SPEC}@${normalizedVersion} --json`
|
|
24
|
+
.cwd(tmpdir())
|
|
25
|
+
.quiet()
|
|
26
|
+
.nothrow();
|
|
27
|
+
if (result.exitCode !== 0) {
|
|
28
|
+
return false;
|
|
29
|
+
}
|
|
30
|
+
const info = JSON.parse(result.stdout.toString());
|
|
31
|
+
if (info.error) {
|
|
32
|
+
return false;
|
|
33
|
+
}
|
|
34
|
+
return info.version === normalizedVersion;
|
|
45
35
|
} catch {
|
|
46
|
-
// Network error or timeout - assume not available
|
|
47
36
|
return false;
|
|
48
37
|
}
|
|
49
38
|
}
|
|
50
39
|
|
|
51
40
|
/**
|
|
52
|
-
* Quick check if a version is available
|
|
53
|
-
* Used for implicit version checks (auto-upgrade flow)
|
|
41
|
+
* Quick check if a version is available via bun's resolver.
|
|
42
|
+
* Used for implicit version checks (auto-upgrade flow).
|
|
54
43
|
*
|
|
55
44
|
* @param version - Version to check (with or without 'v' prefix)
|
|
56
|
-
* @returns true if version is available, false if unavailable or
|
|
45
|
+
* @returns true if version is available, false if unavailable or error
|
|
57
46
|
*/
|
|
58
47
|
export async function isVersionAvailableOnNpmQuick(version: string): Promise<boolean> {
|
|
59
|
-
return isVersionAvailableOnNpm(version
|
|
48
|
+
return isVersionAvailableOnNpm(version);
|
|
60
49
|
}
|
|
61
50
|
|
|
62
51
|
export interface WaitForNpmOptions {
|
|
@@ -103,3 +92,84 @@ export async function waitForNpmAvailability(
|
|
|
103
92
|
|
|
104
93
|
return false;
|
|
105
94
|
}
|
|
95
|
+
|
|
96
|
+
/**
|
|
97
|
+
* Patterns in bun's stderr that indicate a resolution/CDN propagation failure
|
|
98
|
+
* (as opposed to a permanent install error like permissions or disk space).
|
|
99
|
+
*/
|
|
100
|
+
const RESOLUTION_ERROR_PATTERNS = [/failed to resolve/i, /no version matching/i];
|
|
101
|
+
|
|
102
|
+
/**
|
|
103
|
+
* Check whether a bun install failure is a transient resolution error
|
|
104
|
+
* caused by npm CDN propagation delays.
|
|
105
|
+
*/
|
|
106
|
+
export function isResolutionError(stderr: string): boolean {
|
|
107
|
+
return RESOLUTION_ERROR_PATTERNS.some((pattern) => pattern.test(stderr));
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
export interface InstallWithRetryOptions {
|
|
111
|
+
/** Maximum number of attempts including the first (default: 7 → 1 initial + 6 retries) */
|
|
112
|
+
maxAttempts?: number;
|
|
113
|
+
/** Initial delay in ms before the first retry (default: 5000) */
|
|
114
|
+
initialDelayMs?: number;
|
|
115
|
+
/** Maximum delay cap in ms (default: 30000) */
|
|
116
|
+
maxDelayMs?: number;
|
|
117
|
+
/** Multiplier applied to the delay after each retry (default: 2) */
|
|
118
|
+
multiplier?: number;
|
|
119
|
+
/** Callback invoked before each retry with the attempt number and upcoming delay */
|
|
120
|
+
onRetry?: (attempt: number, delayMs: number) => void;
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
/**
|
|
124
|
+
* Run an install function and retry on transient resolution errors with
|
|
125
|
+
* exponential backoff. This covers the window (~2 min) where npm CDN nodes
|
|
126
|
+
* have not yet propagated a newly-published version.
|
|
127
|
+
*
|
|
128
|
+
* Total wait with defaults: 5 + 10 + 20 + 30 + 30 + 30 = 125 s ≈ 2 min
|
|
129
|
+
*
|
|
130
|
+
* @param installFn - Async function that performs the install and returns exitCode + stderr
|
|
131
|
+
* @param options - Retry configuration
|
|
132
|
+
* @returns The successful result (exitCode 0)
|
|
133
|
+
* @throws Error if all retries are exhausted or a non-resolution error occurs
|
|
134
|
+
*/
|
|
135
|
+
export async function installWithRetry(
|
|
136
|
+
installFn: () => Promise<{ exitCode: number; stderr: Buffer }>,
|
|
137
|
+
options: InstallWithRetryOptions = {}
|
|
138
|
+
): Promise<{ exitCode: number; stderr: Buffer }> {
|
|
139
|
+
const {
|
|
140
|
+
maxAttempts = 7,
|
|
141
|
+
initialDelayMs = 5000,
|
|
142
|
+
maxDelayMs = 30000,
|
|
143
|
+
multiplier = 2,
|
|
144
|
+
onRetry,
|
|
145
|
+
} = options;
|
|
146
|
+
|
|
147
|
+
let delay = initialDelayMs;
|
|
148
|
+
|
|
149
|
+
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
|
|
150
|
+
const result = await installFn();
|
|
151
|
+
|
|
152
|
+
if (result.exitCode === 0) {
|
|
153
|
+
return result;
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
const stderr = result.stderr.toString();
|
|
157
|
+
|
|
158
|
+
// Only retry on resolution/propagation errors — bail immediately for anything else
|
|
159
|
+
if (!isResolutionError(stderr)) {
|
|
160
|
+
throw new Error(stderr);
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
// Last attempt exhausted — throw
|
|
164
|
+
if (attempt === maxAttempts) {
|
|
165
|
+
throw new Error(stderr);
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
onRetry?.(attempt, delay);
|
|
169
|
+
await new Promise((resolve) => setTimeout(resolve, delay));
|
|
170
|
+
delay = Math.min(Math.round(delay * multiplier), maxDelayMs);
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
// Unreachable, but satisfies TypeScript
|
|
174
|
+
throw new Error('Install failed after retries');
|
|
175
|
+
}
|
package/src/version-check.ts
CHANGED
|
@@ -5,6 +5,7 @@ import { getVersion, getCompareUrl, getReleaseUrl, toTag } from './version';
|
|
|
5
5
|
import * as tui from './tui';
|
|
6
6
|
import { saveConfig } from './config';
|
|
7
7
|
import { $ } from 'bun';
|
|
8
|
+
import { tmpdir } from 'node:os';
|
|
8
9
|
import { getExecutingAgent } from './agent-detection';
|
|
9
10
|
|
|
10
11
|
const ONE_HOUR_MS = 60 * 60 * 1000;
|
|
@@ -171,8 +172,27 @@ async function performUpgrade(logger: Logger, targetVersion: string): Promise<vo
|
|
|
171
172
|
|
|
172
173
|
logger.info('Upgrading to version %s...', npmVersion);
|
|
173
174
|
|
|
174
|
-
// Use bun to install the specific version globally
|
|
175
|
-
|
|
175
|
+
// Use bun to install the specific version globally with retry for CDN propagation delays
|
|
176
|
+
// Run from tmpdir to avoid interference from any local package.json/node_modules
|
|
177
|
+
const { installWithRetry } = await import('./cmd/upgrade/npm-availability');
|
|
178
|
+
await installWithRetry(
|
|
179
|
+
async () => {
|
|
180
|
+
const result = await $`bun add -g @agentuity/cli@${npmVersion}`
|
|
181
|
+
.cwd(tmpdir())
|
|
182
|
+
.quiet()
|
|
183
|
+
.nothrow();
|
|
184
|
+
return { exitCode: result.exitCode, stderr: result.stderr };
|
|
185
|
+
},
|
|
186
|
+
{
|
|
187
|
+
onRetry: (attempt, delayMs) => {
|
|
188
|
+
logger.info(
|
|
189
|
+
'Package not yet available on CDN, retrying in %ds (attempt %d)...',
|
|
190
|
+
Math.round(delayMs / 1000),
|
|
191
|
+
attempt
|
|
192
|
+
);
|
|
193
|
+
},
|
|
194
|
+
}
|
|
195
|
+
);
|
|
176
196
|
|
|
177
197
|
// If we got here, the upgrade succeeded
|
|
178
198
|
// Re-run the original command with the new binary
|