@justfortytwo/installer 1.0.0-0 → 1.0.0-10

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 (57) hide show
  1. package/README.md +163 -11
  2. package/dist/commands/doctor.d.ts +2 -0
  3. package/dist/commands/doctor.d.ts.map +1 -1
  4. package/dist/commands/doctor.js +11 -8
  5. package/dist/commands/doctor.js.map +1 -1
  6. package/dist/commands/forget.d.ts.map +1 -1
  7. package/dist/commands/forget.js +6 -4
  8. package/dist/commands/forget.js.map +1 -1
  9. package/dist/commands/init.d.ts +86 -0
  10. package/dist/commands/init.d.ts.map +1 -1
  11. package/dist/commands/init.js +254 -56
  12. package/dist/commands/init.js.map +1 -1
  13. package/dist/commands/pair.d.ts +8 -0
  14. package/dist/commands/pair.d.ts.map +1 -1
  15. package/dist/commands/pair.js +37 -3
  16. package/dist/commands/pair.js.map +1 -1
  17. package/dist/commands/start.d.ts +2 -0
  18. package/dist/commands/start.d.ts.map +1 -0
  19. package/dist/commands/start.js +35 -0
  20. package/dist/commands/start.js.map +1 -0
  21. package/dist/commands/status.d.ts +14 -0
  22. package/dist/commands/status.d.ts.map +1 -0
  23. package/dist/commands/status.js +54 -0
  24. package/dist/commands/status.js.map +1 -0
  25. package/dist/commands/stop.d.ts +4 -0
  26. package/dist/commands/stop.d.ts.map +1 -0
  27. package/dist/commands/stop.js +34 -0
  28. package/dist/commands/stop.js.map +1 -0
  29. package/dist/commands/update.d.ts +6 -2
  30. package/dist/commands/update.d.ts.map +1 -1
  31. package/dist/commands/update.js +50 -11
  32. package/dist/commands/update.js.map +1 -1
  33. package/dist/engine.d.ts +32 -8
  34. package/dist/engine.d.ts.map +1 -1
  35. package/dist/engine.js +121 -29
  36. package/dist/engine.js.map +1 -1
  37. package/dist/index.d.ts +2 -2
  38. package/dist/index.d.ts.map +1 -1
  39. package/dist/index.js +23 -6
  40. package/dist/index.js.map +1 -1
  41. package/dist/oneiros.d.ts +2 -0
  42. package/dist/oneiros.d.ts.map +1 -0
  43. package/dist/oneiros.js +28 -0
  44. package/dist/oneiros.js.map +1 -0
  45. package/dist/render.d.ts +4 -3
  46. package/dist/render.d.ts.map +1 -1
  47. package/dist/render.js +13 -10
  48. package/dist/render.js.map +1 -1
  49. package/dist/runtime.d.ts +75 -0
  50. package/dist/runtime.d.ts.map +1 -0
  51. package/dist/runtime.js +219 -0
  52. package/dist/runtime.js.map +1 -0
  53. package/dist/shim.d.ts +52 -0
  54. package/dist/shim.d.ts.map +1 -0
  55. package/dist/shim.js +163 -0
  56. package/dist/shim.js.map +1 -0
  57. package/package.json +7 -31
