@kryd/cli 0.5.1 → 0.6.0

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.
Files changed (3) hide show
  1. package/README.md +3 -3
  2. package/dist/index.js +240 -35
  3. package/package.json +3 -3
package/README.md CHANGED
@@ -34,10 +34,10 @@ Once you've run `kryd init` in a directory, the commands below work **arg-less**
34
34
  | `kryd deploy [project]` | Re-deploy the production-branch HEAD already on the forge — no new commit. |
35
35
  | `kryd logs [target]` | Follow a deploy's build/deploy log **in full** — this is where the build output lives (`--runtime` tails the live container instead). |
36
36
  | `kryd rollback [project] [deployment]` | Roll back to a previous successful deploy — no rebuild. |
37
- | `kryd db create \| detach [project]` | Attach / tear down managed Postgres (shared or bring-your-own). |
38
- | `kryd storage create \| detach [project]` | Attach / tear down S3-compatible object storage. |
37
+ | `kryd db add \| remove \| status [project]` | Attach, tear down or inspect managed Postgres (shared or bring-your-own). `remove` destroys the data and asks first. |
38
+ | `kryd storage add \| remove \| status [project]` | Attach, tear down or inspect S3-compatible object storage. `remove` destroys every object and asks first. |
39
39
  | `kryd env list \| set \| rm [project]` | Manage your own environment variables. `set KEY --stdin` (or a prompt) keeps a secret out of `ps` and your shell history; values are never printed back. Add `--build` for build-time variables (`VITE_*`, `NEXT_PUBLIC_*`) — these are compiled into your public bundle, so they must never be secrets, and they take effect at your next build rather than your next deploy. |
40
- | `kryd ai enable [project]` | Give the project an authenticated EU AI-gateway endpoint (injected on the next deploy). |
40
+ | `kryd ai add \| remove \| status [project]` | Give the project an authenticated EU AI-gateway endpoint (injected on the next deploy), take it away again, or show what it has. |
41
41
 
42
42
  Run `kryd <command> --help` for options. Every project-scoped command accepts an explicit `<project>` id, or resolves it from the `.kryd` link (walking up from the current directory, git-style).
43
43
 
package/dist/index.js CHANGED
@@ -15266,6 +15266,36 @@ async function enableAi(apiUrl, token, input) {
15266
15266
  }
15267
15267
  return { enabled: true, url: parsed.url };
15268
15268
  }
