@pleri/olam-cli 0.1.109 → 0.1.111
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/commands/completion.d.ts +30 -0
- package/dist/commands/completion.d.ts.map +1 -0
- package/dist/commands/completion.js +53 -0
- package/dist/commands/completion.js.map +1 -0
- package/dist/commands/init.d.ts +10 -0
- package/dist/commands/init.d.ts.map +1 -1
- package/dist/commands/init.js +10 -1
- package/dist/commands/init.js.map +1 -1
- package/dist/commands/setup.d.ts +71 -0
- package/dist/commands/setup.d.ts.map +1 -0
- package/dist/commands/setup.js +344 -0
- package/dist/commands/setup.js.map +1 -0
- package/dist/image-digests.json +1 -1
- package/dist/index.js +549 -121
- package/dist/index.js.map +1 -1
- package/dist/lib/completion-generator.d.ts +107 -0
- package/dist/lib/completion-generator.d.ts.map +1 -0
- package/dist/lib/completion-generator.js +226 -0
- package/dist/lib/completion-generator.js.map +1 -0
- package/dist/lib/shell-rc.d.ts +90 -0
- package/dist/lib/shell-rc.d.ts.map +1 -0
- package/dist/lib/shell-rc.js +91 -0
- package/dist/lib/shell-rc.js.map +1 -0
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -487,8 +487,8 @@ var init_parseUtil = __esm({
|
|
|
487
487
|
init_errors();
|
|
488
488
|
init_en();
|
|
489
489
|
makeIssue = (params) => {
|
|
490
|
-
const { data, path:
|
|
491
|
-
const fullPath = [...
|
|
490
|
+
const { data, path: path55, errorMaps, issueData } = params;
|
|
491
|
+
const fullPath = [...path55, ...issueData.path || []];
|
|
492
492
|
const fullIssue = {
|
|
493
493
|
...issueData,
|
|
494
494
|
path: fullPath
|
|
@@ -796,11 +796,11 @@ var init_types = __esm({
|
|
|
796
796
|
init_parseUtil();
|
|
797
797
|
init_util();
|
|
798
798
|
ParseInputLazyPath = class {
|
|
799
|
-
constructor(parent, value,
|
|
799
|
+
constructor(parent, value, path55, key) {
|
|
800
800
|
this._cachedPath = [];
|
|
801
801
|
this.parent = parent;
|
|
802
802
|
this.data = value;
|
|
803
|
-
this._path =
|
|
803
|
+
this._path = path55;
|
|
804
804
|
this._key = key;
|
|
805
805
|
}
|
|
806
806
|
get path() {
|
|
@@ -4281,7 +4281,7 @@ import YAML from "yaml";
|
|
|
4281
4281
|
function bootstrapStepCmd(entry) {
|
|
4282
4282
|
return typeof entry === "string" ? entry : entry.cmd;
|
|
4283
4283
|
}
|
|
4284
|
-
function refineForbiddenKeys(value,
|
|
4284
|
+
function refineForbiddenKeys(value, path55, ctx, rejectSource) {
|
|
4285
4285
|
if (value === null || typeof value !== "object" || Array.isArray(value)) {
|
|
4286
4286
|
return;
|
|
4287
4287
|
}
|
|
@@ -4289,12 +4289,12 @@ function refineForbiddenKeys(value, path53, ctx, rejectSource) {
|
|
|
4289
4289
|
if (FORBIDDEN_KEYS.has(key)) {
|
|
4290
4290
|
ctx.addIssue({
|
|
4291
4291
|
code: external_exports.ZodIssueCode.custom,
|
|
4292
|
-
path: [...
|
|
4292
|
+
path: [...path55, key],
|
|
4293
4293
|
message: `forbidden key "${key}" (prototype-pollution surface)`
|
|
4294
4294
|
});
|
|
4295
4295
|
continue;
|
|
4296
4296
|
}
|
|
4297
|
-
if (rejectSource &&
|
|
4297
|
+
if (rejectSource && path55.length === 0 && key === "source") {
|
|
4298
4298
|
ctx.addIssue({
|
|
4299
4299
|
code: external_exports.ZodIssueCode.custom,
|
|
4300
4300
|
path: ["source"],
|
|
@@ -4302,21 +4302,21 @@ function refineForbiddenKeys(value, path53, ctx, rejectSource) {
|
|
|
4302
4302
|
});
|
|
4303
4303
|
continue;
|
|
4304
4304
|
}
|
|
4305
|
-
refineForbiddenKeys(value[key], [...
|
|
4305
|
+
refineForbiddenKeys(value[key], [...path55, key], ctx, false);
|
|
4306
4306
|
}
|
|
4307
4307
|
}
|
|
4308
|
-
function rejectForbiddenKeys(value,
|
|
4308
|
+
function rejectForbiddenKeys(value, path55, rejectSource) {
|
|
4309
4309
|
if (value === null || typeof value !== "object" || Array.isArray(value)) {
|
|
4310
4310
|
return;
|
|
4311
4311
|
}
|
|
4312
4312
|
for (const key of Object.keys(value)) {
|
|
4313
4313
|
if (FORBIDDEN_KEYS.has(key)) {
|
|
4314
|
-
throw new Error(`[manifest] ${
|
|
4314
|
+
throw new Error(`[manifest] ${path55}: forbidden key "${key}" (prototype-pollution surface)`);
|
|
4315
4315
|
}
|
|
4316
4316
|
if (rejectSource && key === "source") {
|
|
4317
|
-
throw new Error(`[manifest] ${
|
|
4317
|
+
throw new Error(`[manifest] ${path55}: top-level "source" is loader-stamped \u2014 manifests must not author it`);
|
|
4318
4318
|
}
|
|
4319
|
-
rejectForbiddenKeys(value[key], `${
|
|
4319
|
+
rejectForbiddenKeys(value[key], `${path55}.${key}`, false);
|
|
4320
4320
|
}
|
|
4321
4321
|
}
|
|
4322
4322
|
function unknownTopLevelKeys(parsed) {
|
|
@@ -5309,8 +5309,8 @@ var init_client = __esm({
|
|
|
5309
5309
|
throw new Error(`failed to report rate-limit for ${accountId} (HTTP ${res.status})`);
|
|
5310
5310
|
}
|
|
5311
5311
|
}
|
|
5312
|
-
async request(method,
|
|
5313
|
-
const url = `${this.baseUrl}${
|
|
5312
|
+
async request(method, path55, body, attempt = 0) {
|
|
5313
|
+
const url = `${this.baseUrl}${path55}`;
|
|
5314
5314
|
const controller = new AbortController();
|
|
5315
5315
|
const timer = setTimeout(() => controller.abort(), this.timeoutMs);
|
|
5316
5316
|
const headers = {};
|
|
@@ -5328,7 +5328,7 @@ var init_client = __esm({
|
|
|
5328
5328
|
} catch (err) {
|
|
5329
5329
|
if (attempt < RETRY_COUNT && isTransient(err)) {
|
|
5330
5330
|
await sleep(RETRY_BACKOFF_MS * (attempt + 1));
|
|
5331
|
-
return this.request(method,
|
|
5331
|
+
return this.request(method, path55, body, attempt + 1);
|
|
5332
5332
|
}
|
|
5333
5333
|
throw err;
|
|
5334
5334
|
} finally {
|
|
@@ -6877,8 +6877,8 @@ var init_provider3 = __esm({
|
|
|
6877
6877
|
// -----------------------------------------------------------------------
|
|
6878
6878
|
// Internal fetch helper
|
|
6879
6879
|
// -----------------------------------------------------------------------
|
|
6880
|
-
async request(
|
|
6881
|
-
const url = `${this.config.workerUrl}${
|
|
6880
|
+
async request(path55, method, body) {
|
|
6881
|
+
const url = `${this.config.workerUrl}${path55}`;
|
|
6882
6882
|
const bearer = await this.config.mintToken();
|
|
6883
6883
|
const headers = {
|
|
6884
6884
|
Authorization: `Bearer ${bearer}`
|
|
@@ -8170,8 +8170,8 @@ import { execFileSync as execFileSync3 } from "node:child_process";
|
|
|
8170
8170
|
import * as fs14 from "node:fs";
|
|
8171
8171
|
import * as os9 from "node:os";
|
|
8172
8172
|
import * as path15 from "node:path";
|
|
8173
|
-
function expandHome(p,
|
|
8174
|
-
return p.replace(/^~(?=$|\/|\\)/,
|
|
8173
|
+
function expandHome(p, homedir30) {
|
|
8174
|
+
return p.replace(/^~(?=$|\/|\\)/, homedir30());
|
|
8175
8175
|
}
|
|
8176
8176
|
function sanitizeRepoFilename(name) {
|
|
8177
8177
|
const sanitized = name.replace(/[^A-Za-z0-9._-]/g, "_");
|
|
@@ -8194,7 +8194,7 @@ ${stderr}`;
|
|
|
8194
8194
|
}
|
|
8195
8195
|
function snapshotBaselineDiff(repos, workspacePath, deps = {}) {
|
|
8196
8196
|
const exec = deps.exec ?? ((cmd, args, opts) => execFileSync3(cmd, args, opts));
|
|
8197
|
-
const
|
|
8197
|
+
const homedir30 = deps.homedir ?? (() => os9.homedir());
|
|
8198
8198
|
const baselineDir = path15.join(workspacePath, ".olam", "baseline");
|
|
8199
8199
|
try {
|
|
8200
8200
|
fs14.mkdirSync(baselineDir, { recursive: true });
|
|
@@ -8210,7 +8210,7 @@ function snapshotBaselineDiff(repos, workspacePath, deps = {}) {
|
|
|
8210
8210
|
continue;
|
|
8211
8211
|
const filename = `${sanitizeRepoFilename(repo.name)}.diff`;
|
|
8212
8212
|
const outPath = path15.join(baselineDir, filename);
|
|
8213
|
-
const repoPath = expandHome(repo.path,
|
|
8213
|
+
const repoPath = expandHome(repo.path, homedir30);
|
|
8214
8214
|
if (!fs14.existsSync(repoPath)) {
|
|
8215
8215
|
writeBaselineFile(outPath, `# repo: ${repo.name}
|
|
8216
8216
|
# (skipped: path ${repoPath} does not exist)
|
|
@@ -13822,10 +13822,10 @@ async function readHostCpToken2() {
|
|
|
13822
13822
|
if (!fs25.existsSync(tp)) return null;
|
|
13823
13823
|
return fs25.readFileSync(tp, "utf-8").trim();
|
|
13824
13824
|
}
|
|
13825
|
-
async function callHostCpProxy(method, worldId,
|
|
13825
|
+
async function callHostCpProxy(method, worldId, path55, body) {
|
|
13826
13826
|
const token = await readHostCpToken2();
|
|
13827
13827
|
if (!token) return { ok: false, status: 0, error: "no token (host CP not started)" };
|
|
13828
|
-
const url = `http://127.0.0.1:${HOST_CP_PORT}/api/world/${encodeURIComponent(worldId)}${
|
|
13828
|
+
const url = `http://127.0.0.1:${HOST_CP_PORT}/api/world/${encodeURIComponent(worldId)}${path55}`;
|
|
13829
13829
|
try {
|
|
13830
13830
|
const headers = {
|
|
13831
13831
|
Authorization: `Bearer ${token}`
|
|
@@ -14285,7 +14285,7 @@ __export(machine_schema_exports, {
|
|
|
14285
14285
|
writeMachineConfig: () => writeMachineConfig
|
|
14286
14286
|
});
|
|
14287
14287
|
import * as fs41 from "node:fs";
|
|
14288
|
-
import * as
|
|
14288
|
+
import * as path47 from "node:path";
|
|
14289
14289
|
import * as os24 from "node:os";
|
|
14290
14290
|
import { parse as parseYaml5, stringify as stringifyYaml5 } from "yaml";
|
|
14291
14291
|
function readMachineConfig(configPath) {
|
|
@@ -14302,7 +14302,7 @@ function readMachineConfig(configPath) {
|
|
|
14302
14302
|
}
|
|
14303
14303
|
function writeMachineConfig(config, configPath) {
|
|
14304
14304
|
const p = configPath ?? DEFAULT_CONFIG_PATH;
|
|
14305
|
-
fs41.mkdirSync(
|
|
14305
|
+
fs41.mkdirSync(path47.dirname(p), { recursive: true });
|
|
14306
14306
|
fs41.writeFileSync(p, stringifyYaml5({ ...config }), { mode: 420 });
|
|
14307
14307
|
}
|
|
14308
14308
|
function initMachineConfig(opts = {}) {
|
|
@@ -14326,9 +14326,9 @@ var init_machine_schema = __esm({
|
|
|
14326
14326
|
channel: external_exports.enum(["stable", "beta", "edge"]).default("stable"),
|
|
14327
14327
|
auto_update: external_exports.boolean().default(true),
|
|
14328
14328
|
telemetry: external_exports.boolean().default(true),
|
|
14329
|
-
worlds_dir: external_exports.string().default(() =>
|
|
14329
|
+
worlds_dir: external_exports.string().default(() => path47.join(os24.homedir(), ".olam", "worlds"))
|
|
14330
14330
|
});
|
|
14331
|
-
DEFAULT_CONFIG_PATH =
|
|
14331
|
+
DEFAULT_CONFIG_PATH = path47.join(os24.homedir(), ".olam", "config.yaml");
|
|
14332
14332
|
}
|
|
14333
14333
|
});
|
|
14334
14334
|
|
|
@@ -14710,9 +14710,9 @@ var UnknownArchetypeError = class extends Error {
|
|
|
14710
14710
|
};
|
|
14711
14711
|
var ArchetypeCycleError = class extends Error {
|
|
14712
14712
|
path;
|
|
14713
|
-
constructor(
|
|
14714
|
-
super(`Archetype inheritance cycle detected: ${
|
|
14715
|
-
this.path =
|
|
14713
|
+
constructor(path55) {
|
|
14714
|
+
super(`Archetype inheritance cycle detected: ${path55.join(" \u2192 ")} \u2192 ${path55[0] ?? "?"}`);
|
|
14715
|
+
this.path = path55;
|
|
14716
14716
|
this.name = "ArchetypeCycleError";
|
|
14717
14717
|
}
|
|
14718
14718
|
};
|
|
@@ -15359,8 +15359,8 @@ function runStep(label, cmd, args, opts = {}) {
|
|
|
15359
15359
|
}
|
|
15360
15360
|
async function confirm(message) {
|
|
15361
15361
|
if (!process.stdin.isTTY) return true;
|
|
15362
|
-
const { createInterface:
|
|
15363
|
-
const rl =
|
|
15362
|
+
const { createInterface: createInterface6 } = await import("node:readline");
|
|
15363
|
+
const rl = createInterface6({ input: process.stdin, output: process.stdout });
|
|
15364
15364
|
return new Promise((resolve11) => {
|
|
15365
15365
|
rl.question(`${message} [y/N] `, (answer) => {
|
|
15366
15366
|
rl.close();
|
|
@@ -16093,9 +16093,9 @@ function formatFreshnessWarning(result, image = DEFAULT_DEVBOX_IMAGE) {
|
|
|
16093
16093
|
"These source files have changed since the image was built; the",
|
|
16094
16094
|
"changes will NOT take effect in fresh worlds until you rebuild:"
|
|
16095
16095
|
];
|
|
16096
|
-
for (const { path:
|
|
16096
|
+
for (const { path: path55, mtimeMs } of result.newerSources) {
|
|
16097
16097
|
const when = new Date(mtimeMs).toISOString();
|
|
16098
|
-
lines.push(` \u2022 ${
|
|
16098
|
+
lines.push(` \u2022 ${path55} (modified ${when})`);
|
|
16099
16099
|
}
|
|
16100
16100
|
lines.push("");
|
|
16101
16101
|
lines.push("Rebuild with:");
|
|
@@ -16256,9 +16256,9 @@ async function readHostCpTokenForCreate() {
|
|
|
16256
16256
|
try {
|
|
16257
16257
|
const { default: fs50 } = await import("node:fs");
|
|
16258
16258
|
const { default: os28 } = await import("node:os");
|
|
16259
|
-
const { default:
|
|
16260
|
-
const tp =
|
|
16261
|
-
process.env.OLAM_HOME ??
|
|
16259
|
+
const { default: path55 } = await import("node:path");
|
|
16260
|
+
const tp = path55.join(
|
|
16261
|
+
process.env.OLAM_HOME ?? path55.join(os28.homedir(), ".olam"),
|
|
16262
16262
|
"host-cp.token"
|
|
16263
16263
|
);
|
|
16264
16264
|
if (!fs50.existsSync(tp)) return null;
|
|
@@ -16627,8 +16627,8 @@ async function readHostCpToken3() {
|
|
|
16627
16627
|
try {
|
|
16628
16628
|
const { default: fs50 } = await import("node:fs");
|
|
16629
16629
|
const { default: os28 } = await import("node:os");
|
|
16630
|
-
const { default:
|
|
16631
|
-
const tp =
|
|
16630
|
+
const { default: path55 } = await import("node:path");
|
|
16631
|
+
const tp = path55.join(os28.homedir(), ".olam", "host-cp.token");
|
|
16632
16632
|
if (!fs50.existsSync(tp)) return null;
|
|
16633
16633
|
const raw = fs50.readFileSync(tp, "utf-8").trim();
|
|
16634
16634
|
return raw.length > 0 ? raw : null;
|
|
@@ -20361,11 +20361,11 @@ function zodIssueToError(issue, doc, lineCounter) {
|
|
|
20361
20361
|
suggestion: deriveSuggestion(issue)
|
|
20362
20362
|
};
|
|
20363
20363
|
}
|
|
20364
|
-
function formatJsonPath(
|
|
20365
|
-
if (
|
|
20364
|
+
function formatJsonPath(path55) {
|
|
20365
|
+
if (path55.length === 0)
|
|
20366
20366
|
return "<root>";
|
|
20367
20367
|
let out = "";
|
|
20368
|
-
for (const seg of
|
|
20368
|
+
for (const seg of path55) {
|
|
20369
20369
|
if (typeof seg === "number") {
|
|
20370
20370
|
out += `[${seg}]`;
|
|
20371
20371
|
} else {
|
|
@@ -20374,11 +20374,11 @@ function formatJsonPath(path53) {
|
|
|
20374
20374
|
}
|
|
20375
20375
|
return out;
|
|
20376
20376
|
}
|
|
20377
|
-
function resolveYamlLocation(
|
|
20377
|
+
function resolveYamlLocation(path55, doc, lineCounter) {
|
|
20378
20378
|
let bestLine = 0;
|
|
20379
20379
|
let bestColumn = 0;
|
|
20380
|
-
for (let depth =
|
|
20381
|
-
const segment =
|
|
20380
|
+
for (let depth = path55.length; depth >= 0; depth -= 1) {
|
|
20381
|
+
const segment = path55.slice(0, depth);
|
|
20382
20382
|
try {
|
|
20383
20383
|
const node = doc.getIn(segment, true);
|
|
20384
20384
|
if (node && typeof node === "object" && "range" in node) {
|
|
@@ -20596,11 +20596,11 @@ function topoSort(nodes) {
|
|
|
20596
20596
|
}
|
|
20597
20597
|
function traceCycle(start, byId) {
|
|
20598
20598
|
const seen = /* @__PURE__ */ new Set();
|
|
20599
|
-
const
|
|
20599
|
+
const path55 = [];
|
|
20600
20600
|
let current = start;
|
|
20601
20601
|
while (current && !seen.has(current)) {
|
|
20602
20602
|
seen.add(current);
|
|
20603
|
-
|
|
20603
|
+
path55.push(current);
|
|
20604
20604
|
const node = byId.get(current);
|
|
20605
20605
|
const next = node?.dependsOn[0];
|
|
20606
20606
|
if (next === void 0)
|
|
@@ -20608,10 +20608,10 @@ function traceCycle(start, byId) {
|
|
|
20608
20608
|
current = next;
|
|
20609
20609
|
}
|
|
20610
20610
|
if (current && seen.has(current)) {
|
|
20611
|
-
const idx =
|
|
20612
|
-
return [...
|
|
20611
|
+
const idx = path55.indexOf(current);
|
|
20612
|
+
return [...path55.slice(idx), current];
|
|
20613
20613
|
}
|
|
20614
|
-
return
|
|
20614
|
+
return path55;
|
|
20615
20615
|
}
|
|
20616
20616
|
|
|
20617
20617
|
// ../core/dist/executor/types.js
|
|
@@ -23018,8 +23018,8 @@ function performRollbackSwap(plan) {
|
|
|
23018
23018
|
}
|
|
23019
23019
|
async function confirm2(message) {
|
|
23020
23020
|
if (!process.stdin.isTTY) return true;
|
|
23021
|
-
const { createInterface:
|
|
23022
|
-
const rl =
|
|
23021
|
+
const { createInterface: createInterface6 } = await import("node:readline");
|
|
23022
|
+
const rl = createInterface6({ input: process.stdin, output: process.stdout });
|
|
23023
23023
|
return new Promise((resolve11) => {
|
|
23024
23024
|
rl.question(`${message} [y/N] `, (answer) => {
|
|
23025
23025
|
rl.close();
|
|
@@ -25369,16 +25369,442 @@ function registerDoctor(program2) {
|
|
|
25369
25369
|
});
|
|
25370
25370
|
}
|
|
25371
25371
|
|
|
25372
|
+
// src/lib/completion-generator.ts
|
|
25373
|
+
var UnsupportedShellError = class extends Error {
|
|
25374
|
+
constructor(shell) {
|
|
25375
|
+
super(`Unsupported shell: ${shell}. Supported shells: zsh, bash.`);
|
|
25376
|
+
this.name = "UnsupportedShellError";
|
|
25377
|
+
}
|
|
25378
|
+
};
|
|
25379
|
+
function extractCommandTree(program2) {
|
|
25380
|
+
return {
|
|
25381
|
+
name: program2.name(),
|
|
25382
|
+
description: program2.description() ?? "",
|
|
25383
|
+
subcommands: program2.commands.filter((c) => !isHidden(c)).map((c) => extractCommandTree(c))
|
|
25384
|
+
};
|
|
25385
|
+
}
|
|
25386
|
+
function isHidden(cmd) {
|
|
25387
|
+
const c = cmd;
|
|
25388
|
+
return c._hidden === true;
|
|
25389
|
+
}
|
|
25390
|
+
function escapeZsh(s) {
|
|
25391
|
+
return s.replace(/[\r\n]+/g, " ").replace(/'/g, "''").replace(/:/g, "\\:");
|
|
25392
|
+
}
|
|
25393
|
+
function escapeBash(s) {
|
|
25394
|
+
return s.replace(/[\r\n]+/g, " ").replace(/(["\\$`])/g, "\\$1");
|
|
25395
|
+
}
|
|
25396
|
+
function generateZshCompletion(tree) {
|
|
25397
|
+
const lines = [];
|
|
25398
|
+
lines.push(`#compdef ${tree.name}`);
|
|
25399
|
+
lines.push("");
|
|
25400
|
+
lines.push(`_${tree.name}() {`);
|
|
25401
|
+
lines.push(" local -a l1_subs");
|
|
25402
|
+
lines.push(" l1_subs=(");
|
|
25403
|
+
for (const sub of tree.subcommands) {
|
|
25404
|
+
lines.push(` '${sub.name}:${escapeZsh(sub.description)}'`);
|
|
25405
|
+
}
|
|
25406
|
+
lines.push(" )");
|
|
25407
|
+
lines.push("");
|
|
25408
|
+
lines.push(" if (( CURRENT == 2 )); then");
|
|
25409
|
+
lines.push(` _describe '${tree.name} command' l1_subs`);
|
|
25410
|
+
lines.push(" return");
|
|
25411
|
+
lines.push(" fi");
|
|
25412
|
+
lines.push("");
|
|
25413
|
+
const subsWithChildren = tree.subcommands.filter((s) => s.subcommands.length > 0);
|
|
25414
|
+
if (subsWithChildren.length > 0) {
|
|
25415
|
+
lines.push(" case $words[2] in");
|
|
25416
|
+
for (const sub of subsWithChildren) {
|
|
25417
|
+
lines.push(` ${sub.name})`);
|
|
25418
|
+
lines.push(" if (( CURRENT == 3 )); then");
|
|
25419
|
+
lines.push(" local -a l2_subs");
|
|
25420
|
+
lines.push(" l2_subs=(");
|
|
25421
|
+
for (const s2 of sub.subcommands) {
|
|
25422
|
+
lines.push(` '${s2.name}:${escapeZsh(s2.description)}'`);
|
|
25423
|
+
}
|
|
25424
|
+
lines.push(" )");
|
|
25425
|
+
lines.push(` _describe '${sub.name} subcommand' l2_subs`);
|
|
25426
|
+
lines.push(" fi");
|
|
25427
|
+
lines.push(" ;;");
|
|
25428
|
+
}
|
|
25429
|
+
lines.push(" esac");
|
|
25430
|
+
}
|
|
25431
|
+
lines.push("}");
|
|
25432
|
+
lines.push("");
|
|
25433
|
+
lines.push(`_${tree.name} "$@"`);
|
|
25434
|
+
lines.push("");
|
|
25435
|
+
return lines.join("\n");
|
|
25436
|
+
}
|
|
25437
|
+
function generateBashCompletion(tree) {
|
|
25438
|
+
const lines = [];
|
|
25439
|
+
lines.push(`_${tree.name}_completions() {`);
|
|
25440
|
+
lines.push(' local cur="${COMP_WORDS[COMP_CWORD]}"');
|
|
25441
|
+
lines.push(" local cword=$COMP_CWORD");
|
|
25442
|
+
lines.push("");
|
|
25443
|
+
lines.push(" if [[ $cword -eq 1 ]]; then");
|
|
25444
|
+
const l1Names = tree.subcommands.map((s) => s.name).join(" ");
|
|
25445
|
+
lines.push(` COMPREPLY=( $(compgen -W "${escapeBash(l1Names)}" -- "$cur") )`);
|
|
25446
|
+
lines.push(" return");
|
|
25447
|
+
lines.push(" fi");
|
|
25448
|
+
lines.push("");
|
|
25449
|
+
const subsWithChildren = tree.subcommands.filter((s) => s.subcommands.length > 0);
|
|
25450
|
+
if (subsWithChildren.length > 0) {
|
|
25451
|
+
lines.push(' case "${COMP_WORDS[1]}" in');
|
|
25452
|
+
for (const sub of subsWithChildren) {
|
|
25453
|
+
lines.push(` ${sub.name})`);
|
|
25454
|
+
lines.push(" if [[ $cword -eq 2 ]]; then");
|
|
25455
|
+
const l2Names = sub.subcommands.map((s) => s.name).join(" ");
|
|
25456
|
+
lines.push(` COMPREPLY=( $(compgen -W "${escapeBash(l2Names)}" -- "$cur") )`);
|
|
25457
|
+
lines.push(" fi");
|
|
25458
|
+
lines.push(" ;;");
|
|
25459
|
+
}
|
|
25460
|
+
lines.push(" esac");
|
|
25461
|
+
}
|
|
25462
|
+
lines.push("}");
|
|
25463
|
+
lines.push("");
|
|
25464
|
+
lines.push(`complete -F _${tree.name}_completions ${tree.name}`);
|
|
25465
|
+
lines.push("");
|
|
25466
|
+
return lines.join("\n");
|
|
25467
|
+
}
|
|
25468
|
+
function generateCompletion(program2, shell) {
|
|
25469
|
+
const tree = extractCommandTree(program2);
|
|
25470
|
+
if (shell === "zsh") return generateZshCompletion(tree);
|
|
25471
|
+
if (shell === "bash") return generateBashCompletion(tree);
|
|
25472
|
+
throw new UnsupportedShellError(shell);
|
|
25473
|
+
}
|
|
25474
|
+
|
|
25475
|
+
// src/commands/completion.ts
|
|
25476
|
+
function registerCompletion(program2) {
|
|
25477
|
+
program2.command("completion").description(
|
|
25478
|
+
"Emit a POSIX shell completion script for zsh or bash. Pipe to `eval` in your shell rc, or let `olam setup` append it idempotently. Completes top-level commands + one nested level (`olam kg <Tab>`); deeper subcommand trees (`olam world snapshot <Tab>`) fall through without completion."
|
|
25479
|
+
).argument("<shell>", "zsh | bash").action((shell) => {
|
|
25480
|
+
const tree = program2.parent ?? program2;
|
|
25481
|
+
try {
|
|
25482
|
+
const output = generateCompletion(tree, shell);
|
|
25483
|
+
process.stdout.write(output);
|
|
25484
|
+
} catch (err) {
|
|
25485
|
+
if (err instanceof UnsupportedShellError) {
|
|
25486
|
+
process.stderr.write(`${err.message}
|
|
25487
|
+
`);
|
|
25488
|
+
process.exitCode = 1;
|
|
25489
|
+
return;
|
|
25490
|
+
}
|
|
25491
|
+
throw err;
|
|
25492
|
+
}
|
|
25493
|
+
});
|
|
25494
|
+
}
|
|
25495
|
+
|
|
25496
|
+
// src/commands/setup.ts
|
|
25497
|
+
init_cli_version();
|
|
25498
|
+
import { spawn as spawn5 } from "node:child_process";
|
|
25499
|
+
import { existsSync as existsSync45 } from "node:fs";
|
|
25500
|
+
import { homedir as homedir23 } from "node:os";
|
|
25501
|
+
import path45 from "node:path";
|
|
25502
|
+
import { createInterface as createInterface3 } from "node:readline";
|
|
25503
|
+
|
|
25504
|
+
// src/lib/shell-rc.ts
|
|
25505
|
+
import { copyFileSync as copyFileSync5, existsSync as existsSync44, readFileSync as readFileSync31, renameSync as renameSync4, writeFileSync as writeFileSync20 } from "node:fs";
|
|
25506
|
+
import path44 from "node:path";
|
|
25507
|
+
function appendIdempotent(opts) {
|
|
25508
|
+
const { rcPath, marker, contentLine, clock = () => /* @__PURE__ */ new Date() } = opts;
|
|
25509
|
+
if (!existsSync44(rcPath)) {
|
|
25510
|
+
return { status: "no-rc-file", backupPath: null };
|
|
25511
|
+
}
|
|
25512
|
+
const content = readFileSync31(rcPath, "utf-8");
|
|
25513
|
+
if (content.includes(marker)) {
|
|
25514
|
+
return { status: "already-present", backupPath: null };
|
|
25515
|
+
}
|
|
25516
|
+
const timestamp = clock().toISOString().replace(/[:.]/g, "-");
|
|
25517
|
+
const backupPath = `${rcPath}.olam-bak.${timestamp}`;
|
|
25518
|
+
copyFileSync5(rcPath, backupPath);
|
|
25519
|
+
const separator = content.length === 0 || content.endsWith("\n") ? "" : "\n";
|
|
25520
|
+
const trailing = contentLine.endsWith("\n") ? "" : "\n";
|
|
25521
|
+
const nextContent = `${content}${separator}${contentLine}${trailing}`;
|
|
25522
|
+
const tmpPath = `${rcPath}.olam-tmp.${process.pid}`;
|
|
25523
|
+
writeFileSync20(tmpPath, nextContent, { encoding: "utf-8" });
|
|
25524
|
+
renameSync4(tmpPath, rcPath);
|
|
25525
|
+
return { status: "appended", backupPath };
|
|
25526
|
+
}
|
|
25527
|
+
function resolveShellRc(home, shellEnv) {
|
|
25528
|
+
if (!shellEnv) return null;
|
|
25529
|
+
const basename6 = path44.basename(shellEnv);
|
|
25530
|
+
if (basename6 === "zsh") return path44.join(home, ".zshrc");
|
|
25531
|
+
if (basename6 === "bash") return path44.join(home, ".bashrc");
|
|
25532
|
+
return null;
|
|
25533
|
+
}
|
|
25534
|
+
|
|
25535
|
+
// src/commands/setup.ts
|
|
25536
|
+
init_output();
|
|
25537
|
+
var REQUIRED_NODE_MAJOR = 20;
|
|
25538
|
+
var NEXT_STEPS_DOCS = [
|
|
25539
|
+
"docs/architecture/devbox-contract.md \u2014 image contract",
|
|
25540
|
+
"docs/architecture/manifest-spec.md \u2014 per-repo .adb.yaml schema",
|
|
25541
|
+
"docs/architecture/config-spec.md \u2014 workspace .olam/config.yaml schema"
|
|
25542
|
+
];
|
|
25543
|
+
var defaultSpawn = (cmd, args) => new Promise((resolve11) => {
|
|
25544
|
+
const child = spawn5(cmd, [...args], { stdio: "inherit" });
|
|
25545
|
+
child.on("exit", (code) => resolve11({ status: code }));
|
|
25546
|
+
child.on("error", () => resolve11({ status: 1 }));
|
|
25547
|
+
});
|
|
25548
|
+
var defaultPrompt = (question, defaultYes) => {
|
|
25549
|
+
if (!process.stdin.isTTY) {
|
|
25550
|
+
process.stderr.write(
|
|
25551
|
+
`[olam setup] non-TTY stdin detected; using default answer (${defaultYes ? "yes" : "no"}). Re-run with \`--yes\` for explicit non-interactive mode.
|
|
25552
|
+
`
|
|
25553
|
+
);
|
|
25554
|
+
return Promise.resolve(defaultYes);
|
|
25555
|
+
}
|
|
25556
|
+
return new Promise((resolve11) => {
|
|
25557
|
+
const rl = createInterface3({ input: process.stdin, output: process.stdout });
|
|
25558
|
+
const suffix = defaultYes ? " [Y/n]: " : " [y/N]: ";
|
|
25559
|
+
rl.question(`${question}${suffix}`, (answer) => {
|
|
25560
|
+
rl.close();
|
|
25561
|
+
const t = answer.trim().toLowerCase();
|
|
25562
|
+
if (t === "") resolve11(defaultYes);
|
|
25563
|
+
else if (t === "y" || t === "yes") resolve11(true);
|
|
25564
|
+
else if (t === "n" || t === "no") resolve11(false);
|
|
25565
|
+
else resolve11(defaultYes);
|
|
25566
|
+
});
|
|
25567
|
+
rl.on("close", () => resolve11(defaultYes));
|
|
25568
|
+
});
|
|
25569
|
+
};
|
|
25570
|
+
async function phase1SystemCheck(deps) {
|
|
25571
|
+
const dockerProbe = await probeDockerDaemon(deps.dockerExec);
|
|
25572
|
+
if (!dockerProbe.ok) {
|
|
25573
|
+
return phaseFromProbe(dockerProbe);
|
|
25574
|
+
}
|
|
25575
|
+
const nodeVersion = deps.nodeVersion ?? process.version;
|
|
25576
|
+
const nodeMajor = parseNodeMajor(nodeVersion);
|
|
25577
|
+
if (nodeMajor === null || nodeMajor < REQUIRED_NODE_MAJOR) {
|
|
25578
|
+
return {
|
|
25579
|
+
ok: false,
|
|
25580
|
+
message: `Node.js ${nodeVersion} is too old (need \u2265${REQUIRED_NODE_MAJOR})`,
|
|
25581
|
+
remedy: `Install Node.js ${REQUIRED_NODE_MAJOR}+ LTS via nvm/fnm/asdf and re-run \`olam setup\`.`
|
|
25582
|
+
};
|
|
25583
|
+
}
|
|
25584
|
+
return {
|
|
25585
|
+
ok: true,
|
|
25586
|
+
message: `${dockerProbe.message}; node ${nodeVersion}`
|
|
25587
|
+
};
|
|
25588
|
+
}
|
|
25589
|
+
function parseNodeMajor(version) {
|
|
25590
|
+
const m = version.match(/^v?(\d+)\./);
|
|
25591
|
+
if (!m) return null;
|
|
25592
|
+
const n = Number.parseInt(m[1], 10);
|
|
25593
|
+
return Number.isFinite(n) ? n : null;
|
|
25594
|
+
}
|
|
25595
|
+
function phaseFromProbe(probe) {
|
|
25596
|
+
if (probe.ok) return { ok: true, message: probe.message };
|
|
25597
|
+
return { ok: false, message: probe.message, remedy: probe.remedy };
|
|
25598
|
+
}
|
|
25599
|
+
async function phase2CliSanity(deps) {
|
|
25600
|
+
const version = deps.olamCliVersion ?? safeReadCliVersion();
|
|
25601
|
+
if (!version || version === "unknown") {
|
|
25602
|
+
return {
|
|
25603
|
+
ok: false,
|
|
25604
|
+
message: "olam CLI version not detectable",
|
|
25605
|
+
remedy: "Re-install `olam` via `npm install -g @pleri/olam-cli@stable` and re-run."
|
|
25606
|
+
};
|
|
25607
|
+
}
|
|
25608
|
+
return { ok: true, message: `olam ${version}` };
|
|
25609
|
+
}
|
|
25610
|
+
function safeReadCliVersion() {
|
|
25611
|
+
try {
|
|
25612
|
+
return readCliVersion();
|
|
25613
|
+
} catch {
|
|
25614
|
+
return null;
|
|
25615
|
+
}
|
|
25616
|
+
}
|
|
25617
|
+
async function phase3Bootstrap(deps) {
|
|
25618
|
+
const spawnFn = deps.spawnSubprocess ?? defaultSpawn;
|
|
25619
|
+
const r = await spawnFn("olam", ["bootstrap", "--skip-auth-login"]);
|
|
25620
|
+
if (r.status === 0) {
|
|
25621
|
+
return { ok: true, message: "olam bootstrap succeeded" };
|
|
25622
|
+
}
|
|
25623
|
+
return {
|
|
25624
|
+
ok: false,
|
|
25625
|
+
message: `olam bootstrap exited ${r.status}`,
|
|
25626
|
+
remedy: "Re-run `olam setup` after inspecting the bootstrap error above (bootstrap is idempotent)."
|
|
25627
|
+
};
|
|
25628
|
+
}
|
|
25629
|
+
async function phase4ShellInit(opts, deps) {
|
|
25630
|
+
if (opts.skipShellInit) {
|
|
25631
|
+
return { ok: true, skipped: true, message: "skipped via --skip-shell-init" };
|
|
25632
|
+
}
|
|
25633
|
+
const home = deps.home ?? homedir23();
|
|
25634
|
+
const shellEnv = deps.shellEnv ?? process.env.SHELL;
|
|
25635
|
+
const rcPath = resolveShellRc(home, shellEnv);
|
|
25636
|
+
if (rcPath === null) {
|
|
25637
|
+
return {
|
|
25638
|
+
ok: true,
|
|
25639
|
+
skipped: true,
|
|
25640
|
+
message: `unsupported $SHELL (${shellEnv ?? "unset"}); add \`eval "$(olam completion <shell>)"\` to your shell rc manually`
|
|
25641
|
+
};
|
|
25642
|
+
}
|
|
25643
|
+
const shellBasename = path45.basename(shellEnv);
|
|
25644
|
+
const evalLine = `eval "$(olam completion ${shellBasename})"`;
|
|
25645
|
+
const result = appendIdempotent({
|
|
25646
|
+
rcPath,
|
|
25647
|
+
marker: "olam completion",
|
|
25648
|
+
contentLine: evalLine,
|
|
25649
|
+
clock: deps.clock
|
|
25650
|
+
});
|
|
25651
|
+
if (result.status === "no-rc-file") {
|
|
25652
|
+
return {
|
|
25653
|
+
ok: true,
|
|
25654
|
+
skipped: true,
|
|
25655
|
+
message: `${rcPath} not present; skipped (add \`${evalLine}\` to your shell rc manually)`
|
|
25656
|
+
};
|
|
25657
|
+
}
|
|
25658
|
+
if (result.status === "already-present") {
|
|
25659
|
+
return { ok: true, message: `${rcPath}: already configured (no change)` };
|
|
25660
|
+
}
|
|
25661
|
+
return {
|
|
25662
|
+
ok: true,
|
|
25663
|
+
message: `${rcPath}: appended (backup: ${result.backupPath})`
|
|
25664
|
+
};
|
|
25665
|
+
}
|
|
25666
|
+
async function phase5InitProject(opts, deps) {
|
|
25667
|
+
const cwd = deps.cwd ?? process.cwd();
|
|
25668
|
+
const projectRoot = findProjectRoot(cwd);
|
|
25669
|
+
const configPath = path45.join(projectRoot, ".olam", "config.yaml");
|
|
25670
|
+
if (existsSync45(configPath)) {
|
|
25671
|
+
return { ok: true, message: `${configPath} present (no change)` };
|
|
25672
|
+
}
|
|
25673
|
+
const promptFn = deps.prompt ?? defaultPrompt;
|
|
25674
|
+
const shouldInit = opts.yes ? true : await promptFn(`No .olam/config.yaml in ${cwd}. Initialise project here?`, false);
|
|
25675
|
+
if (!shouldInit) {
|
|
25676
|
+
return {
|
|
25677
|
+
ok: true,
|
|
25678
|
+
skipped: true,
|
|
25679
|
+
message: "declined; run `olam init` later when ready"
|
|
25680
|
+
};
|
|
25681
|
+
}
|
|
25682
|
+
const spawnFn = deps.spawnSubprocess ?? defaultSpawn;
|
|
25683
|
+
const r = await spawnFn("olam", ["init"]);
|
|
25684
|
+
if (r.status === 0) {
|
|
25685
|
+
return { ok: true, message: "olam init completed" };
|
|
25686
|
+
}
|
|
25687
|
+
return {
|
|
25688
|
+
ok: false,
|
|
25689
|
+
message: `olam init exited ${r.status}`,
|
|
25690
|
+
remedy: "Inspect the init error above and re-run `olam setup`."
|
|
25691
|
+
};
|
|
25692
|
+
}
|
|
25693
|
+
async function phase6Auth(opts, deps) {
|
|
25694
|
+
if (opts.skipAuth) {
|
|
25695
|
+
return {
|
|
25696
|
+
ok: true,
|
|
25697
|
+
skipped: true,
|
|
25698
|
+
message: "skipped via --skip-auth (run `olam auth login` later)"
|
|
25699
|
+
};
|
|
25700
|
+
}
|
|
25701
|
+
const promptFn = deps.prompt ?? defaultPrompt;
|
|
25702
|
+
const shouldLaunch = opts.yes ? true : await promptFn(
|
|
25703
|
+
"`olam auth login` is interactive (PKCE browser flow, 5 min timeout). Launch now?",
|
|
25704
|
+
false
|
|
25705
|
+
);
|
|
25706
|
+
if (!shouldLaunch) {
|
|
25707
|
+
return {
|
|
25708
|
+
ok: true,
|
|
25709
|
+
skipped: true,
|
|
25710
|
+
message: "declined; run `olam auth login` later when ready"
|
|
25711
|
+
};
|
|
25712
|
+
}
|
|
25713
|
+
const spawnFn = deps.spawnSubprocess ?? defaultSpawn;
|
|
25714
|
+
const r = await spawnFn("olam", ["auth", "login"]);
|
|
25715
|
+
if (r.status === 0) {
|
|
25716
|
+
return { ok: true, message: "olam auth login succeeded" };
|
|
25717
|
+
}
|
|
25718
|
+
return {
|
|
25719
|
+
ok: true,
|
|
25720
|
+
skipped: true,
|
|
25721
|
+
message: `olam auth login exited ${r.status}; re-run \`olam auth login\` after resolving`
|
|
25722
|
+
};
|
|
25723
|
+
}
|
|
25724
|
+
async function phase7Verify(deps) {
|
|
25725
|
+
const spawnFn = deps.spawnSubprocess ?? defaultSpawn;
|
|
25726
|
+
const r = await spawnFn("olam", ["doctor"]);
|
|
25727
|
+
if (r.status === 0) {
|
|
25728
|
+
return { ok: true, message: "olam doctor: all probes green" };
|
|
25729
|
+
}
|
|
25730
|
+
return {
|
|
25731
|
+
ok: false,
|
|
25732
|
+
message: `olam doctor exited ${r.status}`,
|
|
25733
|
+
remedy: "Inspect doctor output above; the specific failing probe names its remedy."
|
|
25734
|
+
};
|
|
25735
|
+
}
|
|
25736
|
+
var PHASE_TITLES = [
|
|
25737
|
+
"Phase 1: System check",
|
|
25738
|
+
"Phase 2: olam CLI sanity",
|
|
25739
|
+
"Phase 3: Bootstrap",
|
|
25740
|
+
"Phase 4: Shell init",
|
|
25741
|
+
"Phase 5: Init project",
|
|
25742
|
+
"Phase 6: Auth prompt",
|
|
25743
|
+
"Phase 7: Final verification"
|
|
25744
|
+
];
|
|
25745
|
+
async function runSetup(opts, deps = {}) {
|
|
25746
|
+
printHeader("olam setup");
|
|
25747
|
+
const phaseFns = [
|
|
25748
|
+
() => phase1SystemCheck(deps),
|
|
25749
|
+
() => phase2CliSanity(deps),
|
|
25750
|
+
() => phase3Bootstrap(deps),
|
|
25751
|
+
() => phase4ShellInit(opts, deps),
|
|
25752
|
+
() => phase5InitProject(opts, deps),
|
|
25753
|
+
() => phase6Auth(opts, deps),
|
|
25754
|
+
() => phase7Verify(deps)
|
|
25755
|
+
];
|
|
25756
|
+
const results = [];
|
|
25757
|
+
let failureAt = null;
|
|
25758
|
+
for (let i = 0; i < phaseFns.length; i += 1) {
|
|
25759
|
+
const name = PHASE_TITLES[i];
|
|
25760
|
+
process.stdout.write(`
|
|
25761
|
+
${name}
|
|
25762
|
+
`);
|
|
25763
|
+
const result = await phaseFns[i]();
|
|
25764
|
+
results.push({ name, result });
|
|
25765
|
+
if (result.ok && result.skipped) {
|
|
25766
|
+
printWarning(` \u2298 ${result.message}`);
|
|
25767
|
+
} else if (result.ok) {
|
|
25768
|
+
printSuccess(` \u2713 ${result.message}`);
|
|
25769
|
+
} else {
|
|
25770
|
+
printError(` \u2717 ${result.message}`);
|
|
25771
|
+
if (result.remedy) printWarning(` remedy: ${result.remedy}`);
|
|
25772
|
+
failureAt = i + 1;
|
|
25773
|
+
break;
|
|
25774
|
+
}
|
|
25775
|
+
}
|
|
25776
|
+
process.stdout.write("\n");
|
|
25777
|
+
if (failureAt !== null) {
|
|
25778
|
+
printError(`Setup FAILED at Phase ${failureAt}`);
|
|
25779
|
+
return { phases: results, failureAt, exitCode: 1 };
|
|
25780
|
+
}
|
|
25781
|
+
printSuccess("Setup complete.");
|
|
25782
|
+
process.stdout.write("\nNext steps \u2014 read these in order for the 3-contract pattern:\n");
|
|
25783
|
+
for (const line of NEXT_STEPS_DOCS) {
|
|
25784
|
+
printInfo("docs", line);
|
|
25785
|
+
}
|
|
25786
|
+
process.stdout.write("\n");
|
|
25787
|
+
return { phases: results, failureAt: null, exitCode: 0 };
|
|
25788
|
+
}
|
|
25789
|
+
function registerSetup(program2) {
|
|
25790
|
+
program2.command("setup").description(
|
|
25791
|
+
"Fresh-host onboarding wizard. Runs 7 phases (system check \u2192 bootstrap \u2192 shell init \u2192 init project \u2192 auth prompt \u2192 doctor verification). Idempotent; safe to re-run."
|
|
25792
|
+
).option("--skip-shell-init", "Skip Phase 4 (do not append to ~/.zshrc / ~/.bashrc)").option("--skip-auth", "Skip Phase 6 (do not prompt for `olam auth login`)").option("-y, --yes", "Auto-affirm every prompt (non-interactive)").action(async (opts) => {
|
|
25793
|
+
const report = await runSetup(opts);
|
|
25794
|
+
if (report.exitCode !== 0) process.exitCode = report.exitCode;
|
|
25795
|
+
});
|
|
25796
|
+
}
|
|
25797
|
+
|
|
25372
25798
|
// src/commands/update.ts
|
|
25373
25799
|
import * as fs42 from "node:fs";
|
|
25374
25800
|
import * as os25 from "node:os";
|
|
25375
|
-
import * as
|
|
25801
|
+
import * as path48 from "node:path";
|
|
25376
25802
|
import { execSync as execSync13 } from "node:child_process";
|
|
25377
25803
|
import pc23 from "picocolors";
|
|
25378
25804
|
|
|
25379
25805
|
// src/lib/symlink-reconcile.ts
|
|
25380
25806
|
import * as fs40 from "node:fs";
|
|
25381
|
-
import * as
|
|
25807
|
+
import * as path46 from "node:path";
|
|
25382
25808
|
var realFs = {
|
|
25383
25809
|
readdirSync: (p) => fs40.readdirSync(p),
|
|
25384
25810
|
existsSync: (p) => fs40.existsSync(p),
|
|
@@ -25397,8 +25823,8 @@ function reconcileSkillSymlinks(npmSkillsDir, claudeSkillsDir, _fs = realFs) {
|
|
|
25397
25823
|
_fs.mkdirSync(claudeSkillsDir, { recursive: true });
|
|
25398
25824
|
const sourceSkills = _fs.existsSync(npmSkillsDir) ? _fs.readdirSync(npmSkillsDir).filter((d) => d.startsWith("olam-")) : [];
|
|
25399
25825
|
for (const skill of sourceSkills) {
|
|
25400
|
-
const linkPath =
|
|
25401
|
-
const target =
|
|
25826
|
+
const linkPath = path46.join(claudeSkillsDir, skill);
|
|
25827
|
+
const target = path46.join(npmSkillsDir, skill);
|
|
25402
25828
|
if (!_fs.existsSync(linkPath)) {
|
|
25403
25829
|
try {
|
|
25404
25830
|
_fs.symlinkSync(target, linkPath);
|
|
@@ -25411,7 +25837,7 @@ function reconcileSkillSymlinks(npmSkillsDir, claudeSkillsDir, _fs = realFs) {
|
|
|
25411
25837
|
}
|
|
25412
25838
|
const deployedEntries = _fs.existsSync(claudeSkillsDir) ? _fs.readdirSync(claudeSkillsDir).filter((d) => d.startsWith("olam-")) : [];
|
|
25413
25839
|
for (const entry of deployedEntries) {
|
|
25414
|
-
const linkPath =
|
|
25840
|
+
const linkPath = path46.join(claudeSkillsDir, entry);
|
|
25415
25841
|
let isSymlink = false;
|
|
25416
25842
|
try {
|
|
25417
25843
|
isSymlink = _fs.lstatSync(linkPath).isSymbolicLink();
|
|
@@ -25436,9 +25862,9 @@ function reconcileSkillSymlinks(npmSkillsDir, claudeSkillsDir, _fs = realFs) {
|
|
|
25436
25862
|
|
|
25437
25863
|
// src/commands/update.ts
|
|
25438
25864
|
var PACKAGE_NAME = "@pleri/olam-cli";
|
|
25439
|
-
var CACHE_DIR2 =
|
|
25440
|
-
var LOG_DIR2 =
|
|
25441
|
-
var LAST_STABLE_FILE =
|
|
25865
|
+
var CACHE_DIR2 = path48.join(os25.homedir(), ".olam", "cache");
|
|
25866
|
+
var LOG_DIR2 = path48.join(os25.homedir(), ".olam", "log");
|
|
25867
|
+
var LAST_STABLE_FILE = path48.join(CACHE_DIR2, "last-stable.txt");
|
|
25442
25868
|
function defaultExec(cmd) {
|
|
25443
25869
|
try {
|
|
25444
25870
|
const stdout = execSync13(cmd, { encoding: "utf-8", stdio: ["ignore", "pipe", "pipe"] });
|
|
@@ -25467,12 +25893,12 @@ function readLastStable(file = LAST_STABLE_FILE) {
|
|
|
25467
25893
|
}
|
|
25468
25894
|
}
|
|
25469
25895
|
function writeLastStable(version, file = LAST_STABLE_FILE) {
|
|
25470
|
-
fs42.mkdirSync(
|
|
25896
|
+
fs42.mkdirSync(path48.dirname(file), { recursive: true });
|
|
25471
25897
|
fs42.writeFileSync(file, version, { mode: 420 });
|
|
25472
25898
|
}
|
|
25473
25899
|
function logUpdateFailure(stderr) {
|
|
25474
25900
|
const ts = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
|
|
25475
|
-
const logFile =
|
|
25901
|
+
const logFile = path48.join(LOG_DIR2, `update-${ts}.log`);
|
|
25476
25902
|
try {
|
|
25477
25903
|
fs42.mkdirSync(LOG_DIR2, { recursive: true });
|
|
25478
25904
|
fs42.appendFileSync(logFile, `[update-failure ${(/* @__PURE__ */ new Date()).toISOString()}]
|
|
@@ -25562,8 +25988,8 @@ async function doUpdate(opts, _exec = defaultExec, _reconcile = reconcileSkillSy
|
|
|
25562
25988
|
let symlinkResult = { added: [], removed: [] };
|
|
25563
25989
|
if (npmRootResult.exitCode === 0) {
|
|
25564
25990
|
const npmRoot = npmRootResult.stdout.trim();
|
|
25565
|
-
const npmSkillsDir =
|
|
25566
|
-
const claudeSkillsDir =
|
|
25991
|
+
const npmSkillsDir = path48.join(npmRoot, "@pleri", "olam-cli", "plugin", "skills");
|
|
25992
|
+
const claudeSkillsDir = path48.join(os25.homedir(), ".claude", "skills");
|
|
25567
25993
|
const rec = _reconcile(npmSkillsDir, claudeSkillsDir);
|
|
25568
25994
|
symlinkResult = { added: rec.added, removed: rec.removed };
|
|
25569
25995
|
if (!quiet && (rec.added.length > 0 || rec.removed.length > 0)) {
|
|
@@ -25609,8 +26035,8 @@ async function doRollback(_exec = defaultExec, _reconcile = reconcileSkillSymlin
|
|
|
25609
26035
|
if (npmRootResult.exitCode === 0) {
|
|
25610
26036
|
const npmRoot = npmRootResult.stdout.trim();
|
|
25611
26037
|
_reconcile(
|
|
25612
|
-
|
|
25613
|
-
|
|
26038
|
+
path48.join(npmRoot, "@pleri", "olam-cli", "plugin", "skills"),
|
|
26039
|
+
path48.join(os25.homedir(), ".claude", "skills")
|
|
25614
26040
|
);
|
|
25615
26041
|
}
|
|
25616
26042
|
return { action: "rolled-back", restoredVersion: prev, exitCode: 0 };
|
|
@@ -25702,10 +26128,10 @@ init_store2();
|
|
|
25702
26128
|
init_store2();
|
|
25703
26129
|
import * as fs43 from "node:fs";
|
|
25704
26130
|
import * as os26 from "node:os";
|
|
25705
|
-
import * as
|
|
26131
|
+
import * as path49 from "node:path";
|
|
25706
26132
|
function expandPath(p) {
|
|
25707
26133
|
if (p === "~" || p.startsWith("~/")) {
|
|
25708
|
-
return
|
|
26134
|
+
return path49.join(os26.homedir(), p.slice(1));
|
|
25709
26135
|
}
|
|
25710
26136
|
return p;
|
|
25711
26137
|
}
|
|
@@ -26114,8 +26540,8 @@ var SECRET = process.env["OLAM_MCP_AUTH_SECRET"] ?? "";
|
|
|
26114
26540
|
function authHeaders() {
|
|
26115
26541
|
return SECRET ? { "X-Olam-Mcp-Secret": SECRET } : {};
|
|
26116
26542
|
}
|
|
26117
|
-
async function apiFetch(
|
|
26118
|
-
const res = await fetch(`${BASE_URL}${
|
|
26543
|
+
async function apiFetch(path55, init = {}) {
|
|
26544
|
+
const res = await fetch(`${BASE_URL}${path55}`, {
|
|
26119
26545
|
...init,
|
|
26120
26546
|
headers: {
|
|
26121
26547
|
"Content-Type": "application/json",
|
|
@@ -26170,11 +26596,11 @@ function getMcpAuthClient() {
|
|
|
26170
26596
|
}
|
|
26171
26597
|
|
|
26172
26598
|
// src/commands/mcp/login.ts
|
|
26173
|
-
import { spawn as
|
|
26599
|
+
import { spawn as spawn6 } from "node:child_process";
|
|
26174
26600
|
function openBrowser2(url) {
|
|
26175
26601
|
const cmd = process.platform === "darwin" ? "open" : process.platform === "win32" ? "start" : "xdg-open";
|
|
26176
26602
|
try {
|
|
26177
|
-
const child =
|
|
26603
|
+
const child = spawn6(cmd, [url], { detached: true, stdio: "ignore" });
|
|
26178
26604
|
child.unref();
|
|
26179
26605
|
} catch {
|
|
26180
26606
|
}
|
|
@@ -26377,7 +26803,7 @@ import pc29 from "picocolors";
|
|
|
26377
26803
|
// src/commands/mcp/import-discovery.ts
|
|
26378
26804
|
import * as fs45 from "node:fs";
|
|
26379
26805
|
import * as os27 from "node:os";
|
|
26380
|
-
import * as
|
|
26806
|
+
import * as path50 from "node:path";
|
|
26381
26807
|
function readJsonFile(filePath) {
|
|
26382
26808
|
try {
|
|
26383
26809
|
const raw = fs45.readFileSync(filePath, "utf-8");
|
|
@@ -26409,18 +26835,18 @@ function extractMcpServers(obj, source, sourceLabel) {
|
|
|
26409
26835
|
}
|
|
26410
26836
|
function getClaudeDesktopPath() {
|
|
26411
26837
|
if (process.platform === "darwin") {
|
|
26412
|
-
return
|
|
26838
|
+
return path50.join(os27.homedir(), "Library", "Application Support", "Claude", "claude_desktop_config.json");
|
|
26413
26839
|
}
|
|
26414
26840
|
if (process.platform === "win32") {
|
|
26415
|
-
const appData = process.env["APPDATA"] ??
|
|
26416
|
-
return
|
|
26841
|
+
const appData = process.env["APPDATA"] ?? path50.join(os27.homedir(), "AppData", "Roaming");
|
|
26842
|
+
return path50.join(appData, "Claude", "claude_desktop_config.json");
|
|
26417
26843
|
}
|
|
26418
|
-
return
|
|
26844
|
+
return path50.join(os27.homedir(), ".config", "Claude", "claude_desktop_config.json");
|
|
26419
26845
|
}
|
|
26420
26846
|
function getOlamRepoPaths() {
|
|
26421
26847
|
const configPaths = [
|
|
26422
|
-
|
|
26423
|
-
|
|
26848
|
+
path50.join(os27.homedir(), ".olam", "config.yaml"),
|
|
26849
|
+
path50.join(process.cwd(), ".olam", "config.yaml")
|
|
26424
26850
|
];
|
|
26425
26851
|
const paths = [];
|
|
26426
26852
|
for (const configPath of configPaths) {
|
|
@@ -26442,7 +26868,7 @@ async function discoverMcpSources(repoPaths) {
|
|
|
26442
26868
|
const sources = [];
|
|
26443
26869
|
const sourceDefs = [
|
|
26444
26870
|
{
|
|
26445
|
-
path:
|
|
26871
|
+
path: path50.join(os27.homedir(), ".claude.json"),
|
|
26446
26872
|
label: "Claude Code (~/.claude.json)"
|
|
26447
26873
|
},
|
|
26448
26874
|
{
|
|
@@ -26450,19 +26876,19 @@ async function discoverMcpSources(repoPaths) {
|
|
|
26450
26876
|
label: "Claude Desktop"
|
|
26451
26877
|
},
|
|
26452
26878
|
{
|
|
26453
|
-
path:
|
|
26879
|
+
path: path50.join(os27.homedir(), ".cursor", "mcp.json"),
|
|
26454
26880
|
label: "Cursor (~/.cursor/mcp.json)"
|
|
26455
26881
|
},
|
|
26456
26882
|
{
|
|
26457
|
-
path:
|
|
26883
|
+
path: path50.join(os27.homedir(), ".codeium", "windsurf", "mcp_config.json"),
|
|
26458
26884
|
label: "Windsurf (~/.codeium/windsurf/mcp_config.json)"
|
|
26459
26885
|
}
|
|
26460
26886
|
];
|
|
26461
26887
|
const resolvedRepoPaths = repoPaths ?? getOlamRepoPaths();
|
|
26462
26888
|
for (const repoPath of resolvedRepoPaths) {
|
|
26463
26889
|
sourceDefs.push({
|
|
26464
|
-
path:
|
|
26465
|
-
label: `.mcp.json (${
|
|
26890
|
+
path: path50.join(repoPath, ".mcp.json"),
|
|
26891
|
+
label: `.mcp.json (${path50.basename(repoPath)})`
|
|
26466
26892
|
});
|
|
26467
26893
|
}
|
|
26468
26894
|
const reads = await Promise.all(
|
|
@@ -26492,7 +26918,7 @@ async function discoverMcpSources(repoPaths) {
|
|
|
26492
26918
|
}
|
|
26493
26919
|
|
|
26494
26920
|
// src/commands/mcp/import-validate.ts
|
|
26495
|
-
import { spawn as
|
|
26921
|
+
import { spawn as spawn7 } from "node:child_process";
|
|
26496
26922
|
var VALIDATION_TIMEOUT_MS = 5e3;
|
|
26497
26923
|
async function validateMcpEntry(entry) {
|
|
26498
26924
|
return new Promise((resolve11) => {
|
|
@@ -26500,7 +26926,7 @@ async function validateMcpEntry(entry) {
|
|
|
26500
26926
|
let timedOut = false;
|
|
26501
26927
|
let child;
|
|
26502
26928
|
try {
|
|
26503
|
-
child =
|
|
26929
|
+
child = spawn7(entry.command, [...entry.args ?? []], {
|
|
26504
26930
|
stdio: ["ignore", "pipe", "ignore"],
|
|
26505
26931
|
env: { ...process.env, ...entry.env ?? {} }
|
|
26506
26932
|
});
|
|
@@ -26694,10 +27120,10 @@ function registerMcp(program2) {
|
|
|
26694
27120
|
// src/commands/kg-build.ts
|
|
26695
27121
|
import { spawnSync as spawnSync15 } from "node:child_process";
|
|
26696
27122
|
import fs48 from "node:fs";
|
|
26697
|
-
import
|
|
27123
|
+
import path53 from "node:path";
|
|
26698
27124
|
|
|
26699
27125
|
// ../core/dist/kg/storage-paths.js
|
|
26700
|
-
import { homedir as
|
|
27126
|
+
import { homedir as homedir28 } from "node:os";
|
|
26701
27127
|
import { join as join48, resolve as resolve10 } from "node:path";
|
|
26702
27128
|
|
|
26703
27129
|
// ../core/dist/world/workspace-name.js
|
|
@@ -26719,7 +27145,7 @@ function validateWorkspaceName(name) {
|
|
|
26719
27145
|
|
|
26720
27146
|
// ../core/dist/kg/storage-paths.js
|
|
26721
27147
|
function olamHome3() {
|
|
26722
|
-
return process.env.OLAM_HOME ?? join48(
|
|
27148
|
+
return process.env.OLAM_HOME ?? join48(homedir28(), ".olam");
|
|
26723
27149
|
}
|
|
26724
27150
|
function kgRoot() {
|
|
26725
27151
|
return join48(olamHome3(), "kg");
|
|
@@ -26727,17 +27153,17 @@ function kgRoot() {
|
|
|
26727
27153
|
function worldsRoot() {
|
|
26728
27154
|
return join48(olamHome3(), "worlds");
|
|
26729
27155
|
}
|
|
26730
|
-
function assertWithinPrefix(
|
|
26731
|
-
if (!
|
|
26732
|
-
throw new Error(`${label} escape: ${
|
|
27156
|
+
function assertWithinPrefix(path55, prefix, label) {
|
|
27157
|
+
if (!path55.startsWith(prefix + "/")) {
|
|
27158
|
+
throw new Error(`${label} escape: ${path55} not under ${prefix}/`);
|
|
26733
27159
|
}
|
|
26734
27160
|
}
|
|
26735
27161
|
function kgPristinePath(workspace) {
|
|
26736
27162
|
validateWorkspaceName(workspace);
|
|
26737
27163
|
const root = kgRoot();
|
|
26738
|
-
const
|
|
26739
|
-
assertWithinPrefix(
|
|
26740
|
-
return
|
|
27164
|
+
const path55 = resolve10(join48(root, workspace));
|
|
27165
|
+
assertWithinPrefix(path55, root, "kgPristinePath");
|
|
27166
|
+
return path55;
|
|
26741
27167
|
}
|
|
26742
27168
|
var KG_PATHS_INTERNALS = Object.freeze({
|
|
26743
27169
|
olamHome: olamHome3,
|
|
@@ -26750,17 +27176,17 @@ init_output();
|
|
|
26750
27176
|
|
|
26751
27177
|
// src/commands/kg-status.ts
|
|
26752
27178
|
import fs46 from "node:fs";
|
|
26753
|
-
import { homedir as
|
|
26754
|
-
import
|
|
27179
|
+
import { homedir as homedir29 } from "node:os";
|
|
27180
|
+
import path51 from "node:path";
|
|
26755
27181
|
init_output();
|
|
26756
27182
|
function olamHome4() {
|
|
26757
|
-
return process.env.OLAM_HOME ??
|
|
27183
|
+
return process.env.OLAM_HOME ?? path51.join(homedir29(), ".olam");
|
|
26758
27184
|
}
|
|
26759
27185
|
function kgRoot2() {
|
|
26760
|
-
return
|
|
27186
|
+
return path51.join(olamHome4(), "kg");
|
|
26761
27187
|
}
|
|
26762
27188
|
function worldsRoot2() {
|
|
26763
|
-
return
|
|
27189
|
+
return path51.join(olamHome4(), "worlds");
|
|
26764
27190
|
}
|
|
26765
27191
|
function dirSizeBytes2(dir) {
|
|
26766
27192
|
if (!fs46.existsSync(dir)) return 0;
|
|
@@ -26775,7 +27201,7 @@ function dirSizeBytes2(dir) {
|
|
|
26775
27201
|
continue;
|
|
26776
27202
|
}
|
|
26777
27203
|
for (const entry of entries) {
|
|
26778
|
-
const full =
|
|
27204
|
+
const full = path51.join(cur, entry.name);
|
|
26779
27205
|
if (entry.isSymbolicLink()) continue;
|
|
26780
27206
|
if (entry.isDirectory()) {
|
|
26781
27207
|
stack.push(full);
|
|
@@ -26796,7 +27222,7 @@ function formatBytes5(n) {
|
|
|
26796
27222
|
return `${(n / 1024 / 1024 / 1024).toFixed(2)} GB`;
|
|
26797
27223
|
}
|
|
26798
27224
|
function readFreshness(workspace) {
|
|
26799
|
-
const file =
|
|
27225
|
+
const file = path51.join(kgPristinePath(workspace), "freshness.json");
|
|
26800
27226
|
if (!fs46.existsSync(file)) return null;
|
|
26801
27227
|
try {
|
|
26802
27228
|
const raw = JSON.parse(fs46.readFileSync(file, "utf-8"));
|
|
@@ -26807,7 +27233,7 @@ function readFreshness(workspace) {
|
|
|
26807
27233
|
}
|
|
26808
27234
|
}
|
|
26809
27235
|
function readOverlayNodeCount(graphifyOutDir) {
|
|
26810
|
-
const graphPath =
|
|
27236
|
+
const graphPath = path51.join(graphifyOutDir, "graph.json");
|
|
26811
27237
|
if (!fs46.existsSync(graphPath)) return null;
|
|
26812
27238
|
try {
|
|
26813
27239
|
const raw = JSON.parse(fs46.readFileSync(graphPath, "utf-8"));
|
|
@@ -26833,7 +27259,7 @@ function listOverlays() {
|
|
|
26833
27259
|
for (const worldEntry of worldDirs) {
|
|
26834
27260
|
if (!worldEntry.isDirectory()) continue;
|
|
26835
27261
|
const worldId = worldEntry.name;
|
|
26836
|
-
const worldDir =
|
|
27262
|
+
const worldDir = path51.join(root, worldId);
|
|
26837
27263
|
let cloneDirs;
|
|
26838
27264
|
try {
|
|
26839
27265
|
cloneDirs = fs46.readdirSync(worldDir, { withFileTypes: true });
|
|
@@ -26842,7 +27268,7 @@ function listOverlays() {
|
|
|
26842
27268
|
}
|
|
26843
27269
|
for (const cloneEntry of cloneDirs) {
|
|
26844
27270
|
if (!cloneEntry.isDirectory()) continue;
|
|
26845
|
-
const graphifyOut =
|
|
27271
|
+
const graphifyOut = path51.join(worldDir, cloneEntry.name, "graphify-out");
|
|
26846
27272
|
if (!fs46.existsSync(graphifyOut)) continue;
|
|
26847
27273
|
records.push({
|
|
26848
27274
|
world_id: worldId,
|
|
@@ -26874,7 +27300,7 @@ function listPristines(overlays) {
|
|
|
26874
27300
|
continue;
|
|
26875
27301
|
}
|
|
26876
27302
|
const fresh = readFreshness(workspace);
|
|
26877
|
-
const graphifyOut =
|
|
27303
|
+
const graphifyOut = path51.join(kgPristinePath(workspace), "graphify-out");
|
|
26878
27304
|
const size = dirSizeBytes2(graphifyOut);
|
|
26879
27305
|
const worldCount = overlays.filter((o) => o.clone_dir === workspace).length;
|
|
26880
27306
|
records.push({
|
|
@@ -27006,12 +27432,12 @@ function registerKgStatusCommand(kg) {
|
|
|
27006
27432
|
}
|
|
27007
27433
|
|
|
27008
27434
|
// src/commands/kg-watch.ts
|
|
27009
|
-
import { spawn as
|
|
27435
|
+
import { spawn as spawn8 } from "node:child_process";
|
|
27010
27436
|
import fs47 from "node:fs";
|
|
27011
|
-
import
|
|
27437
|
+
import path52 from "node:path";
|
|
27012
27438
|
init_output();
|
|
27013
27439
|
function pidFilePath(workspace) {
|
|
27014
|
-
return
|
|
27440
|
+
return path52.join(kgPristinePath(workspace), ".watch.pid");
|
|
27015
27441
|
}
|
|
27016
27442
|
function isPidAlive3(pid) {
|
|
27017
27443
|
if (!Number.isInteger(pid) || pid <= 0) return false;
|
|
@@ -27045,7 +27471,7 @@ function readAndClassifyPid(workspace) {
|
|
|
27045
27471
|
}
|
|
27046
27472
|
function writePidFile(workspace, pid) {
|
|
27047
27473
|
const file = pidFilePath(workspace);
|
|
27048
|
-
const dir =
|
|
27474
|
+
const dir = path52.dirname(file);
|
|
27049
27475
|
fs47.mkdirSync(dir, { recursive: true });
|
|
27050
27476
|
fs47.writeFileSync(file, String(pid), { encoding: "utf-8" });
|
|
27051
27477
|
}
|
|
@@ -27058,7 +27484,7 @@ function removePidFile(workspace) {
|
|
|
27058
27484
|
}
|
|
27059
27485
|
async function runKgWatch(workspaceArg, opts, deps = {}) {
|
|
27060
27486
|
const cwd = deps.cwd ?? opts.cwd ?? process.cwd();
|
|
27061
|
-
const name = workspaceArg ??
|
|
27487
|
+
const name = workspaceArg ?? path52.basename(cwd).toLowerCase();
|
|
27062
27488
|
try {
|
|
27063
27489
|
validateWorkspaceName(name);
|
|
27064
27490
|
} catch (err) {
|
|
@@ -27066,7 +27492,7 @@ async function runKgWatch(workspaceArg, opts, deps = {}) {
|
|
|
27066
27492
|
return { exitCode: 1, pidWritten: false };
|
|
27067
27493
|
}
|
|
27068
27494
|
const pristinePath = kgPristinePath(name);
|
|
27069
|
-
const graphPath =
|
|
27495
|
+
const graphPath = path52.join(pristinePath, "graphify-out", "graph.json");
|
|
27070
27496
|
const pidState = readAndClassifyPid(name);
|
|
27071
27497
|
if (pidState.status === "active") {
|
|
27072
27498
|
printError(
|
|
@@ -27077,7 +27503,7 @@ async function runKgWatch(workspaceArg, opts, deps = {}) {
|
|
|
27077
27503
|
if (pidState.status === "stale-reclaimed") {
|
|
27078
27504
|
printInfo("stale-pid", `reclaimed dead PID file at ${pidFilePath(name)}`);
|
|
27079
27505
|
}
|
|
27080
|
-
const spawnFn = deps.spawnImpl ??
|
|
27506
|
+
const spawnFn = deps.spawnImpl ?? spawn8;
|
|
27081
27507
|
const child = spawnFn(
|
|
27082
27508
|
"graphify",
|
|
27083
27509
|
[cwd, "--watch", "--update", "--graph", graphPath],
|
|
@@ -27132,7 +27558,7 @@ function registerKgWatchCommand(kg) {
|
|
|
27132
27558
|
var DEFAULT_DEVBOX_IMAGE2 = "olam-devbox:latest";
|
|
27133
27559
|
function resolveWorkspace(arg) {
|
|
27134
27560
|
const cwd = process.cwd();
|
|
27135
|
-
const name = arg ??
|
|
27561
|
+
const name = arg ?? path53.basename(cwd).toLowerCase();
|
|
27136
27562
|
validateWorkspaceName(name);
|
|
27137
27563
|
return { name, sourcePath: cwd };
|
|
27138
27564
|
}
|
|
@@ -27154,7 +27580,7 @@ function copyWorkspaceToScratch(source, scratch) {
|
|
|
27154
27580
|
return "cp-r";
|
|
27155
27581
|
}
|
|
27156
27582
|
function parseNodeCount(graphifyOutDir) {
|
|
27157
|
-
const graphPath =
|
|
27583
|
+
const graphPath = path53.join(graphifyOutDir, "graph.json");
|
|
27158
27584
|
if (!fs48.existsSync(graphPath)) return null;
|
|
27159
27585
|
try {
|
|
27160
27586
|
const content = fs48.readFileSync(graphPath, "utf-8");
|
|
@@ -27191,7 +27617,7 @@ async function runKgBuild(workspaceArg, options = {}) {
|
|
|
27191
27617
|
return { exitCode: 2 };
|
|
27192
27618
|
}
|
|
27193
27619
|
const outDir = kgPristinePath(workspace.name);
|
|
27194
|
-
const scratchDir =
|
|
27620
|
+
const scratchDir = path53.join(outDir, "scratch");
|
|
27195
27621
|
fs48.mkdirSync(outDir, { recursive: true });
|
|
27196
27622
|
if (fs48.existsSync(scratchDir)) fs48.rmSync(scratchDir, { recursive: true, force: true });
|
|
27197
27623
|
fs48.mkdirSync(scratchDir);
|
|
@@ -27222,8 +27648,8 @@ async function runKgBuild(workspaceArg, options = {}) {
|
|
|
27222
27648
|
printError(`graphify update failed (exit ${r.status})`);
|
|
27223
27649
|
return { exitCode: r.status ?? 1 };
|
|
27224
27650
|
}
|
|
27225
|
-
const scratchOut =
|
|
27226
|
-
const finalOut =
|
|
27651
|
+
const scratchOut = path53.join(scratchDir, "graphify-out");
|
|
27652
|
+
const finalOut = path53.join(outDir, "graphify-out");
|
|
27227
27653
|
if (!fs48.existsSync(scratchOut)) {
|
|
27228
27654
|
printError(`graphify produced no graphify-out/ in scratch (${scratchOut})`);
|
|
27229
27655
|
return { exitCode: 1 };
|
|
@@ -27242,7 +27668,7 @@ async function runKgBuild(workspaceArg, options = {}) {
|
|
|
27242
27668
|
scratch_strategy: scratchStrategy
|
|
27243
27669
|
};
|
|
27244
27670
|
fs48.writeFileSync(
|
|
27245
|
-
|
|
27671
|
+
path53.join(outDir, "freshness.json"),
|
|
27246
27672
|
JSON.stringify(freshness, null, 2) + "\n",
|
|
27247
27673
|
"utf-8"
|
|
27248
27674
|
);
|
|
@@ -27275,12 +27701,12 @@ function registerKg(program2) {
|
|
|
27275
27701
|
|
|
27276
27702
|
// src/pleri-config.ts
|
|
27277
27703
|
import * as fs49 from "node:fs";
|
|
27278
|
-
import * as
|
|
27704
|
+
import * as path54 from "node:path";
|
|
27279
27705
|
function isPleriConfigured(configDir = process.env.OLAM_CONFIG_DIR ?? ".olam") {
|
|
27280
27706
|
if (process.env.PLERI_BASE_URL) {
|
|
27281
27707
|
return true;
|
|
27282
27708
|
}
|
|
27283
|
-
const configPath =
|
|
27709
|
+
const configPath = path54.join(configDir, "config.yaml");
|
|
27284
27710
|
if (!fs49.existsSync(configPath)) {
|
|
27285
27711
|
return false;
|
|
27286
27712
|
}
|
|
@@ -27323,6 +27749,8 @@ registerRefresh(program);
|
|
|
27323
27749
|
registerBootstrap(program);
|
|
27324
27750
|
registerDiagnose(program);
|
|
27325
27751
|
registerDoctor(program);
|
|
27752
|
+
registerCompletion(program);
|
|
27753
|
+
registerSetup(program);
|
|
27326
27754
|
registerUpdate(program);
|
|
27327
27755
|
registerBegin(program);
|
|
27328
27756
|
registerStop(program);
|