@@ -0,0 +1,35 @@
1
+ // start — run fortytwo's long-running services in the foreground.
2
+ //
3
+ // Loads the project .env (the shell/container env wins over it), starts every
4
+ // service that is installed and configured (the Telegram bridge needs
5
+ // TELEGRAM_BOT_TOKEN; the scheduler needs nothing) and supervises them until
6
+ // Ctrl+C / SIGTERM or until one exits — see runtime.ts. Never daemonizes: use it
7
+ // directly as the container/service command (`fortytwo start`) and let
8
+ // Docker/Podman/systemd own restarts. The services' own bins
9
+ // (fortytwo-telegram-bridge, fortytwo-scheduler) stay available for debugging.
10
+ import { existsSync, readFileSync } from 'node:fs';
11
+ import { join } from 'node:path';
12
+ import { parseEnvContent } from './init.js';
13
+ import { buildServiceEnv, liveRuntime, planServices, supervise } from '../runtime.js';
14
+ export async function runStart(_argv) {
15
+ const root = process.cwd();
16
+ const running = liveRuntime(root);
17
+ if (running) {
18
+ process.stderr.write(`start: fortytwo is already running (pid ${running.pid}). Stop it with \`fortytwo stop\`.\n`);
19
+ return 1;
20
+ }
21
+ const envPath = join(root, '.env');
22
+ const fileEnv = existsSync(envPath) ? parseEnvContent(readFileSync(envPath, 'utf8')) : {};
23
+ const env = buildServiceEnv(process.env, fileEnv, root);
24
+ const { run, skipped } = planServices(root, env);
25
+ for (const s of skipped)
26
+ process.stdout.write(`[fortytwo] ${s.name}: not started (${s.reason})\n`);
27
+ if (run.length === 0) {
28
+ process.stderr.write('start: no fortytwo service can run here. Run `fortytwo init` in this project first, ' +
29
+ 'and set TELEGRAM_BOT_TOKEN in .env for the Telegram channel.\n');
30
+ return 1;
31
+ }
32
+ process.stdout.write(`[fortytwo] starting ${run.map((s) => s.name).join(' + ')} (Ctrl+C to stop)\n`);
33
+ return supervise(run, { root, env, skipped });
34
+ }
35
+ //# sourceMappingURL=start.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"start.js","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"AAAA,kEAAkE;AAClE,EAAE;AACF,8EAA8E;AAC9E,sEAAsE;AACtE,6EAA6E;AAC7E,iFAAiF;AACjF,uEAAuE;AACvE,6DAA6D;AAC7D,+EAA+E;AAE/E,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AACnD,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAC5C,OAAO,EAAE,eAAe,EAAE,WAAW,EAAE,YAAY,EAAE,SAAS,EAAE,MAAM,eAAe,CAAC;AAEtF,MAAM,CAAC,KAAK,UAAU,QAAQ,CAAC,KAAe;IAC5C,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC;IAC3B,MAAM,OAAO,GAAG,WAAW,CAAC,IAAI,CAAC,CAAC;IAClC,IAAI,OAAO,EAAE,CAAC;QACZ,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,2CAA2C,OAAO,CAAC,GAAG,sCAAsC,CAAC,CAAC;QACnH,OAAO,CAAC,CAAC;IACX,CAAC;IACD,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;IACnC,MAAM,OAAO,GAAG,UAAU,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,eAAe,CAAC,YAAY,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;IAC1F,MAAM,GAAG,GAAG,eAAe,CAAC,OAAO,CAAC,GAAG,EAAE,OAAO,EAAE,IAAI,CAAC,CAAC;IACxD,MAAM,EAAE,GAAG,EAAE,OAAO,EAAE,GAAG,YAAY,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;IACjD,KAAK,MAAM,CAAC,IAAI,OAAO;QAAE,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,cAAc,CAAC,CAAC,IAAI,kBAAkB,CAAC,CAAC,MAAM,KAAK,CAAC,CAAC;IACnG,IAAI,GAAG,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACrB,OAAO,CAAC,MAAM,CAAC,KAAK,CAClB,sFAAsF;YACtF,gEAAgE,CACjE,CAAC;QACF,OAAO,CAAC,CAAC;IACX,CAAC;IACD,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,uBAAuB,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,qBAAqB,CAAC,CAAC;IACrG,OAAO,SAAS,CAAC,GAAG,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,OAAO,EAAE,CAAC,CAAC;AAChD,CAAC"}
@@ -0,0 +1,14 @@
1
+ import { type RuntimeState } from '../runtime.js';
2
+ export interface StatusInput {
3
+ runtime: RuntimeState | null;
4
+ schedulerHeartbeat: {
5
+ pid: number;
6
+ ts: string;
7
+ } | null;
8
+ memoryConfigured: boolean;
9
+ nowMs: number;
10
+ }
11
+ /** The status lines (pure, for tests). */
12
+ export declare function statusLines(i: StatusInput): string[];
13
+ export declare function runStatus(_argv: string[]): Promise<number>;
14
+ //# sourceMappingURL=status.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"status.d.ts","sourceRoot":"","sources":["../../src/commands/status.ts"],"names":[],"mappings":"AAWA,OAAO,EAA+B,KAAK,YAAY,EAAE,MAAM,eAAe,CAAC;AAG/E,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,YAAY,GAAG,IAAI,CAAC;IAC7B,kBAAkB,EAAE;QAAE,GAAG,EAAE,MAAM,CAAC;QAAC,EAAE,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IACvD,gBAAgB,EAAE,OAAO,CAAC;IAC1B,KAAK,EAAE,MAAM,CAAC;CACf;AAED,0CAA0C;AAC1C,wBAAgB,WAAW,CAAC,CAAC,EAAE,WAAW,GAAG,MAAM,EAAE,CAkBpD;AAaD,wBAAsB,SAAS,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,CAAC,CAWhE"}
@@ -0,0 +1,54 @@
1
+ // status — is fortytwo running, and which of its services?
2
+ //
3
+ // Reads what already exists instead of searching for processes: the runtime
4
+ // state `fortytwo start` keeps in .fortytwo/runtime.json (Telegram bridge), the
5
+ // scheduler's own heartbeat file (so a scheduler run by hand shows up too), and
6
+ // .mcp.json for memory, which Claude Code itself starts on demand.
7
+ // Exit code: 0 when `fortytwo start` is running, 3 when it is not (LSB "not
8
+ // running"), so `fortytwo status` works as a container health check.
9
+ import { existsSync, readFileSync } from 'node:fs';
10
+ import { join } from 'node:path';
11
+ import { liveRuntime, serviceRunning } from '../runtime.js';
12
+ import { defaultDoctorDeps, HEARTBEAT_STALE_MS } from './doctor.js';
13
+ /** The status lines (pure, for tests). */
14
+ export function statusLines(i) {
15
+ const row = (label, value) => `${label.padEnd(11)}${value}`;
16
+ const lines = [];
17
+ lines.push(row('Fortytwo', i.runtime ? `running (pid ${i.runtime.pid}, since ${i.runtime.startedAt})` : 'not running (start it with `fortytwo start`)'));
18
+ const skippedTg = i.runtime?.skipped.find((s) => s.name === 'telegram');
19
+ lines.push(row('Telegram', serviceRunning(i.runtime, 'telegram') ? 'running'
20
+ : skippedTg ? `not started (${skippedTg.reason})`
21
+ : 'not running'));
22
+ const hb = i.schedulerHeartbeat;
23
+ const age = hb ? i.nowMs - new Date(hb.ts).getTime() : Infinity;
24
+ lines.push(row('Scheduler', hb && age <= HEARTBEAT_STALE_MS ? `running (heartbeat ${Math.max(0, Math.round(age / 1000))}s ago)`
25
+ : hb ? `not running (last heartbeat ${hb.ts})`
26
+ : 'not running'));
27
+ lines.push(row('Memory', i.memoryConfigured ? 'configured via MCP (Claude Code starts it on demand)' : 'not configured (run `fortytwo init`)'));
28
+ return lines;
29
+ }
30
+ function memoryConfigured(root) {
31
+ const path = join(root, '.mcp.json');
32
+ if (!existsSync(path))
33
+ return false;
34
+ try {
35
+ const cfg = JSON.parse(readFileSync(path, 'utf8'));
36
+ return !!cfg.mcpServers?.['fortytwo-memory'];
37
+ }
38
+ catch {
39
+ return false;
40
+ }
41
+ }
42
+ export async function runStatus(_argv) {
43
+ const root = process.cwd();
44
+ const runtime = liveRuntime(root);
45
+ const lines = statusLines({
46
+ runtime,
47
+ schedulerHeartbeat: defaultDoctorDeps().schedulerHeartbeat(),
48
+ memoryConfigured: memoryConfigured(root),
49
+ nowMs: Date.now(),
50
+ });
51
+ process.stdout.write(lines.join('\n') + '\n');
52
+ return runtime ? 0 : 3;
53
+ }
54
+ //# sourceMappingURL=status.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"status.js","sourceRoot":"","sources":["../../src/commands/status.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ export declare function runStop(_argv: string[], opts?: {
2
+ timeoutMs?: number;
3
+ }): Promise<number>;
4
+ //# sourceMappingURL=stop.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stop.d.ts","sourceRoot":"","sources":["../../src/commands/stop.ts"],"names":[],"mappings":"AAWA,wBAAsB,OAAO,CAAC,KAAK,EAAE,MAAM,EAAE,EAAE,IAAI,GAAE;IAAE,SAAS,CAAC,EAAE,MAAM,CAAA;CAAO,GAAG,OAAO,CAAC,MAAM,CAAC,CAuBjG"}
@@ -0,0 +1,34 @@
1
+ // stop — stop a `fortytwo start` running for this project.
2
+ //
3
+ // Signals ONLY the supervisor recorded in .fortytwo/runtime.json, and only while
4
+ // its heartbeat is fresh (see runtime.ts), so a stale file can never hit a
5
+ // reused pid. It never searches for or kills processes by name. The supervisor
6
+ // then stops its own services. Under Docker/systemd prefer their own stop.
7
+ import { isPidAlive, liveRuntime } from '../runtime.js';
8
+ const sleep = (ms) => new Promise((r) => setTimeout(r, ms));
9
+ export async function runStop(_argv, opts = {}) {
10
+ const runtime = liveRuntime(process.cwd());
11
+ if (!runtime) {
12
+ process.stdout.write('fortytwo is not running.\n');
13
+ return 0;
14
+ }
15
+ process.stdout.write(`Stopping fortytwo (pid ${runtime.pid})…\n`);
16
+ try {
17
+ process.kill(runtime.pid, 'SIGTERM');
18
+ }
19
+ catch (err) {
20
+ process.stderr.write(`stop: could not signal pid ${runtime.pid}: ${err.message}\n`);
21
+ return 1;
22
+ }
23
+ const deadline = Date.now() + (opts.timeoutMs ?? 20_000);
24
+ while (Date.now() < deadline) {
25
+ if (!isPidAlive(runtime.pid)) {
26
+ process.stdout.write('fortytwo stopped.\n');
27
+ return 0;
28
+ }
29
+ await sleep(200);
30
+ }
31
+ process.stderr.write(`stop: fortytwo (pid ${runtime.pid}) is still running after SIGTERM.\n`);
32
+ return 1;
33
+ }
34
+ //# sourceMappingURL=stop.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stop.js","sourceRoot":"","sources":["../../src/commands/stop.ts"],"names":[],"mappings":"AAAA,2DAA2D;AAC3D,EAAE;AACF,iFAAiF;AACjF,2EAA2E;AAC3E,+EAA+E;AAC/E,2EAA2E;AAE3E,OAAO,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAExD,MAAM,KAAK,GAAG,CAAC,EAAU,EAAE,EAAE,CAAC,IAAI,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,UAAU,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;AAEpE,MAAM,CAAC,KAAK,UAAU,OAAO,CAAC,KAAe,EAAE,OAA+B,EAAE;IAC9E,MAAM,OAAO,GAAG,WAAW,CAAC,OAAO,CAAC,GAAG,EAAE,CAAC,CAAC;IAC3C,IAAI,CAAC,OAAO,EAAE,CAAC;QACb,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,4BAA4B,CAAC,CAAC;QACnD,OAAO,CAAC,CAAC;IACX,CAAC;IACD,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,0BAA0B,OAAO,CAAC,GAAG,MAAM,CAAC,CAAC;IAClE,IAAI,CAAC;QACH,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,SAAS,CAAC,CAAC;IACvC,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,8BAA8B,OAAO,CAAC,GAAG,KAAM,GAAa,CAAC,OAAO,IAAI,CAAC,CAAC;QAC/F,OAAO,CAAC,CAAC;IACX,CAAC;IACD,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,IAAI,CAAC,SAAS,IAAI,MAAM,CAAC,CAAC;IACzD,OAAO,IAAI,CAAC,GAAG,EAAE,GAAG,QAAQ,EAAE,CAAC;QAC7B,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC;YAC7B,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,qBAAqB,CAAC,CAAC;YAC5C,OAAO,CAAC,CAAC;QACX,CAAC;QACD,MAAM,KAAK,CAAC,GAAG,CAAC,CAAC;IACnB,CAAC;IACD,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,uBAAuB,OAAO,CAAC,GAAG,qCAAqC,CAAC,CAAC;IAC9F,OAAO,CAAC,CAAC;AACX,CAAC"}
@@ -11,7 +11,11 @@ export interface InstallResult {
11
11
  detail: string;
12
12
  }