15269
+ async function getAiStatus(apiUrl, token, projectId) {
15270
+ const res = await fetch(`${apiUrl}/ai/${encodeURIComponent(projectId)}`, {
15271
+ headers: { authorization: `Bearer ${token}` }
15272
+ });
15273
+ if (!res.ok) {
15274
+ throw new ApiError(
15275
+ `AI status check failed (${res.status})`,
15276
+ await parseEnvelope(res),
15277
+ res.status
15278
+ );
15279
+ }
15280
+ const parsed = await res.json().catch(() => void 0);
15281
+ if (!parsed || typeof parsed.enabled !== "boolean" || typeof parsed.url !== "string" && parsed.url !== null) {
15282
+ throw new ApiError("The API returned an unexpected AI-status response.");
15283
+ }
15284
+ return { enabled: parsed.enabled, url: parsed.url };
15285
+ }
15286
+ async function removeAi(apiUrl, token, projectId) {
15287
+ const res = await fetch(`${apiUrl}/ai/${encodeURIComponent(projectId)}`, {
15288
+ method: "DELETE",
15289
+ headers: { authorization: `Bearer ${token}` }
15290
+ });
15291
+ if (!res.ok) {
15292
+ throw new ApiError(
15293
+ `AI removal failed (${res.status})`,
15294
+ await parseEnvelope(res),
15295
+ res.status
15296
+ );
15297
+ }
15298
+ }
15269
15299
  async function fetchResourceStatus(apiUrl, token, path) {
15270
15300
  const res = await fetch(`${apiUrl}${path}`, {
15271
15301
  headers: { authorization: `Bearer ${token}` }
@@ -16859,7 +16889,7 @@ ${note}
16859
16889
  reportError(err);
16860
16890
  }
16861
16891
  }
16862
- async function runDbCreate(opts) {
16892
+ async function runDbAdd(opts) {
16863
16893
  const apiUrl = resolveApiUrl(opts.apiUrl);
16864
16894
  const token = loadConfig().token;
16865
16895
  if (!token) {
@@ -16869,7 +16899,7 @@ async function runDbCreate(opts) {
16869
16899
  }
16870
16900
  const project2 = resolveProjectId(opts.project, opts.cwd);
16871
16901
  if (!project2) {
16872
- reportNotLinked("kryd db create <projectId>");
16902
+ reportNotLinked("kryd db add <projectId>");
16873
16903
  return;
16874
16904
  }
16875
16905
  if (opts.shared && opts.connectionString !== void 0) {
@@ -16918,7 +16948,7 @@ The connection string will be injected as DATABASE_URL on your next deploy.
16918
16948
  The connection string will be injected as DATABASE_URL on your next deploy.
16919
16949
  `,
16920
16950
  failedLabel: "Database provisioning",
16921
- retryCmd: `kryd db create ${project2}`
16951
+ retryCmd: `kryd db status ${project2}`
16922
16952
  });
16923
16953
  } catch (err) {
16924
16954
  reportError(err);
@@ -16940,7 +16970,7 @@ function reportSettleResult(result, opts) {
16940
16970
  );
16941
16971
  }
16942
16972
  }
16943
- async function runStorageCreate(opts) {
16973
+ async function runStorageAdd(opts) {
16944
16974
  const apiUrl = resolveApiUrl(opts.apiUrl);
16945
16975
  const token = loadConfig().token;
16946
16976
  if (!token) {
@@ -16950,7 +16980,7 @@ async function runStorageCreate(opts) {
16950
16980
  }
16951
16981
  const project2 = resolveProjectId(opts.project, opts.cwd);
16952
16982
  if (!project2) {
16953
- reportNotLinked("kryd storage create <projectId>");
16983
+ reportNotLinked("kryd storage add <projectId>");
16954
16984
  return;
16955
16985
  }
16956
16986
  try {
@@ -16965,7 +16995,7 @@ async function runStorageCreate(opts) {
16965
16995
  Its S3 credentials will be injected on your next deploy.
16966
16996
  `,
16967
16997
  failedLabel: "Storage provisioning",
16968
- retryCmd: `kryd storage create ${project2}`
16998
+ retryCmd: `kryd storage status ${project2}`
16969
16999
  });
16970
17000
  } catch (err) {
16971
17001
  reportError(err);
@@ -16982,11 +17012,26 @@ function reportDetachResult(result, opts) {
16982
17012
  process.exitCode = 1;
16983
17013
  } else {
16984
17014
  process.stderr.write(
16985
- `Could not confirm detach \u2014 still detaching (or the worker stalled). Re-run \`${opts.retryCmd}\` to confirm the resource is gone.
17015
+ `Could not confirm removal \u2014 still tearing down (or the worker stalled). Re-run \`${opts.retryCmd}\` to confirm the resource is gone.
17016
+ `
17017
+ );
17018
+ process.exitCode = 1;
17019
+ }
17020
+ }
17021
+ async function confirmResourceRemoval(opts) {
17022
+ if (opts.yes) return true;
17023
+ const io = opts.io ?? defaultPromptIO();
17024
+ if (!isInteractive(io)) {
17025
+ process.stderr.write(
17026
+ `Refusing to remove ${opts.subject} without confirmation. Re-run with --yes to confirm non-interactively.
16986
17027
  `
16987
17028
  );
16988
17029
  process.exitCode = 1;
17030
+ return false;
16989
17031
  }
17032
+ if (await promptConfirm(opts.question, io)) return true;
17033
+ process.stdout.write(opts.declined);
17034
+ return false;
16990
17035
  }
16991
17036
  function isProjectId(arg) {
16992
17037
  return arg.startsWith("proj_");
@@ -17134,7 +17179,7 @@ async function describeProjectResources(apiUrl, token, projectId) {
17134
17179
  out.push("its Git repository on the forge, and its push token");
17135
17180
  return out;
17136
17181
  }
17137
- async function runDbDetach(opts) {
17182
+ async function runDbRemove(opts) {
17138
17183
  const apiUrl = resolveApiUrl(opts.apiUrl);
17139
17184
  const token = loadConfig().token;
17140
17185
  if (!token) {
@@ -17144,27 +17189,36 @@ async function runDbDetach(opts) {
17144
17189
  }
17145
17190
  const project2 = resolveProjectId(opts.project, opts.cwd);
17146
17191
  if (!project2) {
17147
- reportNotLinked("kryd db detach <projectId>");
17192
+ reportNotLinked("kryd db remove <projectId>");
17148
17193
  return;
17149
17194
  }
17195
+ const proceed = await confirmResourceRemoval({
17196
+ yes: opts.yes,
17197
+ io: opts.io,
17198
+ subject: `the database from ${project2}`,
17199
+ question: `Remove the database from ${project2}? It is torn down and all the data in it is destroyed \u2014 this cannot be undone.`,
17200
+ declined: `Left the database on ${project2} in place.
17201
+ `
17202
+ });
17203
+ if (!proceed) return;
17150
17204
  try {
17151
17205
  await detachDatabase(apiUrl, token, project2);
17152
- process.stdout.write(`Detaching the database from ${project2}\u2026
17206
+ process.stdout.write(`Removing the database from ${project2}\u2026
17153
17207
  `);
17154
17208
  const result = await pollResourceDetached(
17155
17209
  () => getDatabaseStatus(apiUrl, token, project2)
17156
17210
  );
17157
17211
  reportDetachResult(result, {
17158
- goneMsg: `Detached the database from ${project2}.
17212
+ goneMsg: `Removed the database from ${project2}.
17159
17213
  `,
17160
- failedLabel: "Database detach",
17161
- retryCmd: `kryd db detach ${project2}`
17214
+ failedLabel: "Database removal",
17215
+ retryCmd: `kryd db remove ${project2}`
17162
17216
  });
17163
17217
  } catch (err) {
17164
17218
  reportError(err);
17165
17219
  }
17166
17220
  }
17167
- async function runAiEnable(opts) {
17221
+ async function runAiAdd(opts) {
17168
17222
  const apiUrl = resolveApiUrl(opts.apiUrl);
17169
17223
  const token = loadConfig().token;
17170
17224
  if (!token) {
@@ -17174,13 +17228,13 @@ async function runAiEnable(opts) {
17174
17228
  }
17175
17229
  const project2 = resolveProjectId(opts.project, opts.cwd);
17176
17230
  if (!project2) {
17177
- reportNotLinked("kryd ai enable <projectId>");
17231
+ reportNotLinked("kryd ai add <projectId>");
17178
17232
  return;
17179
17233
  }
17180
17234
  try {
17181
17235
  const status = await enableAi(apiUrl, token, { projectId: project2 });
17182
17236
  process.stdout.write(
17183
- `AI enabled for ${project2}.
17237
+ `AI endpoint added to ${project2}.
17184
17238
  ` + (status.url ? `Endpoint: ${status.url} (OpenAI-compatible base URL \u2014 use it as-is)
17185
17239
  ` : "") + `AI_GATEWAY_URL + AI_GATEWAY_TOKEN will be injected on your next deploy (kryd deploy).
17186
17240
  `
@@ -17189,7 +17243,7 @@ async function runAiEnable(opts) {
17189
17243
  reportError(err);
17190
17244
  }
17191
17245
  }
17192
- async function runStorageDetach(opts) {
17246
+ async function runAiRemove(opts) {
17193
17247
  const apiUrl = resolveApiUrl(opts.apiUrl);
17194
17248
  const token = loadConfig().token;
17195
17249
  if (!token) {
@@ -17199,21 +17253,164 @@ async function runStorageDetach(opts) {
17199
17253
  }
17200
17254
  const project2 = resolveProjectId(opts.project, opts.cwd);
17201
17255
  if (!project2) {
17202
- reportNotLinked("kryd storage detach <projectId>");
17256
+ reportNotLinked("kryd ai remove <projectId>");
17203
17257
  return;
17204
17258
  }
17259
+ let current;
17260
+ try {
17261
+ current = await getAiStatus(apiUrl, token, project2);
17262
+ } catch (err) {
17263
+ reportError(err);
17264
+ return;
17265
+ }
17266
+ if (!current.enabled) {
17267
+ process.stdout.write(`${project2}: no AI endpoint \u2014 nothing to remove.
17268
+ `);
17269
+ return;
17270
+ }
17271
+ const proceed = await confirmResourceRemoval({
17272
+ yes: opts.yes,
17273
+ io: opts.io,
17274
+ subject: `the AI endpoint from ${project2}`,
17275
+ question: `Remove the AI endpoint from ${project2}? AI_GATEWAY_URL and AI_GATEWAY_TOKEN stop being injected from your next deploy.`,
17276
+ declined: `Left the AI endpoint on ${project2} in place.
17277
+ `
17278
+ });
17279
+ if (!proceed) return;
17280
+ try {
17281
+ await removeAi(apiUrl, token, project2);
17282
+ process.stdout.write(
17283
+ `AI endpoint removed from ${project2}.
17284
+ AI_GATEWAY_URL and AI_GATEWAY_TOKEN stop being injected from your next deploy (kryd deploy).
17285
+ `
17286
+ );
17287
+ } catch (err) {
17288
+ reportError(err);
17289
+ }
17290
+ }
17291
+ async function reportResourceStatus(opts) {
17292
+ try {
17293
+ const result = await opts.read();
17294
+ if (result.status === "failed") {
17295
+ process.stdout.write(
17296
+ `${opts.project}: ${opts.noun} failed \u2014 ${result.failureReason ?? "unknown error"}.
17297
+ Remove it before attaching another.
17298
+ `
17299
+ );
17300
+ return;
17301
+ }
17302
+ process.stdout.write(`${opts.project}: ${opts.noun} ${result.status}.
17303
+ `);
17304
+ } catch (err) {
17305
+ if (err instanceof ApiError && err.status === 404) {
17306
+ process.stdout.write(`${opts.project}: no ${opts.noun} attached.
17307
+ `);
17308
+ return;
17309
+ }
17310
+ reportError(err);
17311
+ }
17312
+ }
17313
+ async function runDbStatus(opts) {
17314
+ const apiUrl = resolveApiUrl(opts.apiUrl);
17315
+ const token = loadConfig().token;
17316
+ if (!token) {
17317
+ process.stderr.write("Not logged in \u2014 run `kryd login` first.\n");
17318
+ process.exitCode = 1;
17319
+ return;
17320
+ }
17321
+ const project2 = resolveProjectId(opts.project, opts.cwd);
17322
+ if (!project2) {
17323
+ reportNotLinked("kryd db status <projectId>");
17324
+ return;
17325
+ }
17326
+ await reportResourceStatus({
17327
+ read: () => getDatabaseStatus(apiUrl, token, project2),
17328
+ noun: "database",
17329
+ project: project2
17330
+ });
17331
+ }
17332
+ async function runStorageStatus(opts) {
17333
+ const apiUrl = resolveApiUrl(opts.apiUrl);
17334
+ const token = loadConfig().token;
17335
+ if (!token) {
17336
+ process.stderr.write("Not logged in \u2014 run `kryd login` first.\n");
17337
+ process.exitCode = 1;
17338
+ return;
17339
+ }
17340
+ const project2 = resolveProjectId(opts.project, opts.cwd);
17341
+ if (!project2) {
17342
+ reportNotLinked("kryd storage status <projectId>");
17343
+ return;
17344
+ }
17345
+ await reportResourceStatus({
17346
+ read: () => getStorageStatus(apiUrl, token, project2),
17347
+ noun: "object storage",
17348
+ project: project2
17349
+ });
17350
+ }
17351
+ async function runAiStatus(opts) {
17352
+ const apiUrl = resolveApiUrl(opts.apiUrl);
17353
+ const token = loadConfig().token;
17354
+ if (!token) {
17355
+ process.stderr.write("Not logged in \u2014 run `kryd login` first.\n");
17356
+ process.exitCode = 1;
17357
+ return;
17358
+ }
17359
+ const project2 = resolveProjectId(opts.project, opts.cwd);
17360
+ if (!project2) {
17361
+ reportNotLinked("kryd ai status <projectId>");
17362
+ return;
17363
+ }
17364
+ try {
17365
+ const status = await getAiStatus(apiUrl, token, project2);
17366
+ if (!status.enabled) {
17367
+ process.stdout.write(`${project2}: no AI endpoint.
17368
+ `);
17369
+ return;
17370
+ }
17371
+ process.stdout.write(
17372
+ status.url ? `${project2}: AI endpoint ${status.url}
17373
+ ` : `${project2}: AI endpoint enabled, but its URL could not be read back right now.
17374
+ `
17375
+ );
17376
+ } catch (err) {
17377
+ reportError(err);
17378
+ }
17379
+ }
17380
+ async function runStorageRemove(opts) {
17381
+ const apiUrl = resolveApiUrl(opts.apiUrl);
17382
+ const token = loadConfig().token;
17383
+ if (!token) {
17384
+ process.stderr.write("Not logged in \u2014 run `kryd login` first.\n");
17385
+ process.exitCode = 1;
17386
+ return;
17387
+ }
17388
+ const project2 = resolveProjectId(opts.project, opts.cwd);
17389
+ if (!project2) {
17390
+ reportNotLinked("kryd storage remove <projectId>");
17391
+ return;
17392
+ }
17393
+ const proceed = await confirmResourceRemoval({
17394
+ yes: opts.yes,
17395
+ io: opts.io,
17396
+ subject: `object storage from ${project2}`,
17397
+ question: `Remove object storage from ${project2}? The bucket is torn down and every object in it is destroyed \u2014 this cannot be undone.`,
17398
+ declined: `Left the object storage on ${project2} in place.
17399
+ `
17400
+ });
17401
+ if (!proceed) return;
17205
17402
  try {
17206
17403
  await detachStorage(apiUrl, token, project2);
17207
- process.stdout.write(`Detaching object storage from ${project2}\u2026
17404
+ process.stdout.write(`Removing object storage from ${project2}\u2026
17208
17405
  `);
17209
17406
  const result = await pollResourceDetached(
17210
17407
  () => getStorageStatus(apiUrl, token, project2)
17211
17408
  );
17212
17409
  reportDetachResult(result, {
17213
- goneMsg: `Detached object storage from ${project2}.
17410
+ goneMsg: `Removed object storage from ${project2}.
17214
17411
  `,
17215
- failedLabel: "Storage detach",
17216
- retryCmd: `kryd storage detach ${project2}`
17412
+ failedLabel: "Storage removal",
17413
+ retryCmd: `kryd storage remove ${project2}`
17217
17414
  });
17218
17415
  } catch (err) {
17219
17416
  reportError(err);
@@ -17599,7 +17796,7 @@ async function runEnvRemove(opts) {
17599
17796
  if (isReservedEnvVarName(key)) {
17600
17797
  process.stderr.write(
17601
17798
  `${key} is reserved by Kryd and cannot be removed here.
17602
- If it comes from a resource you attached, detach that instead (\`kryd db detach\`, \`kryd storage detach\`).
17799
+ If it comes from a resource you attached, remove that instead (\`kryd db remove\`, \`kryd storage remove\`).
17603
17800
  `
17604
17801
  );
17605
17802
  process.exitCode = 1;
@@ -17666,7 +17863,7 @@ Run \`kryd env list\` to see what is set. (If you meant the runtime variable of
17666
17863
  reportError(err);
17667
17864
  }
17668
17865
  }
17669
- var CLI_VERSION = true ? "0.5.1" : "0.0.0-dev";
17866
+ var CLI_VERSION = true ? "0.6.0" : "0.0.0-dev";
17670
17867
  var program = new Command();
17671
17868
  program.name("kryd").description("Kryd CLI").version(CLI_VERSION);
17672
17869
  program.command("login").description("Sign in via the browser (default) and store a token").option("--email <email>", "account email (with --password; non-interactive escape hatch)").option("--password <password>", "account password (with --email; visible in `ps` \u2014 prefer the browser flow)").option(
@@ -17718,14 +17915,16 @@ project.command("rm [project]").description(
17718
17915
  "Permanently delete a project and everything Kryd created for it (by name or id; asks you to type its name)"
17719
17916
  ).option("--yes", "skip the confirmation (for non-interactive use)").option("--api-url <url>", "control-plane API base URL").action((projectArg, opts) => runProjectRemove({ ...opts, project: projectArg }));
17720
17917
  var db = program.command("db").description("Manage project databases");
17721
- db.command("create [project]").description("Attach a shared or bring-your-own Postgres database to a project").option("--shared", "attach a shared managed database (the default)").option(
17918
+ db.command("add [project]").description("Attach a shared or bring-your-own Postgres database to a project").option("--shared", "attach a shared managed database (the default)").option(
17722
17919
  "--connection-string <url>",
17723
17920
  "attach an existing database (BYO) by pasting its connection string"
17724
- ).option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runDbCreate({ ...opts, project: project2 }));
17725
- db.command("detach [project]").description("Tear down the project's database and reclaim its credential").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runDbDetach({ ...opts, project: project2 }));
17921
+ ).option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runDbAdd({ ...opts, project: project2 }));
17922
+ db.command("remove [project]").description("Tear down the project's database and everything in it (asks for confirmation)").option("--yes", "skip the confirmation prompt").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runDbRemove({ ...opts, project: project2 }));
17923
+ db.command("status [project]").description("Show whether the project has a database, and what state it is in").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runDbStatus({ ...opts, project: project2 }));
17726
17924
  var storage = program.command("storage").description("Manage project object storage");
17727
- storage.command("create [project]").description("Create an S3-compatible object-storage bucket for a project").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runStorageCreate({ ...opts, project: project2 }));
17728
- storage.command("detach [project]").description("Tear down the project's object storage and reclaim its credentials").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runStorageDetach({ ...opts, project: project2 }));
17925
+ storage.command("add [project]").description("Create an S3-compatible object-storage bucket for a project").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runStorageAdd({ ...opts, project: project2 }));
17926
+ storage.command("remove [project]").description("Tear down the project's bucket and every object in it (asks for confirmation)").option("--yes", "skip the confirmation prompt").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runStorageRemove({ ...opts, project: project2 }));
17927
+ storage.command("status [project]").description("Show whether the project has object storage, and what state it is in").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runStorageStatus({ ...opts, project: project2 }));
17729
17928
  var env = program.command("env").description("Manage your app's environment variables");
17730
17929
  env.command("list [project]").description("List the project's environment variables (names and origin \u2014 never values)").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runEnvList({ ...opts, project: project2 }));
17731
17930
  env.command("set <key> [project]").description(
@@ -17757,7 +17956,9 @@ env.command("pull [project]").description(
17757
17956
  "file to write, relative to the project root (default: .env.kryd \u2014 never your hand-maintained .env)"
17758
17957
  ).option("--force", "overwrite the --out file if it already exists").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runEnvPull({ ...opts, project: project2 }));
17759
17958
  var ai = program.command("ai").description("Manage the app's EU AI gateway");
17760
- ai.command("enable [project]").description("Give the project an authenticated EU AI endpoint (injects on next deploy)").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runAiEnable({ ...opts, project: project2 }));
17959
+ ai.command("add [project]").description("Give the project an authenticated EU AI endpoint (injects on next deploy)").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runAiAdd({ ...opts, project: project2 }));
17960
+ ai.command("remove [project]").description("Stop injecting the project's AI endpoint (asks for confirmation)").option("--yes", "skip the confirmation prompt").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runAiRemove({ ...opts, project: project2 }));
17961
+ ai.command("status [project]").description("Show whether the project has an AI endpoint, and what it is").option("--api-url <url>", "control-plane API base URL").action((project2, opts) => runAiStatus({ ...opts, project: project2 }));
17761
17962
  function invokedDirectly() {
17762
17963
  const entry = process.argv[1];
17763
17964
  if (!entry) return false;
@@ -17778,9 +17979,12 @@ if (invokedDirectly()) {
17778
17979
  }
17779
17980
  export {
17780
17981
  program,
17781
- runAiEnable,
17782
- runDbCreate,
17783
- runDbDetach,
17982
+ runAiAdd,
17983
+ runAiRemove,
17984
+ runAiStatus,
17985
+ runDbAdd,
17986
+ runDbRemove,
17987
+ runDbStatus,
17784
17988
  runDeploy,
17785
17989
  runEnvList,
17786
17990
  runEnvPull,
@@ -17796,8 +18000,9 @@ export {
17796
18000
  runRedeploy,
17797
18001
  runRollback,
17798
18002
  runRuntimeLogs,
17799
- runStorageCreate,
17800
- runStorageDetach,
18003
+ runStorageAdd,
18004
+ runStorageRemove,
18005
+ runStorageStatus,
17801
18006
  runWhoami,
17802
18007
  splitKeyValue
17803
18008
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kryd/cli",
3
- "version": "0.5.1",
3
+ "version": "0.6.0",
4
4
  "description": "Kryd CLI — push a React / Vite / Next.js app to the European cloud for your AI: git push → live with SSL, one-click managed Postgres & object storage, and an EU-hosted AI gateway already wired in. Your code and your model calls stay in the EU.",
5
5
  "keywords": [
6
6
  "kryd",
@@ -49,9 +49,9 @@
49
49
  "tsx": "^4.19.2",
50
50
  "typescript": "^5.6.3",
51
51
  "vitest": "^2.1.8",
52
- "@kryd/shared-types": "0.0.0",
53
52
  "@kryd/config-ts": "0.0.0",
54
- "@kryd/config-eslint": "0.0.0"
53
+ "@kryd/config-eslint": "0.0.0",
54
+ "@kryd/shared-types": "0.0.0"
55
55
  },
56
56
  "scripts": {
57
57
  "build": "esbuild src/index.ts --bundle --platform=node --format=esm --external:commander --define:__KRYD_VERSION__=\\\"$npm_package_version\\\" --outfile=dist/index.js",