@cabane/cli 0.1.10 → 0.2.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 +41 -41
  2. package/dist/cli.js +35 -30
  3. package/package.json +3 -3
package/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # cabane CLI
1
+ # cabane-server CLI
2
2
 
3
3
  Run a self-hosted [Cabane](https://cabane.ai) on your own machine. `@cabane/cli`
4
4
  installs the Cabane server, runs the whole stack — server plus embedded Postgres —
@@ -13,12 +13,12 @@ itself and needs no model key of its own.
13
13
  The short version:
14
14
 
15
15
  ```sh
16
- npm i -g @cabane/cli # install the CLI (bin: `cabane`)
17
- cabane init # first-run wizard (data location, port, URL)
18
- cabane install --token cabdist_… # fetch + verify + unpack the server
19
- cabane up --daemon # run the stack
16
+ npm i -g @cabane/cli # install the CLI (bin: `cabane-server`)
17
+ cabane-server init # first-run wizard (data location, port, URL)
18
+ cabane-server install --token cabdist_… # fetch + verify + unpack the server
19
+ cabane-server up --daemon # run the stack
20
20
  # open http://localhost:3000, sign up
21
- cabane setup-agent # confirm your account + how to pair a companion
21
+ cabane-server setup-agent # confirm your account + how to pair a companion
22
22
  ```
23
23
 
24
24
  Each step, in order, below.
@@ -33,26 +33,26 @@ Each step, in order, below.
33
33
 
34
34
  ## Getting started
35
35
 
36
- 1. **Install the CLI.** `npm i -g @cabane/cli` — installs the `cabane` binary.
36
+ 1. **Install the CLI.** `npm i -g @cabane/cli` — installs the `cabane-server` binary.
37
37
 
38
- 2. **Run `cabane init`** — the interactive first-run wizard. It asks where your
38
+ 2. **Run `cabane-server init`** — the interactive first-run wizard. It asks where your
39
39
  data lives (and shows the resolved paths — `data/storage` for uploads,
40
40
  `data/pg` for the database), the port, and an optional public URL. Everything
41
- persists to config, so a later `cabane up` needs no flags. Re-run it any time to
41
+ persists to config, so a later `cabane-server up` needs no flags. Re-run it any time to
42
42
  reconfigure, or skip it and pass flags directly if you prefer.
43
43
 
44
- 3. **Run `cabane install --token cabdist_…`** — fetches the server artifact with
44
+ 3. **Run `cabane-server install --token cabdist_…`** — fetches the server artifact with
45
45
  your distribution token, verifies its sha256, and unpacks it. (Have a local
46
- tarball instead? `cabane install --from <artifact.tgz>` works offline.)
46
+ tarball instead? `cabane-server install --from <artifact.tgz>` works offline.)
47
47
 
48
- 4. **Run `cabane up --daemon`** — starts and supervises the stack: embedded
48
+ 4. **Run `cabane-server up --daemon`** — starts and supervises the stack: embedded
49
49
  Postgres and the server. Leave off `--daemon` to run it in the foreground.
50
50
 
51
51
  5. **Sign up.** Open <http://localhost:3000> and create your account and first
52
52
  workspace.
53
53
 
54
54
  6. **Pair a companion.** Your workspace seeds an agent, but it has nowhere to run
55
- until you pair a device. `cabane setup-agent` (mint an access token in
55
+ until you pair a device. `cabane-server setup-agent` (mint an access token in
56
56
  **Settings → Developer**, paste it at the prompt) confirms your account and
57
57
  prints the steps: install the Companion (desktop app, or the headless
58
58
  `@cabane/companion`), sign in against this instance, pair it, then assign the
@@ -64,7 +64,7 @@ see the [Cabane docs](https://app.cabane.ai/docs).
64
64
 
65
65
  ## What it supervises
66
66
 
67
- `cabane up` runs two children in order, with a clean SIGTERM teardown:
67
+ `cabane-server up` runs two children in order, with a clean SIGTERM teardown:
68
68
 
69
69
  1. **Embedded Postgres** — the `embedded-postgres` binaries (pinned pg 16.14) run
70
70
  as a child on a local off-5432 port; data in `<CABANE_HOME>/data/pg`. No system
@@ -72,7 +72,7 @@ see the [Cabane docs](https://app.cabane.ai/docs).
72
72
  2. **The server** — the artifact's single-process API+SPA (`server.js`, filesystem
73
73
  storage, the bundled SPA served via `WEB_DIST`), env composed automatically
74
74
  (`NODE_ENV=production`, `http://localhost:<port>`, generated-once vision
75
- secret, any persisted `cabane set-env` creds). Migrations apply on boot.
75
+ secret, any persisted `cabane-server set-env` creds). Migrations apply on boot.
76
76
 
77
77
  Agents don't run here — they run on a companion you pair (a separate process on a
78
78
  device you control), the same as hosted Cabane.