13
13
  export interface UpdateDeps {
14
+ /** Running CLI, not the target project package; optional for embedded callers. */
15
+ runningInstallerVersion?: () => string | null;
16
+ persistInstaller?: (exactSpec: string) => InstallResult;
14
17
  readState: () => InstallState | null;
18
+ runtimeActive?: () => boolean;
15
19
  installedVersion: (spec: string) => string | null;
16
20
  /** spec -> declared semver range (this CLI's fortytwo.compat). */
17
21
  compatRanges: Record<string, string>;
@@ -26,8 +30,8 @@ export interface UpdateDeps {
26
30
  }>;
27
31
  /** Persist the resolved set, rotating current -> previous. */
28
32
  record: (pins: VersionPin[]) => void;
29
- /** Re-render the persona scaffold (idempotent). */
30
- render: () => void;
33
+ /** Reconcile machine-owned runtime assets; never render persona context. */
34
+ reconcile: () => Promise<void>;
31
35
  out: (s: string) => void;
32
36
  err: (s: string) => void;
33
37
  }
@@ -1 +1 @@
1
- {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../src/commands/update.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../src/commands/update.ts"],"names":[],"mappings":"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"}
@@ -9,17 +9,20 @@
9
9
  // the install lands, so rollback always targets the set that was running.
10
10
  // 4. POST-VERIFY with doctor. On failure: leave the new set in place but LOUDLY
11
11
  // point at `fortytwo rollback` — rollback is MANUAL by design (never auto-
12
- // revert, so the user can inspect first). On success: re-render the persona
13
- // scaffold (idempotent) in case a new template version shipped.
12
+ // revert, so the user can inspect first). On success: reconcile machine-owned runtime assets only.
13
+ // Existing context is never re-rendered by update.
14
14
  //
15
15
  // rollback re-installs state.json's `previous` set and rotates the ledger back.
16
16
  // Both share the resolve/install primitives below and are unit-tested through an
17
17
  // injected `*Deps` (so no test touches the network or the real npm).
18
18
  import { spawnSync } from 'node:child_process';
19
- import { recordVersionSet, readState, readIdentity, } from '../state.js';
20
- import { compareSemver, readInstalledVersion, readSelfCompatRanges, satisfiesRange } from '../engine.js';
19
+ import { isPidAlive, liveRuntime } from '../runtime.js';
20
+ import { HEARTBEAT_STALE_MS } from './doctor.js';
21
+ import { recordVersionSet, readState, } from '../state.js';
22
+ import { compareSemver, readInstalledVersion, readSelfCompatRanges, readSelfVersion, satisfiesRange } from '../engine.js';
21
23
  import { runDoctorChecks, defaultDoctorDeps } from './doctor.js';
22
- import { renderPersona } from '../render.js';
24
+ import { reconcileOneiros } from '../oneiros.js';
25
+ import { readProjectSetting, DEFAULT_DB_PATH, CLI_PACKAGE, cliInstallSpec } from './init.js';
23
26
  // --- pure: pick the latest published version satisfying a range ---
24
27
  /** Semver precedence (-1 / 0 / 1), pre-release aware (`1.0.0-0 < 1.0.0`). */
25
28
  export function compareVersions(a, b) {
@@ -54,6 +57,33 @@ export async function performUpdate(deps, flags) {
54
57
  deps.err('update: no install found — run `fortytwo init` first.\n');
55
58
  return 2;
56
59
  }
60
+ if (!flags.dryRun && deps.runtimeActive?.()) {
61
+ deps.err('update: stop the running runtime first (`fortytwo stop`, or your service manager), run `fortytwo update`, then `fortytwo start`. No packages or context were changed.\n');
62
+ return 1;
63
+ }
64
+ if (deps.runningInstallerVersion) {
65
+ const running = deps.runningInstallerVersion();
66
+ const installed = deps.installedVersion(CLI_PACKAGE);
67
+ if (!running || !deps.persistInstaller) {
68
+ deps.err('update: cannot determine or persist the running installer version.\n');
69
+ return 1;
70
+ }
71
+ if (installed && compareVersions(running, installed) < 0) {
72
+ deps.err('update: the project installer is newer than this command. Use the project-local fortytwo update.\n');
73
+ return 1;
74
+ }
75
+ const spec = cliInstallSpec(running, installed);
76
+ if (spec) {
77
+ deps.out(`update: pin project installer to ${spec}${flags.dryRun ? ' (dry-run)' : ''}\n`);
78
+ if (!flags.dryRun) {
79
+ const result = deps.persistInstaller(spec);
80
+ if (!result.ok) {
81
+ deps.err(`update: installer persistence failed (${result.detail}). Retry update before starting services.\n`);
82
+ return 1;
83
+ }
84
+ }
85
+ }
86
+ }
57
87
  // The engine = the declared compat siblings that are CURRENTLY installed. We
58
88
  // upgrade what's there; we don't pull in siblings the user deliberately omitted.
59
89
  const ranges = {};
@@ -73,6 +103,8 @@ export async function performUpdate(deps, flags) {
73
103
  const versionOf = (pins, name) => pins.find((p) => p.name === name)?.resolved;
74
104
  const changed = target.filter((t) => versionOf(current, t.name) !== t.resolved);
75
105
  if (changed.length === 0) {
106
+ if (!flags.dryRun)
107
+ await deps.reconcile();
76
108
  deps.out('update: already at the latest in-range version:\n' +
77
109
  current.map((p) => ` ${p.name}@${p.resolved} (${p.range})`).join('\n') + '\n');
78
110
  return 0;
@@ -101,8 +133,8 @@ export async function performUpdate(deps, flags) {
101
133
  deps.err('\nupdate: installed, but doctor reports required checks FAILED. Inspect, then run `fortytwo rollback` to restore the previous set.\n');
102
134
  return 1;
103
135
  }
104
- deps.render();
105
- deps.out('\nupdate: healthy — engine upgraded.\n');
136
+ await deps.reconcile();
137
+ deps.out('\nupdate: healthy — engine upgraded. Start services with `fortytwo start` (or your service manager).\n');
106
138
  return 0;
107
139
  }
108
140
  export async function performRollback(deps) {
@@ -144,8 +176,8 @@ export function fetchPublishedVersions(pkg) {
144
176
  }
145
177
  });
146
178
  }
147
- function npmInstall(specs, root) {
148
- const res = spawnSync('npm', ['install', '--no-audit', '--no-fund', ...specs], { cwd: root, stdio: 'inherit' });
179
+ function npmInstall(specs, root, flags = []) {
180
+ const res = spawnSync('npm', ['install', '--no-audit', '--no-fund', ...flags, ...specs], { cwd: root, stdio: 'inherit' });
149
181
  if (res.status === 0)
150
182
  return { ok: true, detail: 'ok' };
151
183
  return { ok: false, detail: res.error ? res.error.message : `npm exited ${res.status}` };
@@ -156,15 +188,22 @@ function parseUpdateArgs(argv) {
156
188
  export async function runUpdate(argv) {
157
189
  const root = process.cwd();
158
190
  const deps = {
191
+ runningInstallerVersion: readSelfVersion,
192
+ persistInstaller: (spec) => npmInstall([spec], root, ['--save-exact']),
159
193
  readState: () => readState(root),
194
+ runtimeActive: () => {
195
+ if (liveRuntime(root))
196
+ return true;
197
+ const heartbeat = defaultDoctorDeps().schedulerHeartbeat();
198
+ return !!heartbeat && Date.now() - Date.parse(heartbeat.ts) <= HEARTBEAT_STALE_MS && isPidAlive(heartbeat.pid);
199
+ },
160
200
  installedVersion: readInstalledVersion,
161
201
  compatRanges: readSelfCompatRanges(),
162
202
  fetchVersions: fetchPublishedVersions,
163
203
  install: (specs) => npmInstall(specs, root),
164
204
  doctor: () => runDoctorChecks(defaultDoctorDeps()),
165
205
  record: (pins) => { recordVersionSet(pins, root); },
166
- render: () => { const id = readIdentity(root); if (id)
167
- renderPersona(id, { root }); },
206
+ reconcile: () => reconcileOneiros(root, readProjectSetting('DB_PATH', root) ?? DEFAULT_DB_PATH),
168
207
  out: (s) => process.stdout.write(s),
169
208
  err: (s) => process.stderr.write(s),
170
209
  };
@@ -1 +1 @@
1
- {"version":3,"file":"update.js","sourceRoot":"","sources":["../../src/commands/update.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"update.js","sourceRoot":"","sources":["../../src/commands/update.ts"],"names":[],"mappings":"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"}
package/dist/engine.d.ts CHANGED
@@ -1,5 +1,22 @@
1
- /** Dynamically import an engine sibling; null if it is not installed. */
2
- export declare function loadSibling<T = Record<string, unknown>>(spec: string): Promise<T | null>;
1
+ /**
2
+ * Directory of an installed sibling, found by walking up `<dir>/node_modules`
3
+ * from the project root exactly like Node's resolver; null if absent. Pure fs,
4
+ * so import-only `exports` maps (gate, telegram) can't defeat it the way they
5
+ * defeat require.resolve.
6
+ */
7
+ export declare function findSiblingDir(spec: string, projectRoot?: string): string | null;
8
+ /**
9
+ * The ESM entry file of a package's root export, relative to its dir: `exports`
10
+ * (string, `"."`, or a bare conditions object; conditions `import` > `node` >
11
+ * `default`, nested allowed), then `main`, then `index.js`. Null if the root is
12
+ * not exported for import.
13
+ */
14
+ export declare function resolveEsmEntry(pkg: {
15
+ exports?: unknown;
16
+ main?: unknown;
17
+ }): string | null;
18
+ /** Dynamically import an engine sibling from the project; null if it is not installed. */
19
+ export declare function loadSibling<T = Record<string, unknown>>(spec: string, projectRoot?: string): Promise<T | null>;
3
20
  export declare const loadGate: () => Promise<{
4
21
  POLICY_SCHEMA_VERSION?: number;
5
22
  } | null>;
@@ -16,13 +33,12 @@ export declare const loadMemory: () => Promise<{
16
33
  } | null>;
17
34
  export declare const loadTelegram: () => Promise<Record<string, unknown> | null>;
18
35
  /**
19
- * Installed version of a sibling (its package.json `version`), or null. Walks up
20
- * ancestor `node_modules` dirs exactly like Node's resolver — pure fs, so it is
21
- * immune to import-only `exports` maps (which defeat require.resolve) and to
22
- * bundled test runners where import.meta.resolve is unavailable. Matches where
23
- * loadSibling's dynamic import would find the package.
36
+ * Installed version of a sibling in the project (its package.json `version`), or
37
+ * null. Same lookup as loadSibling, so the two always agree.
24
38
  */
25
- export declare function readInstalledVersion(spec: string): string | null;
39
+ export declare function readInstalledVersion(spec: string, projectRoot?: string): string | null;
40
+ /** This CLI's own version (package.json `version`), or null. */
41
+ export declare function readSelfVersion(): string | null;
26
42
  /** The CLI's declared compat ranges (package.json `fortytwo.compat`). */
27
43
  export declare function readSelfCompatRanges(): Record<string, string>;
28
44
  /**
@@ -42,6 +58,14 @@ export declare function compareSemver(a: string, b: string): number;
42
58
  export declare function satisfiesRange(version: string, range: string): boolean;
43
59
  /** GET {baseUrl}/api/tags; return installed model names, or null if unreachable. */
44
60
  export declare function fetchOllamaModels(baseUrl: string): Promise<string[] | null>;
61
+ /**
62
+ * POST {baseUrl}/api/pull and wait for it to finish. Talks to the server over
63
+ * HTTP — not the local `ollama` CLI, which only reaches localhost — so a remote
64
+ * or sibling-container endpoint works. Streams progress (so a multi-minute pull
65
+ * never sits idle long enough to trip fetch's timeouts). Returns null on success,
66
+ * else a short error.
67
+ */
68
+ export declare function pullOllamaModel(baseUrl: string, model: string): Promise<string | null>;
45
69
  export type MigrationState = 'ok' | 'missing' | 'pending' | 'unavailable';
46
70
  /**
47
71
  * Migration health for the memory DB: 'missing' (no DB file → run init),
@@ -1 +1 @@
1
- {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AAWA,yEAAyE;AACzE,wBAAsB,WAAW,CAAC,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAM9F;AAED,eAAO,MAAM,QAAQ;4BAA+C,MAAM;SAAyB,CAAC;AACpG,eAAO,MAAM,UAAU;mCAEY,MAAM;aAG5B,CAAC,IAAI,EAAE,MAAM,KAAK;QAAE,CAAC,EAAE;YAAE,MAAM,EAAE;gBAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAA;aAAE,CAAA;SAAE,CAAA;KAAE;oBAC1E,CAAC,CAAC,EAAE,OAAO,KAAK,OAAO,CAAC,IAAI,CAAC;SACrB,CAAC;AAC7B,eAAO,MAAM,YAAY,+CAA8C,CAAC;AAExE;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAgBhE;AAoBD,yEAAyE;AACzE,wBAAgB,oBAAoB,IAAI,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAI7D;AAWD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM,CA0B1D;AAED;;;;;;;GAOG;AACH,wBAAgB,cAAc,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAYtE;AAED,oFAAoF;AACpF,wBAAsB,iBAAiB,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,GAAG,IAAI,CAAC,CASjF;AAED,MAAM,MAAM,cAAc,GAAG,IAAI,GAAG,SAAS,GAAG,SAAS,GAAG,aAAa,CAAC;AAE1E;;;;GAIG;AACH,wBAAsB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC,CAehF"}
1
+ {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AAoBA;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,WAAW,GAAE,MAAsB,GAAG,MAAM,GAAG,IAAI,CAU/F;AAED;;;;;GAKG;AACH,wBAAgB,eAAe,CAAC,GAAG,EAAE;IAAE,OAAO,CAAC,EAAE,OAAO,CAAC;IAAC,IAAI,CAAC,EAAE,OAAO,CAAA;CAAE,GAAG,MAAM,GAAG,IAAI,CAoBzF;AAED,0FAA0F;AAC1F,wBAAsB,WAAW,CAAC,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC3D,IAAI,EAAE,MAAM,EACZ,WAAW,GAAE,MAAsB,GAClC,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAWnB;AAED,eAAO,MAAM,QAAQ;4BAA+C,MAAM;SAAyB,CAAC;AACpG,eAAO,MAAM,UAAU;mCAEY,MAAM;aAG5B,CAAC,IAAI,EAAE,MAAM,KAAK;QAAE,CAAC,EAAE;YAAE,MAAM,EAAE;gBAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAA;aAAE,CAAA;SAAE,CAAA;KAAE;oBAC1E,CAAC,CAAC,EAAE,OAAO,KAAK,OAAO,CAAC,IAAI,CAAC;SACrB,CAAC;AAC7B,eAAO,MAAM,YAAY,+CAA8C,CAAC;AAExE;;;GAGG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,EAAE,WAAW,GAAE,MAAsB,GAAG,MAAM,GAAG,IAAI,CAQrG;AAoBD,gEAAgE;AAChE,wBAAgB,eAAe,IAAI,MAAM,GAAG,IAAI,CAG/C;AAED,yEAAyE;AACzE,wBAAgB,oBAAoB,IAAI,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAI7D;AAWD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM,CA0B1D;AAED;;;;;;;GAOG;AACH,wBAAgB,cAAc,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAYtE;AAED,oFAAoF;AACpF,wBAAsB,iBAAiB,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,GAAG,IAAI,CAAC,CASjF;AAED;;;;;;GAMG;AACH,wBAAsB,eAAe,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAkB5F;AAED,MAAM,MAAM,cAAc,GAAG,IAAI,GAAG,SAAS,GAAG,SAAS,GAAG,aAAa,CAAC;AAE1E;;;;GAIG;AACH,wBAAsB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC,CAehF"}
package/dist/engine.js CHANGED
@@ -1,16 +1,79 @@
1
1
  // engine.ts — access to the optional @justfortytwo/* engine siblings.
2
2
  //
3
- // The installer declares the engine packages as OPTIONAL peerDependencies and
4
- // reaches them via dynamic import, so a partial install (e.g. gate-only) never
3
+ // The engine packages are NOT declared as dependencies or peerDependencies: their
4
+ // versions live only in package.json `fortytwo.compat` (installed by init, checked
5
+ // by doctor, moved by update). The CLI reaches them via dynamic import resolved
6
+ // from the project's node_modules, so a partial install (e.g. gate-only) never
5
7
  // crashes the CLI — a missing sibling makes the dependent command/check report
6
8
  // "not installed" instead of throwing.
7
9
  import { readFileSync, existsSync } from 'node:fs';
8
- import { fileURLToPath } from 'node:url';
9
- import { dirname, join, parse } from 'node:path';
10
- /** Dynamically import an engine sibling; null if it is not installed. */
11
- export async function loadSibling(spec) {
10
+ import { fileURLToPath, pathToFileURL } from 'node:url';
11
+ import { dirname, join, parse, resolve } from 'node:path';
12
+ // PROJECT-ROOTED RESOLUTION. Siblings live in the TARGET PROJECT's node_modules,
13
+ // never next to the installer: under `npx create-fortytwo` the installer runs from
14
+ // npm's exec cache (~/.npm/_npx/<hash>/node_modules), a separate tree. So every
15
+ // lookup below starts at the project root (the cwd every command operates on),
16
+ // not at import.meta.url — a bare `import(spec)` / `createRequire(import.meta.url)`
17
+ // would resolve from the exec cache and miss the engine `init` just installed.
18
+ /**
19
+ * Directory of an installed sibling, found by walking up `<dir>/node_modules`
20
+ * from the project root exactly like Node's resolver; null if absent. Pure fs,
21
+ * so import-only `exports` maps (gate, telegram) can't defeat it the way they
22
+ * defeat require.resolve.
23
+ */
24
+ export function findSiblingDir(spec, projectRoot = process.cwd()) {
25
+ const segments = spec.split('/'); // e.g. ['@justfortytwo', 'gate']
26
+ let dir = resolve(projectRoot);
27
+ const root = parse(dir).root;
28
+ while (true) {
29
+ const candidate = join(dir, 'node_modules', ...segments);
30
+ if (existsSync(join(candidate, 'package.json')))
31
+ return candidate;
32
+ if (dir === root)
33
+ return null;
34
+ dir = dirname(dir);
35
+ }
36
+ }
37
+ /**
38
+ * The ESM entry file of a package's root export, relative to its dir: `exports`
39
+ * (string, `"."`, or a bare conditions object; conditions `import` > `node` >
40
+ * `default`, nested allowed), then `main`, then `index.js`. Null if the root is
41
+ * not exported for import.
42
+ */
43
+ export function resolveEsmEntry(pkg) {
44
+ const pick = (target) => {
45
+ if (typeof target === 'string')
46
+ return target;
47
+ if (!target || typeof target !== 'object' || Array.isArray(target))
48
+ return null;
49
+ const conditions = target;
50
+ for (const c of ['import', 'node', 'default']) {
51
+ if (c in conditions) {
52
+ const hit = pick(conditions[c]);
53
+ if (hit)
54
+ return hit;
55
+ }
56
+ }
57
+ return null;
58
+ };
59
+ const { exports } = pkg;
60
+ if (exports !== undefined && exports !== null) {
61
+ const isSubpathMap = typeof exports === 'object' && !Array.isArray(exports) && Object.keys(exports).some((k) => k.startsWith('.'));
62
+ return pick(isSubpathMap ? exports['.'] : exports);
63
+ }
64
+ return typeof pkg.main === 'string' && pkg.main ? pkg.main : 'index.js';
65
+ }
66
+ /** Dynamically import an engine sibling from the project; null if it is not installed. */
67
+ export async function loadSibling(spec, projectRoot = process.cwd()) {
68
+ const dir = findSiblingDir(spec, projectRoot);
69
+ if (!dir)
70
+ return null;
12
71
  try {
13
- return (await import(spec));
72
+ const pkg = JSON.parse(readFileSync(join(dir, 'package.json'), 'utf8'));
73
+ const entry = resolveEsmEntry(pkg);
74
+ if (!entry)
75
+ return null;
76
+ return (await import(pathToFileURL(join(dir, entry)).href));
14
77
  }
15
78
  catch {
16
79
  return null;
@@ -20,29 +83,18 @@ export const loadGate = () => loadSibling('@justfortytwo/gate');
20
83
  export const loadMemory = () => loadSibling('@justfortytwo/memory');
21
84
  export const loadTelegram = () => loadSibling('@justfortytwo/telegram');
22
85
  /**
23
- * Installed version of a sibling (its package.json `version`), or null. Walks up
24
- * ancestor `node_modules` dirs exactly like Node's resolver — pure fs, so it is
25
- * immune to import-only `exports` maps (which defeat require.resolve) and to
26
- * bundled test runners where import.meta.resolve is unavailable. Matches where
27
- * loadSibling's dynamic import would find the package.
86
+ * Installed version of a sibling in the project (its package.json `version`), or
87
+ * null. Same lookup as loadSibling, so the two always agree.
28
88
  */
29
- export function readInstalledVersion(spec) {
30
- const segments = spec.split('/'); // e.g. ['@justfortytwo', 'gate']
31
- let dir = dirname(fileURLToPath(import.meta.url));
32
- const root = parse(dir).root;
33
- while (true) {
34
- const candidate = join(dir, 'node_modules', ...segments, 'package.json');
35
- if (existsSync(candidate)) {
36
- try {
37
- return JSON.parse(readFileSync(candidate, 'utf8')).version ?? null;
38
- }
39
- catch {
40
- return null;
41
- }
42
- }
43
- if (dir === root)
44
- return null;
45
- dir = dirname(dir);
89
+ export function readInstalledVersion(spec, projectRoot = process.cwd()) {
90
+ const dir = findSiblingDir(spec, projectRoot);
91
+ if (!dir)
92
+ return null;
93
+ try {
94
+ return JSON.parse(readFileSync(join(dir, 'package.json'), 'utf8')).version ?? null;
95
+ }
96
+ catch {
97
+ return null;
46
98
  }
47
99
  }
48
100
  /** Walk up from this module to find the installer's own package.json. */
@@ -64,6 +116,11 @@ function findSelfPackageJson() {
64
116
  dir = dirname(dir);
65
117
  }
66
118
  }
119
+ /** This CLI's own version (package.json `version`), or null. */
120
+ export function readSelfVersion() {
121
+ const v = findSelfPackageJson()?.version;
122
+ return typeof v === 'string' ? v : null;
123
+ }
67
124
  /** The CLI's declared compat ranges (package.json `fortytwo.compat`). */
68
125
  export function readSelfCompatRanges() {
69
126
  const pkg = findSelfPackageJson();
@@ -157,6 +214,41 @@ export async function fetchOllamaModels(baseUrl) {
157
214
  return null;
158
215
  }
159
216
  }
217
+ /**
218
+ * POST {baseUrl}/api/pull and wait for it to finish. Talks to the server over
219
+ * HTTP — not the local `ollama` CLI, which only reaches localhost — so a remote
220
+ * or sibling-container endpoint works. Streams progress (so a multi-minute pull
221
+ * never sits idle long enough to trip fetch's timeouts). Returns null on success,
222
+ * else a short error.
223
+ */
224
+ export async function pullOllamaModel(baseUrl, model) {
225
+ try {
226
+ const res = await fetch(`${baseUrl.replace(/\/$/, '')}/api/pull`, {
227
+ method: 'POST',
228
+ headers: { 'content-type': 'application/json' },
229
+ body: JSON.stringify({ model, name: model, stream: true }), // `name`: older Ollama servers
230
+ });
231
+ if (!res.ok)
232
+ return `HTTP ${res.status}`;
233
+ let last = {};
234
+ for (const line of (await res.text()).split('\n')) {
235
+ if (!line.trim())
236
+ continue;
237
+ try {
238
+ last = JSON.parse(line);
239
+ }
240
+ catch {
241
+ continue;
242
+ }
243
+ if (last.error)
244
+ return last.error;
245
+ }
246
+ return last.status === 'success' ? null : `pull ended with status "${last.status ?? 'unknown'}"`;
247
+ }
248
+ catch (err) {
249
+ return err.message;
250
+ }
251
+ }
160
252
  /**
161
253
  * Migration health for the memory DB: 'missing' (no DB file → run init),
162
254
  * 'ok' (the migrated `memories` table exists), 'pending' (DB present but not