@@ -93,35 +93,35 @@ which a standalone `@cabane/companion` user companion already keys off, so a
93
93
  self-host install can never clobber a companion's device pairing on a shared box.
94
94
  Override the whole root with the **`CABANE_HOME`** env var (the multi-instance
95
95
  lever); a pre-existing self-host install still living at `~/.cabane` is adopted in
96
- place, so no data moves. A `cabane install` / `set-env` pointed (via `CABANE_HOME`)
96
+ place, so no data moves. A `cabane-server install` / `set-env` pointed (via `CABANE_HOME`)
97
97
  at a directory that holds a companion config refuses rather than overwrite it.
98
98
 
99
- **Relocating just the data.** `cabane init` can point the **data** leg (pg +
99
+ **Relocating just the data.** `cabane-server init` can point the **data** leg (pg +
100
100
  storage) at any path you choose while `config.json` + `app/` stay under the root —
101
101
  handy for putting bulky uploads on a bigger disk. The default is still
102
102
  `<root>/data`; the chosen location persists in config, so `up` finds it with no
103
103
  env var or flag.
104
104
 
105
105
  **Your data is safe across upgrades.** `data/` (pg + storage) sits apart from the
106
- versioned `app/<version>/` tree, so `cabane install`, `cabane update`, and a
106
+ versioned `app/<version>/` tree, so `cabane-server install`, `cabane-server update`, and a
107
107
  same-version reinstall only ever touch the app tree — your account, files, and
108
- conversations persist untouched. `cabane status` prints the `home` + `data`
108
+ conversations persist untouched. `cabane-server status` prints the `home` + `data`
109
109
  paths so you can see it.
110
110
 
111
111
  ## Commands
112
112
 
113
- | Command | What it does |
114
- | -------------------- | --------------------------------------------------------------------------------------------- |
115
- | `cabane init` | interactive first-run wizard: data location, port, public URL |
116
- | `cabane install` | fetch (token → gated artifact) or `--from` a local tarball; unpack + `npm install --omit=dev` |
117
- | `cabane up` | start + supervise the stack (`--daemon` for background) |
118
- | `cabane setup-agent` | after signup: confirm your account + print companion-pairing guidance |
119
- | `cabane update` | install a newer published artifact (keeps N-1 for rollback) |
120
- | `cabane set-env` | persist generic `KEY=VALUE` server env forwarded to the server (`--list` / `--unset`) |
121
- | `cabane down` | stop a running stack |
122
- | `cabane status` | what's installed + running |
123
- | `cabane logs` | tail the server log |
124
- | `cabane doctor` | preflight: diagnose common self-host failure classes (runs with the stack down) |
113
+ | Command | What it does |
114
+ | --------------------------- | --------------------------------------------------------------------------------------------- |
115
+ | `cabane-server init` | interactive first-run wizard: data location, port, public URL |
116
+ | `cabane-server install` | fetch (token → gated artifact) or `--from` a local tarball; unpack + `npm install --omit=dev` |
117
+ | `cabane-server up` | start + supervise the stack (`--daemon` for background) |
118
+ | `cabane-server setup-agent` | after signup: confirm your account + print companion-pairing guidance |
119
+ | `cabane-server update` | install a newer published artifact (keeps N-1 for rollback) |
120
+ | `cabane-server set-env` | persist generic `KEY=VALUE` server env forwarded to the server (`--list` / `--unset`) |
121
+ | `cabane-server down` | stop a running stack |
122
+ | `cabane-server status` | what's installed + running |
123
+ | `cabane-server logs` | tail the server log |
124
+ | `cabane-server doctor` | preflight: diagnose common self-host failure classes (runs with the stack down) |
125
125
 
126
126
  ## Running agents
127
127
 
@@ -134,9 +134,9 @@ against the login or key already there; the server never sees the credential. Fo
134
134
  single-box setup, the companion can run on the same machine as the server (point it
135
135
  at `http://localhost:3000`).
136
136
 
137
- ## Troubleshooting — `cabane doctor`
137
+ ## Troubleshooting — `cabane-server doctor`
138
138
 
139
- When something won't start, run `cabane doctor` **first**. It's a standalone
139
+ When something won't start, run `cabane-server doctor` **first**. It's a standalone
140
140
  preflight (no server needed — it's what you reach for precisely when things are
141
141
  broken) that checks the common self-host failure classes and prints a legible
142
142
  pass/fail/warn report, each with a one-line fix, then exits non-zero if any hard
@@ -149,29 +149,29 @@ check fails. It's strictly local — nothing phones home. Checks:
149
149
  - **Disk space** for the data dir.
150
150
  - **macOS Gatekeeper** — quarantine on the Postgres binaries (macOS only).
151
151
 
152
- ## Server env — `cabane set-env`
152
+ ## Server env — `cabane-server set-env`
153
153
 
154
- The self-hosted server needs no model credential of its own. `cabane set-env` stays
154
+ The self-hosted server needs no model credential of its own. `cabane-server set-env` stays
155
155
  for any generic server env you _do_ want to persist:
156
156
 
157
157
  ```sh
158
158
  # persisted — save once; every future `up` (fresh shell, reboot) picks it up.
159
159
  # A bare KEY prompts for the value (hidden); `KEY=VALUE` still works for scripting.
160
- cabane set-env SOME_KEY
161
- cabane down && cabane up --daemon
160
+ cabane-server set-env SOME_KEY
161
+ cabane-server down && cabane-server up --daemon
162
162
  ```
163
163
 
164
164
  It stores generic `KEY=VALUE` pairs in `<CABANE_HOME>/config.json` and layers them
165
165
  into the server's env on every `up` — beneath the composed infra vars, so an
166
166
  operator key reaches the server but can never clobber `DATABASE_URL` / `NODE_ENV` /
167
- `STORAGE_*`. A bare `cabane set-env KEY` (no `=value`) prompts for the value without
167
+ `STORAGE_*`. A bare `cabane-server set-env KEY` (no `=value`) prompts for the value without
168
168
  echoing, so a secret never lands on the command line. Inspect with
169
- `cabane set-env --list` (values masked), remove with `cabane set-env --unset KEY`.
169
+ `cabane-server set-env --list` (values masked), remove with `cabane-server set-env --unset KEY`.
170
170
  A live shell export takes precedence over a persisted value. Apply a change to an
171
- already-running stack with `cabane down && cabane up`.
171
+ already-running stack with `cabane-server down && cabane-server up`.
172
172
 
173
173
  ## Notes
174
174
 
175
175
  - **macOS Gatekeeper** may quarantine the unsigned Postgres binaries. If pg
176
176
  fails to exec on first run, clear the quarantine xattr and retry —
177
- `cabane doctor` detects this and prints the fix.
177
+ `cabane-server doctor` detects this and prints the fix.
package/dist/cli.js CHANGED
@@ -224,7 +224,7 @@ async function checkPort(ctx) {
224
224
  "port",
225
225
  "Port",
226
226
  `:${port} is occupied by another process`,
227
- `Free port ${port}, or install on another with \`cabane install --port <n>\`, then retry.`
227
+ `Free port ${port}, or install on another with \`cabane-server install --port <n>\`, then retry.`
228
228
  );
229
229
  }
230
230
  function ownSupervisorPid(paths) {
@@ -275,7 +275,7 @@ function checkStorage(ctx) {
275
275
  `Make ${target} writable, or point Cabane elsewhere with \`CABANE_HOME=<dir>\`.`
276
276
  );
277
277
  }
278
- const note = existsSync2(root) ? "" : " (will be created on first `cabane up`)";
278
+ const note = existsSync2(root) ? "" : " (will be created on first `cabane-server up`)";
279
279
  return pass("storage", "Storage root", `${root} \u2014 writable${note}`);
280
280
  }
281
281
  async function resolvePgBinaries(platform, arch) {
@@ -328,7 +328,7 @@ async function checkPostgres(ctx) {
328
328
  return pass(
329
329
  "postgres",
330
330
  "Embedded Postgres",
331
- `binaries present; data dir uninitialised \u2014 first \`cabane up\` will init it (${dataDir})`
331
+ `binaries present; data dir uninitialised \u2014 first \`cabane-server up\` will init it (${dataDir})`
332
332
  );
333
333
  }
334
334
  const stale = stalePostmaster(dataDir);
@@ -337,7 +337,7 @@ async function checkPostgres(ctx) {
337
337
  "postgres",
338
338
  "Embedded Postgres",
339
339
  `data dir initialised but holds a stale postmaster.pid (pid ${stale}, not running) \u2014 ${dataDir}`,
340
- "Harmless \u2014 Postgres clears it on the next `cabane up`; remove data/pg/postmaster.pid if start still refuses."
340
+ "Harmless \u2014 Postgres clears it on the next `cabane-server up`; remove data/pg/postmaster.pid if start still refuses."
341
341
  );
342
342
  }
343
343
  return pass("postgres", "Embedded Postgres", `binaries present; data dir healthy \u2014 ${dataDir}`);
@@ -428,7 +428,7 @@ var STATUS_GLYPH = {
428
428
  };
429
429
  var NAME_WIDTH = 22;
430
430
  function reportLines(summary) {
431
- const lines = ["cabane doctor", ""];
431
+ const lines = ["cabane-server doctor", ""];
432
432
  for (const r of summary.results) {
433
433
  lines.push(`${STATUS_GLYPH[r.status]} ${r.name.padEnd(NAME_WIDTH)} ${r.detail}`);
434
434
  if (r.fix) lines.push(` ${" ".repeat(NAME_WIDTH)} \u21B3 fix: ${r.fix}`);
@@ -565,7 +565,7 @@ async function down() {
565
565
  rmSync2(paths.supervisorPidFile, { force: true });
566
566
  rmSync2(paths.stateFile, { force: true });
567
567
  if (free) ok("stopped");
568
- else warn2(`stopped, but port ${port} still looks busy \u2014 check \`cabane status\`.`);
568
+ else warn2(`stopped, but port ${port} still looks busy \u2014 check \`cabane-server status\`.`);
569
569
  }
570
570
  async function killPid(pid) {
571
571
  try {
@@ -666,7 +666,7 @@ async function promptSecret(question) {
666
666
  async function init() {
667
667
  if (!isInteractive()) {
668
668
  throw new Error(
669
- "`cabane init` is an interactive wizard \u2014 run it in a terminal, or configure non-interactively with `cabane install --port \u2026` + `cabane set-env KEY=VALUE`."
669
+ "`cabane-server init` is an interactive wizard \u2014 run it in a terminal, or configure non-interactively with `cabane-server install --port \u2026` + `cabane-server set-env KEY=VALUE`."
670
670
  );
671
671
  }
672
672
  assertNotForeignCompanion();
@@ -716,9 +716,13 @@ async function init() {
716
716
  info("");
717
717
  const installed = config.currentVersion && isInstalled(appDirFor(paths, config.currentVersion));
718
718
  if (installed) {
719
- info("next: `cabane up` (no flags needed), then sign up and `cabane setup-agent`.");
719
+ info(
720
+ "next: `cabane-server up` (no flags needed), then sign up and `cabane-server setup-agent`."
721
+ );
720
722
  } else {
721
- info("next: `cabane install` to fetch the server, then `cabane up` (no flags needed).");
723
+ info(
724
+ "next: `cabane-server install` to fetch the server, then `cabane-server up` (no flags needed)."
725
+ );
722
726
  }
723
727
  }
724
728
  function expandPath(input, root) {
@@ -736,7 +740,7 @@ async function promptPort(current) {
736
740
  if (Number.isInteger(n) && n > 0 && n <= 65535) return n;
737
741
  warn2(`invalid port: ${answer} \u2014 enter a number between 1 and 65535.`);
738
742
  }
739
- throw new Error("no valid port after several tries \u2014 re-run `cabane init`.");
743
+ throw new Error("no valid port after several tries \u2014 re-run `cabane-server init`.");
740
744
  }
741
745
 
742
746
  // src/commands/install.ts
@@ -759,7 +763,7 @@ async function fetchManifest(distBase, token, version) {
759
763
  if (res.status === 404) return null;
760
764
  if (res.status === 401) {
761
765
  throw new Error(
762
- "distribution token rejected (401) \u2014 check the token passed to `cabane install`"
766
+ "distribution token rejected (401) \u2014 check the token passed to `cabane-server install`"
763
767
  );
764
768
  }
765
769
  if (!res.ok) {
@@ -846,7 +850,7 @@ async function install(opts) {
846
850
  } else {
847
851
  info(`data will live at ${paths.dataDir} (pg + storage) \u2014 preserved across upgrades`);
848
852
  }
849
- info("next: cabane up");
853
+ info("next: cabane-server up");
850
854
  } finally {
851
855
  cleanup?.();
852
856
  }
@@ -878,7 +882,7 @@ async function logs(opts) {
878
882
  const paths = resolvePaths();
879
883
  const n = String(opts.lines ?? 80);
880
884
  if (!existsSync6(paths.serverLog)) {
881
- info("no logs yet \u2014 start the stack with `cabane up`.");
885
+ info("no logs yet \u2014 start the stack with `cabane-server up`.");
882
886
  return;
883
887
  }
884
888
  const args = opts.follow ? ["-n", n, "-F", paths.serverLog] : ["-n", n, paths.serverLog];
@@ -895,7 +899,7 @@ function printList() {
895
899
  const env = loadConfig().companionEnv ?? {};
896
900
  const keys = Object.keys(env);
897
901
  if (keys.length === 0) {
898
- info("no persisted server env. Add one: `cabane set-env KEY=VALUE`");
902
+ info("no persisted server env. Add one: `cabane-server set-env KEY=VALUE`");
899
903
  return;
900
904
  }
901
905
  step("persisted server env:");
@@ -941,7 +945,7 @@ async function setEnv(pairs, opts) {
941
945
  config.companionEnv = { ...config.companionEnv ?? {}, ...parsed };
942
946
  });
943
947
  for (const key of Object.keys(parsed)) ok(`set ${key}=${mask(parsed[key])}`);
944
- info("restart to apply: `cabane down && cabane up --daemon`");
948
+ info("restart to apply: `cabane-server down && cabane-server up --daemon`");
945
949
  }
946
950
  }
947
951
 
@@ -1025,11 +1029,11 @@ async function setupAgent(opts) {
1025
1029
  const base = localBaseUrl(config.port);
1026
1030
  const instanceUrl = config.publicUrl ?? base;
1027
1031
  if (!await healthy(config.port)) {
1028
- throw new Error(`server is not up on ${base} \u2014 run \`cabane up\` and sign up first.`);
1032
+ throw new Error(`server is not up on ${base} \u2014 run \`cabane-server up\` and sign up first.`);
1029
1033
  }
1030
1034
  const token = await resolvePat(opts, base);
1031
1035
  const client = makeClient(base, token);
1032
- const me = await client.get("/api/auth/me");
1036
+ const me = await client.get("/api/me");
1033
1037
  ok(`owner resolved (${me.user.id})`);
1034
1038
  const assignment = await defaultAgentAssignment(client);
1035
1039
  info("");
@@ -1099,7 +1103,7 @@ async function status() {
1099
1103
  process.stdout.write(` ${label.padEnd(12)}${value}
1100
1104
  `);
1101
1105
  };
1102
- process.stdout.write("cabane\n");
1106
+ process.stdout.write("cabane-server\n");
1103
1107
  line("version", config.currentVersion ?? "(not installed)");
1104
1108
  if (config.previousVersion) line("previous", config.previousVersion);
1105
1109
  line("port", String(config.port));
@@ -1107,7 +1111,7 @@ async function status() {
1107
1111
  line("data", `${paths.dataDir} (pg + storage \xB7 kept across upgrades)`);
1108
1112
  line("supervisor", supervisorUp ? `up (pid ${supervisorPid})` : "down");
1109
1113
  line("server", serverUp ? `up \xB7 http://localhost:${config.port}` : "down");
1110
- if (!supervisorUp) info("start it: cabane up");
1114
+ if (!supervisorUp) info("start it: cabane-server up");
1111
1115
  }
1112
1116
  function readState2(file) {
1113
1117
  try {
@@ -1281,7 +1285,7 @@ async function up(opts) {
1281
1285
  const paths = pathsFor(config);
1282
1286
  if (opts.port) config.port = opts.port;
1283
1287
  if (!config.currentVersion) {
1284
- throw new Error("nothing installed yet \u2014 run `cabane install` first.");
1288
+ throw new Error("nothing installed yet \u2014 run `cabane-server install` first.");
1285
1289
  }
1286
1290
  const appDir = appDirFor(paths, config.currentVersion);
1287
1291
  if (!isInstalled(appDir)) {
@@ -1296,7 +1300,7 @@ async function up(opts) {
1296
1300
  }
1297
1301
  if (await portInUse(config.port)) {
1298
1302
  throw new Error(
1299
- `port ${config.port} is already in use. If cabane is running, use \`cabane down\`; otherwise a stale process is holding it \u2014 free it and retry.`
1303
+ `port ${config.port} is already in use. If cabane is running, use \`cabane-server down\`; otherwise a stale process is holding it \u2014 free it and retry.`
1300
1304
  );
1301
1305
  }
1302
1306
  if (opts.daemon) {
@@ -1309,7 +1313,7 @@ async function launchDaemon(paths, config) {
1309
1313
  if (existsSync8(paths.supervisorPidFile)) {
1310
1314
  const pid = Number(readFileSync6(paths.supervisorPidFile, "utf8").trim());
1311
1315
  if (pid && pidAlive(pid)) {
1312
- warn2(`already running (supervisor pid ${pid}). Use \`cabane down\` to stop it.`);
1316
+ warn2(`already running (supervisor pid ${pid}). Use \`cabane-server down\` to stop it.`);
1313
1317
  return;
1314
1318
  }
1315
1319
  }
@@ -1342,8 +1346,8 @@ async function launchDaemon(paths, config) {
1342
1346
  }
1343
1347
  function daemonFooter() {
1344
1348
  return [
1345
- "next: open the URL, sign up, then pair a companion so your agents can answer \u2014 `cabane setup-agent` explains how",
1346
- "logs: cabane logs \xB7 stop: cabane down"
1349
+ "next: open the URL, sign up, then pair a companion so your agents can answer \u2014 `cabane-server setup-agent` explains how",
1350
+ "logs: cabane-server logs \xB7 stop: cabane-server down"
1347
1351
  ];
1348
1352
  }
1349
1353
  var Supervisor = class {
@@ -1369,7 +1373,7 @@ var Supervisor = class {
1369
1373
  visionSecret: config.visionSecret,
1370
1374
  ...config.credentialKey ? { credentialKey: config.credentialKey } : {},
1371
1375
  ...config.publicUrl ? { publicBaseUrl: config.publicUrl } : {},
1372
- // Persisted `cabane set-env` creds (generic server env) are layered beneath
1376
+ // Persisted `cabane-server set-env` creds (generic server env) are layered beneath
1373
1377
  // the composed infra vars.
1374
1378
  ...config.companionEnv ? { persistedEnv: config.companionEnv } : {},
1375
1379
  // The artifact's build version → the server reports it on the companion
@@ -1473,8 +1477,9 @@ async function update(opts) {
1473
1477
  const distBase = (opts.distBase ?? config.distBase).replace(/\/$/, "");
1474
1478
  const token = opts.token ?? config.distToken;
1475
1479
  if (!token)
1476
- throw new Error("no distribution token stored \u2014 run `cabane install --token \u2026` first.");
1477
- if (!config.currentVersion) throw new Error("nothing installed \u2014 run `cabane install` first.");
1480
+ throw new Error("no distribution token stored \u2014 run `cabane-server install --token \u2026` first.");
1481
+ if (!config.currentVersion)
1482
+ throw new Error("nothing installed \u2014 run `cabane-server install` first.");
1478
1483
  step(`checking ${distBase} for updates\u2026`);
1479
1484
  const manifest = await fetchManifest(distBase, token, opts.version);
1480
1485
  if (!manifest) throw new Error("no artifact available from the distribution endpoint.");
@@ -1490,12 +1495,12 @@ async function update(opts) {
1490
1495
  }
1491
1496
  await install({ token, distBase, version: target });
1492
1497
  ok(`installed ${target} (previous kept for rollback)`);
1493
- info("restart to run it: cabane down && cabane up");
1498
+ info("restart to run it: cabane-server down && cabane-server up");
1494
1499
  }
1495
1500
 
1496
1501
  // src/cli.ts
1497
1502
  var program = new Command();
1498
- program.name("cabane").description("Run a self-hosted Cabane on your own machine \u2014 no docker, no repo.").version("0.1.2");
1503
+ program.name("cabane-server").description("Run a self-hosted Cabane on your own machine \u2014 no docker, no repo.").version("0.2.0");
1499
1504
  var parsePort = (raw) => {
1500
1505
  const n = Number(raw);
1501
1506
  if (!Number.isInteger(n) || n <= 0 || n > 65535) throw new Error(`invalid port: ${raw}`);
@@ -1503,7 +1508,7 @@ var parsePort = (raw) => {
1503
1508
  };
1504
1509
  program.command("init").description("interactive first-run wizard: data location, port, and public URL").action(init);
1505
1510
  program.command("install").description("install the server artifact (token \u2192 gated download, or --from a local tarball)").option("--token <token>", "distribution token (cabdist_\u2026) \u2014 prompted if omitted").option("--from <tarball>", "install from a local artifact tarball instead of downloading").option("--dist-base <url>", "distribution origin to fetch from (default https://dist.cabane.ai)").option("--version <version>", "install a specific published version (default: latest)").option("--port <port>", "local port the server will listen on (default 3000)", parsePort).option("--force", "reinstall even if this version is already present").action(install);
1506
- program.command("up").description("start + supervise the stack (Postgres + server)").option("--daemon", "run in the background (terminal returns; stop with `cabane down`)").option("--port <port>", "override the configured port", parsePort).action(up);
1511
+ program.command("up").description("start + supervise the stack (Postgres + server)").option("--daemon", "run in the background (terminal returns; stop with `cabane-server down`)").option("--port <port>", "override the configured port", parsePort).action(up);
1507
1512
  program.command("setup-agent").description("after browser signup: confirm your account and print companion-pairing guidance").option("--token <token>", "a Cabane access token (cab_\u2026) \u2014 prompted if omitted").action(setupAgent);
1508
1513
  program.command("update").description("install a newer published artifact (keeps the previous for rollback)").option("--token <token>", "distribution token (cabdist_\u2026) \u2014 defaults to the stored one").option("--dist-base <url>", "distribution origin to fetch from").option("--version <version>", "install a specific version instead of latest").action(update);
1509
1514
  program.command("set-env [pairs...]").description(
package/package.json CHANGED
@@ -1,8 +1,8 @@
1
1
  {
2
2
  "name": "@cabane/cli",
3
- "version": "0.1.10",
3
+ "version": "0.2.0",
4
4
  "type": "module",
5
- "description": "The cabane CLI — install, run, and update a self-hosted Cabane on your own machine (server + embedded Postgres; agents run on a companion you pair).",
5
+ "description": "The cabane-server CLI — install, run, and update a self-hosted Cabane on your own machine (server + embedded Postgres; agents run on a companion you pair).",
6
6
  "license": "UNLICENSED",
7
7
  "homepage": "https://cabane.ai",
8
8
  "repository": {
@@ -16,7 +16,7 @@
16
16
  "cli"
17
17
  ],
18
18
  "bin": {
19
- "cabane": "dist/cli.js"
19
+ "cabane-server": "dist/cli.js"
20
20
  },
21
21
  "main": "./dist/cli.js",
22
22
  "files": [