@oxagen/cli 2.1.4-654 → 2.1.4-672
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/oxagen.mjs +324 -193
- package/package.json +1 -1
package/oxagen.mjs
CHANGED
|
@@ -9656,7 +9656,7 @@ function describeAgent(agent) {
|
|
|
9656
9656
|
if (agent.host.revoked_at !== null)
|
|
9657
9657
|
return `${what} (retired on this machine)`;
|
|
9658
9658
|
if (agent.host.host_status === "revoked")
|
|
9659
|
-
return `${what} (revoked on the
|
|
9659
|
+
return `${what} (revoked on the Runs page)`;
|
|
9660
9660
|
return what;
|
|
9661
9661
|
}
|
|
9662
9662
|
function portsInUse(home, exceptDir) {
|
|
@@ -24104,7 +24104,7 @@ import { readFileSync as readFileSync11 } from "node:fs";
|
|
|
24104
24104
|
import { dirname as dirname9, resolve as resolve3 } from "node:path";
|
|
24105
24105
|
import { fileURLToPath } from "node:url";
|
|
24106
24106
|
function readVersion() {
|
|
24107
|
-
if (true) return "2.1.4-
|
|
24107
|
+
if (true) return "2.1.4-672";
|
|
24108
24108
|
try {
|
|
24109
24109
|
const here = dirname9(fileURLToPath(import.meta.url));
|
|
24110
24110
|
const pkg = JSON.parse(
|
|
@@ -28266,7 +28266,7 @@ function printStatus(report, deps) {
|
|
|
28266
28266
|
} = report;
|
|
28267
28267
|
if (report.retired === true)
|
|
28268
28268
|
deps.out(
|
|
28269
|
-
`Not enrolled. ${h.host_enrollment_id} was unenrolled here on ${h.revoked_at ?? ""}. The server-side revoke is still pending: run \`oxagen agent unenroll\` again while signed in, or revoke it from the
|
|
28269
|
+
`Not enrolled. ${h.host_enrollment_id} was unenrolled here on ${h.revoked_at ?? ""}. The server-side revoke is still pending: run \`oxagen agent unenroll\` again while signed in, or revoke it from the Runs page.`
|
|
28270
28270
|
);
|
|
28271
28271
|
for (const problem of report.problems ?? [])
|
|
28272
28272
|
deps.out(`Unreadable ${problem}`);
|
|
@@ -28428,7 +28428,7 @@ async function revokeOnControlPlane(host, options, deps, warnings) {
|
|
|
28428
28428
|
);
|
|
28429
28429
|
if ("missing" in resolved) {
|
|
28430
28430
|
warnings.push(
|
|
28431
|
-
"no operator token; the host stays active server-side until an operator revokes it (`oxagen login`, then `oxagen agent unenroll` again, or revoke from the
|
|
28431
|
+
"no operator token; the host stays active server-side until an operator revokes it (`oxagen login`, then `oxagen agent unenroll` again, or revoke from the Runs page)"
|
|
28432
28432
|
);
|
|
28433
28433
|
return false;
|
|
28434
28434
|
}
|
|
@@ -28806,7 +28806,7 @@ async function unenrollLocked(options, deps) {
|
|
|
28806
28806
|
const host = read2.host;
|
|
28807
28807
|
if (read2.error !== void 0) {
|
|
28808
28808
|
warnings.push(
|
|
28809
|
-
`${read2.error}; removing the hooks and the service anyway. The enrollment cannot be revoked from here: revoke it from the
|
|
28809
|
+
`${read2.error}; removing the hooks and the service anyway. The enrollment cannot be revoked from here: revoke it from the Runs page.`
|
|
28810
28810
|
);
|
|
28811
28811
|
incomplete = true;
|
|
28812
28812
|
}
|
|
@@ -29758,7 +29758,7 @@ ${problems.map((problem) => ` ${problem}`).join("\n")}`
|
|
|
29758
29758
|
}
|
|
29759
29759
|
} else
|
|
29760
29760
|
warnings.push(
|
|
29761
|
-
`the previous enrollment ${existing.host_enrollment_id} could not be revoked (${problems.join("; ")}); its host key stays valid until ${existing.expires_at} unless an operator revokes it from the
|
|
29761
|
+
`the previous enrollment ${existing.host_enrollment_id} could not be revoked (${problems.join("; ")}); its host key stays valid until ${existing.expires_at} unless an operator revokes it from the Runs page`
|
|
29762
29762
|
);
|
|
29763
29763
|
}
|
|
29764
29764
|
}
|
|
@@ -31166,7 +31166,7 @@ ${refusals.map((refusal) => ` ${refusal}`).join("\n")}`
|
|
|
31166
31166
|
warnings
|
|
31167
31167
|
);
|
|
31168
31168
|
deps.out(
|
|
31169
|
-
revoked ? " revoked" : " not revoked server-side; the next reassign or unenroll asks again, or an operator can finish it from the
|
|
31169
|
+
revoked ? " revoked" : " not revoked server-side; the next reassign or unenroll asks again, or an operator can finish it from the Runs page"
|
|
31170
31170
|
);
|
|
31171
31171
|
deps.out("[2/3] Removing the old enrollment's hooks");
|
|
31172
31172
|
for (const failure2 of (await stripEnrollmentHooks(host, deps)).failed)
|
|
@@ -31636,7 +31636,7 @@ async function uninstall(options, deps) {
|
|
|
31636
31636
|
for (const path2 of tally2.removed) deps.out(` removed ${path2}`);
|
|
31637
31637
|
for (const revoke of pending)
|
|
31638
31638
|
warnings.push(
|
|
31639
|
-
`the control plane did not confirm the revoke of ${revoke}. Revoke it on the
|
|
31639
|
+
`the control plane did not confirm the revoke of ${revoke}. Revoke it on the Runs page`
|
|
31640
31640
|
);
|
|
31641
31641
|
for (const warning of warnings.slice(unenrolled.warnings.length))
|
|
31642
31642
|
deps.err(`warning: ${warning}`);
|
|
@@ -55176,7 +55176,7 @@ var init_package = __esm({
|
|
|
55176
55176
|
"package.json"() {
|
|
55177
55177
|
package_default = {
|
|
55178
55178
|
name: "@oxagen/cli",
|
|
55179
|
-
version: "2.1.4-
|
|
55179
|
+
version: "2.1.4-672",
|
|
55180
55180
|
description: "Oxagen governance CLI \u2014 spend, lineage, grounding, credentials, and audit (agentic coding lives in the stella CLI)",
|
|
55181
55181
|
type: "module",
|
|
55182
55182
|
main: "./dist/index.js",
|
|
@@ -58176,6 +58176,233 @@ var init_repo = __esm({
|
|
|
58176
58176
|
}
|
|
58177
58177
|
});
|
|
58178
58178
|
|
|
58179
|
+
// src/commands/steering-findings.ts
|
|
58180
|
+
var steering_findings_exports = {};
|
|
58181
|
+
__export(steering_findings_exports, {
|
|
58182
|
+
PROPOSAL_STATUS_WORDS: () => PROPOSAL_STATUS_WORDS,
|
|
58183
|
+
STEERING_FINDINGS_CAPABILITIES: () => STEERING_FINDINGS_CAPABILITIES,
|
|
58184
|
+
apiRefusal: () => apiRefusal,
|
|
58185
|
+
reportApiFailure: () => reportApiFailure,
|
|
58186
|
+
steeringFindings: () => steeringFindings,
|
|
58187
|
+
usageError: () => usageError
|
|
58188
|
+
});
|
|
58189
|
+
function isRecord7(value) {
|
|
58190
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
58191
|
+
}
|
|
58192
|
+
function textOrNull(value) {
|
|
58193
|
+
return typeof value === "string" && value.length > 0 ? value : null;
|
|
58194
|
+
}
|
|
58195
|
+
function apiRefusal(err2) {
|
|
58196
|
+
const message = errorMessage(err2);
|
|
58197
|
+
const start = message.indexOf("{");
|
|
58198
|
+
const end = message.lastIndexOf("}");
|
|
58199
|
+
if (start >= 0 && end > start) {
|
|
58200
|
+
try {
|
|
58201
|
+
const body2 = JSON.parse(message.slice(start, end + 1));
|
|
58202
|
+
const error = isRecord7(body2) && isRecord7(body2.error) ? body2.error : null;
|
|
58203
|
+
const said = error === null ? null : textOrNull(error.message);
|
|
58204
|
+
if (error !== null && said !== null) {
|
|
58205
|
+
return {
|
|
58206
|
+
code: textOrNull(error.code),
|
|
58207
|
+
reason: textOrNull(error.reason),
|
|
58208
|
+
message: said
|
|
58209
|
+
};
|
|
58210
|
+
}
|
|
58211
|
+
} catch {
|
|
58212
|
+
}
|
|
58213
|
+
}
|
|
58214
|
+
return { code: null, reason: null, message };
|
|
58215
|
+
}
|
|
58216
|
+
function reportApiFailure(out, writer, err2, nextSteps = {}) {
|
|
58217
|
+
const refusal = apiRefusal(err2);
|
|
58218
|
+
out.error(refusal.message, refusal.reason ?? refusal.code ?? "api");
|
|
58219
|
+
if (out.isJson || refusal.reason === null) return;
|
|
58220
|
+
const next = nextSteps[refusal.reason];
|
|
58221
|
+
if (next !== void 0) writer.writeErr(next);
|
|
58222
|
+
}
|
|
58223
|
+
function usageError(writer, message, line) {
|
|
58224
|
+
writer.writeErr(`error: ${message}`);
|
|
58225
|
+
writer.writeErr(`usage: ${line}`);
|
|
58226
|
+
process.exitCode = 2;
|
|
58227
|
+
}
|
|
58228
|
+
function plural(count12, one, many) {
|
|
58229
|
+
return `${count12} ${count12 === 1 ? one : many}`;
|
|
58230
|
+
}
|
|
58231
|
+
function findingRow(finding) {
|
|
58232
|
+
const pr = finding.pull_request;
|
|
58233
|
+
const proposal = finding.proposal;
|
|
58234
|
+
return [
|
|
58235
|
+
finding.id,
|
|
58236
|
+
finding.kind,
|
|
58237
|
+
`${finding.path}:${finding.line}`,
|
|
58238
|
+
finding.record.label ?? finding.record.lineage,
|
|
58239
|
+
`#${pr.number} ${pr.state}`,
|
|
58240
|
+
proposal === null ? "none" : `${proposal.id} (${PROPOSAL_STATUS_WORDS[proposal.status]})`
|
|
58241
|
+
];
|
|
58242
|
+
}
|
|
58243
|
+
async function steeringFindings(opts = {}, writer = stdoutWriter) {
|
|
58244
|
+
const out = createOutput({ json: opts.json }, writer);
|
|
58245
|
+
let result2;
|
|
58246
|
+
try {
|
|
58247
|
+
result2 = await apiGetOrThrow(
|
|
58248
|
+
"repository/findings"
|
|
58249
|
+
);
|
|
58250
|
+
} catch (err2) {
|
|
58251
|
+
reportApiFailure(out, writer, err2);
|
|
58252
|
+
return;
|
|
58253
|
+
}
|
|
58254
|
+
if (out.isJson) {
|
|
58255
|
+
out.data(result2);
|
|
58256
|
+
return;
|
|
58257
|
+
}
|
|
58258
|
+
const repositories = result2.repositories.filter((r) => r.findings.length > 0);
|
|
58259
|
+
if (repositories.length === 0) {
|
|
58260
|
+
writer.write(
|
|
58261
|
+
"No findings. The Oxagen check found no statement in a linked repository's instruction files that repeats or contradicts a steering record."
|
|
58262
|
+
);
|
|
58263
|
+
return;
|
|
58264
|
+
}
|
|
58265
|
+
let total2 = 0;
|
|
58266
|
+
for (const [index, repository] of repositories.entries()) {
|
|
58267
|
+
if (index > 0) writer.write("");
|
|
58268
|
+
writer.write(`${repository.full_name} (${repository.provider})`);
|
|
58269
|
+
printTable(
|
|
58270
|
+
["FINDING", "KIND", "FILE", "RECORD", "PULL REQUEST", "PROPOSAL"],
|
|
58271
|
+
repository.findings.map(findingRow),
|
|
58272
|
+
writer
|
|
58273
|
+
);
|
|
58274
|
+
total2 += repository.findings.length;
|
|
58275
|
+
}
|
|
58276
|
+
writer.write("");
|
|
58277
|
+
writer.write(
|
|
58278
|
+
`${plural(total2, "finding", "findings")} in ${plural(repositories.length, "repository", "repositories")}.`
|
|
58279
|
+
);
|
|
58280
|
+
const promotable = repositories.some(
|
|
58281
|
+
(r) => r.findings.some((f) => f.kind === "contradiction" && f.proposal === null)
|
|
58282
|
+
);
|
|
58283
|
+
if (promotable) {
|
|
58284
|
+
writer.write(
|
|
58285
|
+
"Promote a contradiction to a proposal with `oxagen steering promote <finding-id>`."
|
|
58286
|
+
);
|
|
58287
|
+
}
|
|
58288
|
+
}
|
|
58289
|
+
var STEERING_FINDINGS_CAPABILITIES, PROPOSAL_STATUS_WORDS;
|
|
58290
|
+
var init_steering_findings = __esm({
|
|
58291
|
+
"src/commands/steering-findings.ts"() {
|
|
58292
|
+
init_api();
|
|
58293
|
+
init_capture_writer();
|
|
58294
|
+
init_output();
|
|
58295
|
+
STEERING_FINDINGS_CAPABILITIES = [
|
|
58296
|
+
"list_code_repository_findings"
|
|
58297
|
+
];
|
|
58298
|
+
PROPOSAL_STATUS_WORDS = {
|
|
58299
|
+
proposed: "waiting for its steering PR",
|
|
58300
|
+
pr_open: "steering PR open",
|
|
58301
|
+
checks_running: "checks running",
|
|
58302
|
+
checks_passed: "checks passed",
|
|
58303
|
+
checks_failed: "checks failed",
|
|
58304
|
+
merged: "merged",
|
|
58305
|
+
rejected: "rejected"
|
|
58306
|
+
};
|
|
58307
|
+
}
|
|
58308
|
+
});
|
|
58309
|
+
|
|
58310
|
+
// src/commands/repo-scan.ts
|
|
58311
|
+
var repo_scan_exports = {};
|
|
58312
|
+
__export(repo_scan_exports, {
|
|
58313
|
+
REPO_SCAN_CAPABILITIES: () => REPO_SCAN_CAPABILITIES,
|
|
58314
|
+
repoScan: () => repoScan
|
|
58315
|
+
});
|
|
58316
|
+
function fileRow(file) {
|
|
58317
|
+
const size = file.size === null ? "-" : String(file.size);
|
|
58318
|
+
const files3 = file.kind === "skill" ? ` (${file.files.length} files)` : "";
|
|
58319
|
+
return [
|
|
58320
|
+
file.kind,
|
|
58321
|
+
`${file.path}${files3}`,
|
|
58322
|
+
file.harness,
|
|
58323
|
+
size,
|
|
58324
|
+
file.fixture ? "fixture" : ""
|
|
58325
|
+
];
|
|
58326
|
+
}
|
|
58327
|
+
function plural2(count12, one, many) {
|
|
58328
|
+
return `${count12} ${count12 === 1 ? one : many}`;
|
|
58329
|
+
}
|
|
58330
|
+
function countsLine(counts) {
|
|
58331
|
+
const parts = [
|
|
58332
|
+
[counts.instructions, "instruction file", "instruction files"],
|
|
58333
|
+
[counts.rule, "rule", "rules"],
|
|
58334
|
+
[counts.skill, "skill", "skills"],
|
|
58335
|
+
[counts.command, "command", "commands"],
|
|
58336
|
+
[counts.subagent, "subagent file", "subagent files"],
|
|
58337
|
+
[counts.settings, "settings file", "settings files"],
|
|
58338
|
+
[counts.mcpConfig, "MCP config", "MCP configs"],
|
|
58339
|
+
[counts.personal, "personal file", "personal files"]
|
|
58340
|
+
];
|
|
58341
|
+
const found = parts.filter(([n4]) => n4 > 0).map(([n4, one, many]) => plural2(n4, one, many));
|
|
58342
|
+
const fixtures = counts.fixtures > 0 ? `, and ${plural2(counts.fixtures, "file", "files")} under fixture folders` : "";
|
|
58343
|
+
return `${found.length > 0 ? found.join(", ") : "No harness files"}${fixtures}.`;
|
|
58344
|
+
}
|
|
58345
|
+
async function repoScan(ref2, opts = {}, writer = stdoutWriter) {
|
|
58346
|
+
const fullName = ref2.trim().replace(/^\/+|\/+$/g, "");
|
|
58347
|
+
if (!/^[^/\s]+(\/[^/\s]+)+$/.test(fullName)) {
|
|
58348
|
+
usageError(
|
|
58349
|
+
writer,
|
|
58350
|
+
`expected <owner/name>, got ${JSON.stringify(ref2)}`,
|
|
58351
|
+
USAGE
|
|
58352
|
+
);
|
|
58353
|
+
return;
|
|
58354
|
+
}
|
|
58355
|
+
const out = createOutput({ json: opts.json }, writer);
|
|
58356
|
+
let result2;
|
|
58357
|
+
try {
|
|
58358
|
+
result2 = await apiPostOrThrow(
|
|
58359
|
+
"repository/config/scan",
|
|
58360
|
+
{ provider: opts.gitlab ? "gitlab" : "github", fullName }
|
|
58361
|
+
);
|
|
58362
|
+
} catch (err2) {
|
|
58363
|
+
reportApiFailure(out, writer, err2, NEXT_STEPS);
|
|
58364
|
+
return;
|
|
58365
|
+
}
|
|
58366
|
+
if (out.isJson) {
|
|
58367
|
+
out.data(result2);
|
|
58368
|
+
return;
|
|
58369
|
+
}
|
|
58370
|
+
writer.write(
|
|
58371
|
+
`${result2.fullName} (${result2.provider}), ${result2.defaultBranch} at ${result2.commitSha}`
|
|
58372
|
+
);
|
|
58373
|
+
if (result2.partialReason !== null) writer.write(result2.partialReason);
|
|
58374
|
+
if (result2.files.length > 0) {
|
|
58375
|
+
writer.write("");
|
|
58376
|
+
printTable(
|
|
58377
|
+
["KIND", "PATH", "HARNESS", "BYTES", "FIXTURE"],
|
|
58378
|
+
result2.files.map(fileRow),
|
|
58379
|
+
writer
|
|
58380
|
+
);
|
|
58381
|
+
}
|
|
58382
|
+
if (result2.aliases.length > 0) {
|
|
58383
|
+
writer.write("");
|
|
58384
|
+
for (const alias of result2.aliases) writer.write(`${alias.path}: ${alias.reason}`);
|
|
58385
|
+
}
|
|
58386
|
+
writer.write("");
|
|
58387
|
+
writer.write(countsLine(result2.counts));
|
|
58388
|
+
}
|
|
58389
|
+
var REPO_SCAN_CAPABILITIES, USAGE, NEXT_STEPS;
|
|
58390
|
+
var init_repo_scan = __esm({
|
|
58391
|
+
"src/commands/repo-scan.ts"() {
|
|
58392
|
+
init_api();
|
|
58393
|
+
init_capture_writer();
|
|
58394
|
+
init_output();
|
|
58395
|
+
init_steering_findings();
|
|
58396
|
+
REPO_SCAN_CAPABILITIES = ["scan_repository_config"];
|
|
58397
|
+
USAGE = "oxagen repo scan <owner/name> [--gitlab] [--json]";
|
|
58398
|
+
NEXT_STEPS = {
|
|
58399
|
+
github_not_connected: "Connect GitHub from the Repositories page, then scan again.",
|
|
58400
|
+
repository_not_installed: "Give the Oxagen GitHub App access to the repository, then scan again.",
|
|
58401
|
+
gitlab_not_connected: "Connect the GitLab project with a project access token, then scan again."
|
|
58402
|
+
};
|
|
58403
|
+
}
|
|
58404
|
+
});
|
|
58405
|
+
|
|
58179
58406
|
// ../../packages/steering-freshness/src/git.ts
|
|
58180
58407
|
import { execFile as execFile5 } from "node:child_process";
|
|
58181
58408
|
function classifyProbeFailure(err2) {
|
|
@@ -58601,23 +58828,23 @@ function hookConfigPath(projectRoot, harness, env = process.env, home = homedir1
|
|
|
58601
58828
|
function stellaJsonPath(env, home) {
|
|
58602
58829
|
return join46(env["STELLA_HOME"] ?? join46(home, ".stella"), "settings.json");
|
|
58603
58830
|
}
|
|
58604
|
-
function
|
|
58831
|
+
function isRecord8(v) {
|
|
58605
58832
|
return v !== null && typeof v === "object" && !Array.isArray(v);
|
|
58606
58833
|
}
|
|
58607
58834
|
function readConfig2(text5) {
|
|
58608
58835
|
try {
|
|
58609
58836
|
const parsed2 = JSON.parse(text5);
|
|
58610
|
-
if (!
|
|
58837
|
+
if (!isRecord8(parsed2)) return null;
|
|
58611
58838
|
if (parsed2["hooks"] === void 0) return parsed2;
|
|
58612
58839
|
const hooks = parsed2["hooks"];
|
|
58613
|
-
if (!
|
|
58840
|
+
if (!isRecord8(hooks)) return null;
|
|
58614
58841
|
for (const groups of Object.values(hooks)) {
|
|
58615
58842
|
if (!Array.isArray(groups)) return null;
|
|
58616
58843
|
for (const group of groups) {
|
|
58617
|
-
if (!
|
|
58844
|
+
if (!isRecord8(group)) return null;
|
|
58618
58845
|
if (group["hooks"] === void 0) continue;
|
|
58619
58846
|
if (!Array.isArray(group["hooks"])) return null;
|
|
58620
|
-
if (!group["hooks"].every(
|
|
58847
|
+
if (!group["hooks"].every(isRecord8)) return null;
|
|
58621
58848
|
}
|
|
58622
58849
|
}
|
|
58623
58850
|
return parsed2;
|
|
@@ -58749,12 +58976,12 @@ async function groupHookInstalled(path2, io) {
|
|
|
58749
58976
|
function readCursorConfig(text5) {
|
|
58750
58977
|
try {
|
|
58751
58978
|
const parsed2 = JSON.parse(text5);
|
|
58752
|
-
if (!
|
|
58979
|
+
if (!isRecord8(parsed2)) return null;
|
|
58753
58980
|
if (parsed2["hooks"] === void 0) return parsed2;
|
|
58754
58981
|
const hooks = parsed2["hooks"];
|
|
58755
|
-
if (!
|
|
58982
|
+
if (!isRecord8(hooks)) return null;
|
|
58756
58983
|
for (const entries2 of Object.values(hooks)) {
|
|
58757
|
-
if (!Array.isArray(entries2) || !entries2.every(
|
|
58984
|
+
if (!Array.isArray(entries2) || !entries2.every(isRecord8)) return null;
|
|
58758
58985
|
}
|
|
58759
58986
|
return parsed2;
|
|
58760
58987
|
} catch {
|
|
@@ -73339,6 +73566,15 @@ var init_src4 = __esm({
|
|
|
73339
73566
|
}
|
|
73340
73567
|
});
|
|
73341
73568
|
|
|
73569
|
+
// ../../packages/oxagen/src/run-enrichment.ts
|
|
73570
|
+
var RUN_SUMMARY_MODES;
|
|
73571
|
+
var init_run_enrichment = __esm({
|
|
73572
|
+
"../../packages/oxagen/src/run-enrichment.ts"() {
|
|
73573
|
+
"use strict";
|
|
73574
|
+
RUN_SUMMARY_MODES = ["always", "on_demand", "never"];
|
|
73575
|
+
}
|
|
73576
|
+
});
|
|
73577
|
+
|
|
73342
73578
|
// ../../packages/oxagen/src/run-fit.ts
|
|
73343
73579
|
var RUN_FIT_METHOD, runEffortSourceSchema, runFitReadSchema, runModelFitSchema, runEffortFitSchema, runFitReadingSchema, runFitSchema;
|
|
73344
73580
|
var init_run_fit = __esm({
|
|
@@ -73415,6 +73651,7 @@ var init_run_list = __esm({
|
|
|
73415
73651
|
init_zod();
|
|
73416
73652
|
init_src3();
|
|
73417
73653
|
init_registry2();
|
|
73654
|
+
init_run_enrichment();
|
|
73418
73655
|
init_run_fit();
|
|
73419
73656
|
init_spend_shared();
|
|
73420
73657
|
init_run_shared();
|
|
@@ -73802,21 +74039,38 @@ var init_run_list = __esm({
|
|
|
73802
74039
|
version: external_exports.string().nullable(),
|
|
73803
74040
|
runtime: external_exports.string().nullable()
|
|
73804
74041
|
}).nullable(),
|
|
73805
|
-
/**
|
|
74042
|
+
/**
|
|
74043
|
+
* The workspace's run summaries mode (D30): `always`, `on_demand`, or
|
|
74044
|
+
* `never`. It decides whether the run offers Summarize
|
|
74045
|
+
* (`summarizeOffered` in `@oxagen/oxagen/run-enrichment`). oxagen names
|
|
74046
|
+
* every run in every mode.
|
|
74047
|
+
*/
|
|
74048
|
+
summaries: external_exports.enum(RUN_SUMMARY_MODES).optional(),
|
|
74049
|
+
/**
|
|
74050
|
+
* Deprecated: true only under the `always` mode. It used to be the switch
|
|
74051
|
+
* that turned run names and summaries off together (ADR-153).
|
|
74052
|
+
*/
|
|
73806
74053
|
enrichmentEnabled: external_exports.boolean().optional(),
|
|
73807
74054
|
/**
|
|
73808
74055
|
* Why the last automatic account failed, as a short reason code such as
|
|
73809
|
-
* `
|
|
74056
|
+
* `customer_key_refused` or `credit_refused:<code>`. Absent once an
|
|
74057
|
+
* account exists, and under the `never` mode.
|
|
73810
74058
|
*/
|
|
73811
74059
|
enrichmentError: external_exports.string().optional(),
|
|
74060
|
+
/**
|
|
74061
|
+
* True on a sealed run under `always` whose summary failed: the model
|
|
74062
|
+
* provider refused a key the customer brought (D30). Such a run offers
|
|
74063
|
+
* Summarize and a banner that names the reason.
|
|
74064
|
+
*/
|
|
74065
|
+
summaryFailed: external_exports.boolean().optional(),
|
|
73812
74066
|
/**
|
|
73813
74067
|
* What the run is called, cut to `RUN_LABEL_MAX` with an ellipsis. A
|
|
73814
74068
|
* name a person gave the run (`edit_run`) comes first. Otherwise a
|
|
73815
74069
|
* wrapped session reads the title its harness gave it, then the name
|
|
73816
74070
|
* Oxagen wrote (the model's, or the fallback from the first prompt),
|
|
73817
74071
|
* then the title ingest derived, and a ledger run reads the name Oxagen
|
|
73818
|
-
* wrote.
|
|
73819
|
-
*
|
|
74072
|
+
* wrote. oxagen names every run in every run summaries mode (D30). Null
|
|
74073
|
+
* when there is none.
|
|
73820
74074
|
*/
|
|
73821
74075
|
name: external_exports.string().max(RUN_LABEL_MAX).nullable(),
|
|
73822
74076
|
/**
|
|
@@ -73940,7 +74194,7 @@ var init_run_list = __esm({
|
|
|
73940
74194
|
/**
|
|
73941
74195
|
* `true` answers `liveRuns`, the workspace's live count. The count reads
|
|
73942
74196
|
* every root session the workspace holds, so a read that does not show
|
|
73943
|
-
* it leaves this out and pays nothing for it.
|
|
74197
|
+
* it leaves this out and pays nothing for it. Runs sets it.
|
|
73944
74198
|
*/
|
|
73945
74199
|
countLive: external_exports.boolean().optional()
|
|
73946
74200
|
}).strict(),
|
|
@@ -74413,7 +74667,7 @@ var init_steering_repo = __esm({
|
|
|
74413
74667
|
});
|
|
74414
74668
|
|
|
74415
74669
|
// ../../packages/steering-check/src/repo.ts
|
|
74416
|
-
function
|
|
74670
|
+
function isRecord9(value) {
|
|
74417
74671
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
74418
74672
|
}
|
|
74419
74673
|
function isString(value) {
|
|
@@ -74539,7 +74793,7 @@ function parseTomlLoose(text5) {
|
|
|
74539
74793
|
if (text5 === void 0) return null;
|
|
74540
74794
|
try {
|
|
74541
74795
|
const value = parse(text5);
|
|
74542
|
-
return
|
|
74796
|
+
return isRecord9(value) ? value : null;
|
|
74543
74797
|
} catch {
|
|
74544
74798
|
return null;
|
|
74545
74799
|
}
|
|
@@ -74547,7 +74801,7 @@ function parseTomlLoose(text5) {
|
|
|
74547
74801
|
function canonicalJson(value) {
|
|
74548
74802
|
if (Array.isArray(value))
|
|
74549
74803
|
return `[${value.map(canonicalJson).join(",")}]`;
|
|
74550
|
-
if (
|
|
74804
|
+
if (isRecord9(value)) {
|
|
74551
74805
|
const keys = Object.keys(value).sort();
|
|
74552
74806
|
return `{${keys.map((key) => `${JSON.stringify(key)}:${canonicalJson(value[key])}`).join(",")}}`;
|
|
74553
74807
|
}
|
|
@@ -74557,7 +74811,7 @@ function parseJsonLoose(text5) {
|
|
|
74557
74811
|
if (text5 === void 0) return null;
|
|
74558
74812
|
try {
|
|
74559
74813
|
const value = JSON.parse(text5);
|
|
74560
|
-
return
|
|
74814
|
+
return isRecord9(value) ? value : null;
|
|
74561
74815
|
} catch {
|
|
74562
74816
|
return null;
|
|
74563
74817
|
}
|
|
@@ -74571,9 +74825,9 @@ function workspaceRepositories(tree) {
|
|
|
74571
74825
|
}
|
|
74572
74826
|
function entries(value) {
|
|
74573
74827
|
const found = /* @__PURE__ */ new Map();
|
|
74574
|
-
if (!
|
|
74828
|
+
if (!isRecord9(value)) return found;
|
|
74575
74829
|
for (const [key, entry2] of Object.entries(value)) {
|
|
74576
|
-
if (
|
|
74830
|
+
if (isRecord9(entry2)) found.set(key, entry2);
|
|
74577
74831
|
}
|
|
74578
74832
|
return found;
|
|
74579
74833
|
}
|
|
@@ -74739,7 +74993,7 @@ function isPositiveInteger(value) {
|
|
|
74739
74993
|
}
|
|
74740
74994
|
function alwaysOnBudget(tree) {
|
|
74741
74995
|
const steering = parseTomlLoose(tree?.get(GOVERNANCE_TOML_PATH))?.steering;
|
|
74742
|
-
const value =
|
|
74996
|
+
const value = isRecord9(steering) ? steering.always_on_tokens : void 0;
|
|
74743
74997
|
if (value === "off") return "off";
|
|
74744
74998
|
if (isPositiveInteger(value))
|
|
74745
74999
|
return { tokens: value, source: "governance.toml" };
|
|
@@ -74747,7 +75001,7 @@ function alwaysOnBudget(tree) {
|
|
|
74747
75001
|
}
|
|
74748
75002
|
function definitionBudget(tree) {
|
|
74749
75003
|
const tools = parseTomlLoose(tree?.get(WORKSPACE_TOML_PATH))?.tools;
|
|
74750
|
-
const value =
|
|
75004
|
+
const value = isRecord9(tools) ? tools.definition_budget : void 0;
|
|
74751
75005
|
return isPositiveInteger(value) ? { tokens: value, source: "workspace.toml" } : {
|
|
74752
75006
|
tokens: DEFAULT_WORKSPACE_DEFINITION_BUDGET,
|
|
74753
75007
|
source: "Oxagen's default"
|
|
@@ -74855,12 +75109,12 @@ function directDefinitions(tree) {
|
|
|
74855
75109
|
const servers = [];
|
|
74856
75110
|
for (const [name, folder] of serverFolders(tree)) {
|
|
74857
75111
|
const exposure = folder.server?.exposure;
|
|
74858
|
-
if (!
|
|
75112
|
+
if (!isRecord9(exposure) || exposure.mode !== "direct") continue;
|
|
74859
75113
|
let tokens = 0;
|
|
74860
75114
|
let tools = 0;
|
|
74861
75115
|
for (const [key, entry2] of folder.tools) {
|
|
74862
75116
|
const upstream = folder.locked.get(key)?.upstream;
|
|
74863
|
-
if (!
|
|
75117
|
+
if (!isRecord9(upstream)) continue;
|
|
74864
75118
|
const description = isString(entry2.description) ? entry2.description : upstream.description;
|
|
74865
75119
|
const definition = {
|
|
74866
75120
|
name: `${name}__${key}`,
|
|
@@ -75613,7 +75867,7 @@ function credentialFields(value, prefix = "") {
|
|
|
75613
75867
|
(item, n4) => credentialFields(item, prefix === "" ? String(n4) : `${prefix}.${n4}`)
|
|
75614
75868
|
);
|
|
75615
75869
|
}
|
|
75616
|
-
if (!
|
|
75870
|
+
if (!isRecord9(value)) return [];
|
|
75617
75871
|
return Object.entries(value).flatMap(
|
|
75618
75872
|
([key, item]) => credentialFields(item, prefix === "" ? key : `${prefix}.${key}`)
|
|
75619
75873
|
);
|
|
@@ -75649,7 +75903,7 @@ function groupFindings(tree, context) {
|
|
|
75649
75903
|
const reviewers = parsed2.reviewers;
|
|
75650
75904
|
const findings = [];
|
|
75651
75905
|
reviewers.forEach((entry2, n4) => {
|
|
75652
|
-
if (!
|
|
75906
|
+
if (!isRecord9(entry2) || !isString(entry2.group) || context.groups.includes(entry2.group))
|
|
75653
75907
|
return;
|
|
75654
75908
|
const field = `reviewers.${n4}.group`;
|
|
75655
75909
|
findings.push(
|
|
@@ -77309,137 +77563,6 @@ var init_steering_import = __esm({
|
|
|
77309
77563
|
}
|
|
77310
77564
|
});
|
|
77311
77565
|
|
|
77312
|
-
// src/commands/steering-findings.ts
|
|
77313
|
-
var steering_findings_exports = {};
|
|
77314
|
-
__export(steering_findings_exports, {
|
|
77315
|
-
PROPOSAL_STATUS_WORDS: () => PROPOSAL_STATUS_WORDS,
|
|
77316
|
-
STEERING_FINDINGS_CAPABILITIES: () => STEERING_FINDINGS_CAPABILITIES,
|
|
77317
|
-
apiRefusal: () => apiRefusal,
|
|
77318
|
-
reportApiFailure: () => reportApiFailure,
|
|
77319
|
-
steeringFindings: () => steeringFindings,
|
|
77320
|
-
usageError: () => usageError
|
|
77321
|
-
});
|
|
77322
|
-
function isRecord9(value) {
|
|
77323
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
77324
|
-
}
|
|
77325
|
-
function textOrNull(value) {
|
|
77326
|
-
return typeof value === "string" && value.length > 0 ? value : null;
|
|
77327
|
-
}
|
|
77328
|
-
function apiRefusal(err2) {
|
|
77329
|
-
const message = errorMessage(err2);
|
|
77330
|
-
const start = message.indexOf("{");
|
|
77331
|
-
const end = message.lastIndexOf("}");
|
|
77332
|
-
if (start >= 0 && end > start) {
|
|
77333
|
-
try {
|
|
77334
|
-
const body2 = JSON.parse(message.slice(start, end + 1));
|
|
77335
|
-
const error = isRecord9(body2) && isRecord9(body2.error) ? body2.error : null;
|
|
77336
|
-
const said = error === null ? null : textOrNull(error.message);
|
|
77337
|
-
if (error !== null && said !== null) {
|
|
77338
|
-
return {
|
|
77339
|
-
code: textOrNull(error.code),
|
|
77340
|
-
reason: textOrNull(error.reason),
|
|
77341
|
-
message: said
|
|
77342
|
-
};
|
|
77343
|
-
}
|
|
77344
|
-
} catch {
|
|
77345
|
-
}
|
|
77346
|
-
}
|
|
77347
|
-
return { code: null, reason: null, message };
|
|
77348
|
-
}
|
|
77349
|
-
function reportApiFailure(out, writer, err2, nextSteps = {}) {
|
|
77350
|
-
const refusal = apiRefusal(err2);
|
|
77351
|
-
out.error(refusal.message, refusal.reason ?? refusal.code ?? "api");
|
|
77352
|
-
if (out.isJson || refusal.reason === null) return;
|
|
77353
|
-
const next = nextSteps[refusal.reason];
|
|
77354
|
-
if (next !== void 0) writer.writeErr(next);
|
|
77355
|
-
}
|
|
77356
|
-
function usageError(writer, message, line) {
|
|
77357
|
-
writer.writeErr(`error: ${message}`);
|
|
77358
|
-
writer.writeErr(`usage: ${line}`);
|
|
77359
|
-
process.exitCode = 2;
|
|
77360
|
-
}
|
|
77361
|
-
function plural(count12, one, many) {
|
|
77362
|
-
return `${count12} ${count12 === 1 ? one : many}`;
|
|
77363
|
-
}
|
|
77364
|
-
function findingRow(finding) {
|
|
77365
|
-
const pr = finding.pull_request;
|
|
77366
|
-
const proposal = finding.proposal;
|
|
77367
|
-
return [
|
|
77368
|
-
finding.id,
|
|
77369
|
-
finding.kind,
|
|
77370
|
-
`${finding.path}:${finding.line}`,
|
|
77371
|
-
finding.record.label ?? finding.record.lineage,
|
|
77372
|
-
`#${pr.number} ${pr.state}`,
|
|
77373
|
-
proposal === null ? "none" : `${proposal.id} (${PROPOSAL_STATUS_WORDS[proposal.status]})`
|
|
77374
|
-
];
|
|
77375
|
-
}
|
|
77376
|
-
async function steeringFindings(opts = {}, writer = stdoutWriter) {
|
|
77377
|
-
const out = createOutput({ json: opts.json }, writer);
|
|
77378
|
-
let result2;
|
|
77379
|
-
try {
|
|
77380
|
-
result2 = await apiGetOrThrow(
|
|
77381
|
-
"repository/findings"
|
|
77382
|
-
);
|
|
77383
|
-
} catch (err2) {
|
|
77384
|
-
reportApiFailure(out, writer, err2);
|
|
77385
|
-
return;
|
|
77386
|
-
}
|
|
77387
|
-
if (out.isJson) {
|
|
77388
|
-
out.data(result2);
|
|
77389
|
-
return;
|
|
77390
|
-
}
|
|
77391
|
-
const repositories = result2.repositories.filter((r) => r.findings.length > 0);
|
|
77392
|
-
if (repositories.length === 0) {
|
|
77393
|
-
writer.write(
|
|
77394
|
-
"No findings. The Oxagen check found no statement in a linked repository's instruction files that repeats or contradicts a steering record."
|
|
77395
|
-
);
|
|
77396
|
-
return;
|
|
77397
|
-
}
|
|
77398
|
-
let total2 = 0;
|
|
77399
|
-
for (const [index, repository] of repositories.entries()) {
|
|
77400
|
-
if (index > 0) writer.write("");
|
|
77401
|
-
writer.write(`${repository.full_name} (${repository.provider})`);
|
|
77402
|
-
printTable(
|
|
77403
|
-
["FINDING", "KIND", "FILE", "RECORD", "PULL REQUEST", "PROPOSAL"],
|
|
77404
|
-
repository.findings.map(findingRow),
|
|
77405
|
-
writer
|
|
77406
|
-
);
|
|
77407
|
-
total2 += repository.findings.length;
|
|
77408
|
-
}
|
|
77409
|
-
writer.write("");
|
|
77410
|
-
writer.write(
|
|
77411
|
-
`${plural(total2, "finding", "findings")} in ${plural(repositories.length, "repository", "repositories")}.`
|
|
77412
|
-
);
|
|
77413
|
-
const promotable = repositories.some(
|
|
77414
|
-
(r) => r.findings.some((f) => f.kind === "contradiction" && f.proposal === null)
|
|
77415
|
-
);
|
|
77416
|
-
if (promotable) {
|
|
77417
|
-
writer.write(
|
|
77418
|
-
"Promote a contradiction to a proposal with `oxagen steering promote <finding-id>`."
|
|
77419
|
-
);
|
|
77420
|
-
}
|
|
77421
|
-
}
|
|
77422
|
-
var STEERING_FINDINGS_CAPABILITIES, PROPOSAL_STATUS_WORDS;
|
|
77423
|
-
var init_steering_findings = __esm({
|
|
77424
|
-
"src/commands/steering-findings.ts"() {
|
|
77425
|
-
init_api();
|
|
77426
|
-
init_capture_writer();
|
|
77427
|
-
init_output();
|
|
77428
|
-
STEERING_FINDINGS_CAPABILITIES = [
|
|
77429
|
-
"list_code_repository_findings"
|
|
77430
|
-
];
|
|
77431
|
-
PROPOSAL_STATUS_WORDS = {
|
|
77432
|
-
proposed: "waiting for its steering PR",
|
|
77433
|
-
pr_open: "steering PR open",
|
|
77434
|
-
checks_running: "checks running",
|
|
77435
|
-
checks_passed: "checks passed",
|
|
77436
|
-
checks_failed: "checks failed",
|
|
77437
|
-
merged: "merged",
|
|
77438
|
-
rejected: "rejected"
|
|
77439
|
-
};
|
|
77440
|
-
}
|
|
77441
|
-
});
|
|
77442
|
-
|
|
77443
77566
|
// src/commands/steering-promote.ts
|
|
77444
77567
|
var steering_promote_exports = {};
|
|
77445
77568
|
__export(steering_promote_exports, {
|
|
@@ -77452,7 +77575,7 @@ async function steeringPromote(findingId, opts = {}, writer = stdoutWriter) {
|
|
|
77452
77575
|
usageError(
|
|
77453
77576
|
writer,
|
|
77454
77577
|
`expected a finding id that starts with crf_, got ${JSON.stringify(findingId)}. Run \`oxagen steering findings\` to list them.`,
|
|
77455
|
-
|
|
77578
|
+
USAGE2
|
|
77456
77579
|
);
|
|
77457
77580
|
return;
|
|
77458
77581
|
}
|
|
@@ -77464,7 +77587,7 @@ async function steeringPromote(findingId, opts = {}, writer = stdoutWriter) {
|
|
|
77464
77587
|
{ finding_id: id2 }
|
|
77465
77588
|
);
|
|
77466
77589
|
} catch (err2) {
|
|
77467
|
-
reportApiFailure(out, writer, err2,
|
|
77590
|
+
reportApiFailure(out, writer, err2, NEXT_STEPS2);
|
|
77468
77591
|
return;
|
|
77469
77592
|
}
|
|
77470
77593
|
if (out.isJson) {
|
|
@@ -77481,7 +77604,7 @@ async function steeringPromote(findingId, opts = {}, writer = stdoutWriter) {
|
|
|
77481
77604
|
writer.write(`Status: ${PROPOSAL_STATUS_WORDS[result2.status]}`);
|
|
77482
77605
|
writer.write("Nothing steers until a person merges the steering PR.");
|
|
77483
77606
|
}
|
|
77484
|
-
var STEERING_PROMOTE_CAPABILITIES, FINDING_ID,
|
|
77607
|
+
var STEERING_PROMOTE_CAPABILITIES, FINDING_ID, USAGE2, NEXT_STEPS2;
|
|
77485
77608
|
var init_steering_promote = __esm({
|
|
77486
77609
|
"src/commands/steering-promote.ts"() {
|
|
77487
77610
|
init_api();
|
|
@@ -77492,8 +77615,8 @@ var init_steering_promote = __esm({
|
|
|
77492
77615
|
"promote_instruction_to_steering"
|
|
77493
77616
|
];
|
|
77494
77617
|
FINDING_ID = /^crf_[0-9A-Za-z]+$/;
|
|
77495
|
-
|
|
77496
|
-
|
|
77618
|
+
USAGE2 = "oxagen steering promote <finding-id> [--json]";
|
|
77619
|
+
NEXT_STEPS2 = {
|
|
77497
77620
|
finding_resolved: "Run `oxagen steering findings` to see the statements that still match a record.",
|
|
77498
77621
|
already_proposed: "Run `oxagen steering findings` to see the open proposal and its steering PR.",
|
|
77499
77622
|
lineage_pr_open: "Merge or close the PR that is open on the record, then promote the finding again."
|
|
@@ -77519,7 +77642,7 @@ async function steeringRestoreBlock(proposalId, path2, opts = {}, writer = stdou
|
|
|
77519
77642
|
usageError(
|
|
77520
77643
|
writer,
|
|
77521
77644
|
`expected a proposal id that starts with prp_, got ${JSON.stringify(proposalId)}`,
|
|
77522
|
-
|
|
77645
|
+
USAGE3
|
|
77523
77646
|
);
|
|
77524
77647
|
return;
|
|
77525
77648
|
}
|
|
@@ -77528,7 +77651,7 @@ async function steeringRestoreBlock(proposalId, path2, opts = {}, writer = stdou
|
|
|
77528
77651
|
usageError(
|
|
77529
77652
|
writer,
|
|
77530
77653
|
`expected AGENTS.md, CLAUDE.md, or README.md, got ${JSON.stringify(path2)}`,
|
|
77531
|
-
|
|
77654
|
+
USAGE3
|
|
77532
77655
|
);
|
|
77533
77656
|
return;
|
|
77534
77657
|
}
|
|
@@ -77553,7 +77676,7 @@ async function steeringRestoreBlock(proposalId, path2, opts = {}, writer = stdou
|
|
|
77553
77676
|
writer.write(`Commit: ${result2.commit_sha}`);
|
|
77554
77677
|
writer.write(`Status: ${PROPOSAL_STATUS_WORDS[result2.status]}`);
|
|
77555
77678
|
}
|
|
77556
|
-
var STEERING_RESTORE_BLOCK_CAPABILITIES, MANAGED_BLOCK_FILES, PROPOSAL_ID2,
|
|
77679
|
+
var STEERING_RESTORE_BLOCK_CAPABILITIES, MANAGED_BLOCK_FILES, PROPOSAL_ID2, USAGE3;
|
|
77557
77680
|
var init_steering_restore_block = __esm({
|
|
77558
77681
|
"src/commands/steering-restore-block.ts"() {
|
|
77559
77682
|
init_api();
|
|
@@ -77569,7 +77692,7 @@ var init_steering_restore_block = __esm({
|
|
|
77569
77692
|
"README.md": true
|
|
77570
77693
|
};
|
|
77571
77694
|
PROPOSAL_ID2 = /^prp_[0-9A-Za-z]+$/;
|
|
77572
|
-
|
|
77695
|
+
USAGE3 = "oxagen steering restore-block <proposal-id> <AGENTS.md|CLAUDE.md|README.md> [--json]";
|
|
77573
77696
|
}
|
|
77574
77697
|
});
|
|
77575
77698
|
|
|
@@ -79024,7 +79147,7 @@ function formatFrame(frame) {
|
|
|
79024
79147
|
return parts.join(" ");
|
|
79025
79148
|
}
|
|
79026
79149
|
function formatCounts(counts) {
|
|
79027
|
-
return counts.map((c) => `${c.kind} ${c.count} (in ${
|
|
79150
|
+
return counts.map((c) => `${c.kind} ${c.count} (in ${plural3(c.frames, "frame")})`).join(", ");
|
|
79028
79151
|
}
|
|
79029
79152
|
function formatVerification(result2) {
|
|
79030
79153
|
const lines = [];
|
|
@@ -79037,7 +79160,7 @@ function formatVerification(result2) {
|
|
|
79037
79160
|
).length;
|
|
79038
79161
|
if (notCarried > 0) {
|
|
79039
79162
|
lines.push(
|
|
79040
|
-
` Digest not carried on ${
|
|
79163
|
+
` Digest not carried on ${plural3(notCarried, "wrapped (tse_) frame")}. A wrapped frame is hashed over its full event, and the bundle does not hold that event for these frames: an export before format 3 never did, and a format-3 export leaves it out when the stored row cannot be proven to rebuild it. For these frames, only the links and the Merkle root can be checked.`
|
|
79041
79164
|
);
|
|
79042
79165
|
}
|
|
79043
79166
|
lines.push("");
|
|
@@ -79066,7 +79189,7 @@ function formatVerification(result2) {
|
|
|
79066
79189
|
(c) => c.status === "broken"
|
|
79067
79190
|
).length;
|
|
79068
79191
|
lines.push(
|
|
79069
|
-
result2.ok ? `HELD ${runId}: ${
|
|
79192
|
+
result2.ok ? `HELD ${runId}: ${plural3(result2.frames.length, "frame")}` : `BROKEN ${runId}: ${brokenFrames} of ${plural3(result2.frames.length, "frame")} broken, ${plural3(brokenChecks, "check")} broken`
|
|
79070
79193
|
);
|
|
79071
79194
|
return lines;
|
|
79072
79195
|
}
|
|
@@ -79084,7 +79207,7 @@ async function verifyBundle3(bundle2, opts = {}, writer = stdoutWriter) {
|
|
|
79084
79207
|
if (!result2.ok && (process.exitCode === void 0 || process.exitCode === 0))
|
|
79085
79208
|
process.exitCode = 1;
|
|
79086
79209
|
}
|
|
79087
|
-
var REQUIRED, OPTIONAL, BundleReadError,
|
|
79210
|
+
var REQUIRED, OPTIONAL, BundleReadError, plural3;
|
|
79088
79211
|
var init_verify2 = __esm({
|
|
79089
79212
|
"src/commands/verify.ts"() {
|
|
79090
79213
|
init_esm2();
|
|
@@ -79099,7 +79222,7 @@ var init_verify2 = __esm({
|
|
|
79099
79222
|
OPTIONAL = "redactions.json";
|
|
79100
79223
|
BundleReadError = class extends Error {
|
|
79101
79224
|
};
|
|
79102
|
-
|
|
79225
|
+
plural3 = (n4, word) => `${n4} ${word}${n4 === 1 ? "" : "s"}`;
|
|
79103
79226
|
}
|
|
79104
79227
|
});
|
|
79105
79228
|
|
|
@@ -79320,7 +79443,7 @@ function ago(iso, now = /* @__PURE__ */ new Date()) {
|
|
|
79320
79443
|
if (hours < 48) return `${hours}h ago`;
|
|
79321
79444
|
return `${Math.round(hours / 24)}d ago`;
|
|
79322
79445
|
}
|
|
79323
|
-
function
|
|
79446
|
+
function plural4(count12, one, many) {
|
|
79324
79447
|
return `${count12} ${count12 === 1 ? one : many}`;
|
|
79325
79448
|
}
|
|
79326
79449
|
function table(headers, rows) {
|
|
@@ -79334,7 +79457,7 @@ function table(headers, rows) {
|
|
|
79334
79457
|
}
|
|
79335
79458
|
function formatWorkspaceMemories(result2, now = /* @__PURE__ */ new Date()) {
|
|
79336
79459
|
if (result2.groups.length === 0) {
|
|
79337
|
-
return result2.total_groups === 0 ? "No memories yet. Oxagen collects them from enrolled hosts every five minutes." : `No memories on this page. The list holds ${
|
|
79460
|
+
return result2.total_groups === 0 ? "No memories yet. Oxagen collects them from enrolled hosts every five minutes." : `No memories on this page. The list holds ${plural4(result2.total_groups, "group", "groups")}.`;
|
|
79338
79461
|
}
|
|
79339
79462
|
const rows = result2.groups.map((group) => {
|
|
79340
79463
|
const { memory } = group;
|
|
@@ -79359,14 +79482,14 @@ function formatWorkspaceMemories(result2, now = /* @__PURE__ */ new Date()) {
|
|
|
79359
79482
|
const shown2 = result2.groups.length;
|
|
79360
79483
|
lines.push(
|
|
79361
79484
|
"",
|
|
79362
|
-
shown2 < result2.total_groups ? `Showing ${shown2} of ${
|
|
79485
|
+
shown2 < result2.total_groups ? `Showing ${shown2} of ${plural4(result2.total_groups, "group", "groups")}. Use --limit and --offset to page.` : `${plural4(result2.total_groups, "group", "groups")}.`
|
|
79363
79486
|
);
|
|
79364
79487
|
if (result2.truncated)
|
|
79365
79488
|
lines.push(
|
|
79366
79489
|
`More than ${result2.total_memories} memories matched, and the list groups the top ${result2.total_memories}. Narrow the filters to see the rest.`
|
|
79367
79490
|
);
|
|
79368
79491
|
lines.push(
|
|
79369
|
-
`${
|
|
79492
|
+
`${plural4(result2.waiting, "memory waits", "memories wait")} in this workspace.`
|
|
79370
79493
|
);
|
|
79371
79494
|
return lines.join("\n");
|
|
79372
79495
|
}
|
|
@@ -79450,7 +79573,7 @@ function formatDismissResult(result2, restore) {
|
|
|
79450
79573
|
const lines = [];
|
|
79451
79574
|
if (result2.changed.length > 0)
|
|
79452
79575
|
lines.push(
|
|
79453
|
-
`${restore ? "Restored" : "Dismissed"} ${
|
|
79576
|
+
`${restore ? "Restored" : "Dismissed"} ${plural4(result2.changed.length, "memory", "memories")}: ${result2.changed.join(", ")}.`
|
|
79454
79577
|
);
|
|
79455
79578
|
else lines.push(`No memory was ${restore ? "restored" : "dismissed"}.`);
|
|
79456
79579
|
if (!restore && result2.rejections > 0)
|
|
@@ -101965,11 +102088,11 @@ function errorText4(error) {
|
|
|
101965
102088
|
function asSentence(text5) {
|
|
101966
102089
|
return /[.!?…]$/.test(text5) ? text5 : `${text5}.`;
|
|
101967
102090
|
}
|
|
101968
|
-
function
|
|
102091
|
+
function plural5(count12, one, many) {
|
|
101969
102092
|
return `${count12} ${count12 === 1 ? one : many}`;
|
|
101970
102093
|
}
|
|
101971
102094
|
function pagingNote(paged, options) {
|
|
101972
|
-
const read2 = `${
|
|
102095
|
+
const read2 = `${plural5(paged.items, "item", "items")} from ${plural5(paged.pages, "page", "pages")}`;
|
|
101973
102096
|
switch (paged.stop) {
|
|
101974
102097
|
case "last_page":
|
|
101975
102098
|
return void 0;
|
|
@@ -121430,12 +121553,12 @@ function checkString(schema, value, path2) {
|
|
|
121430
121553
|
const length = [...value].length;
|
|
121431
121554
|
if (typeof schema.minLength === "number" && length < schema.minLength) {
|
|
121432
121555
|
issues.push(
|
|
121433
|
-
`${path2} must be at least ${schema.minLength} ${
|
|
121556
|
+
`${path2} must be at least ${schema.minLength} ${plural6(schema.minLength, "character")} long.`
|
|
121434
121557
|
);
|
|
121435
121558
|
}
|
|
121436
121559
|
if (typeof schema.maxLength === "number" && length > schema.maxLength) {
|
|
121437
121560
|
issues.push(
|
|
121438
|
-
`${path2} must be at most ${schema.maxLength} ${
|
|
121561
|
+
`${path2} must be at most ${schema.maxLength} ${plural6(schema.maxLength, "character")} long.`
|
|
121439
121562
|
);
|
|
121440
121563
|
}
|
|
121441
121564
|
if (typeof schema.pattern === "string" && testPattern(schema.pattern, value) === false) {
|
|
@@ -121524,7 +121647,7 @@ function listOf(values) {
|
|
|
121524
121647
|
const more = values.length - shown2.length;
|
|
121525
121648
|
return more > 0 ? `${shown2.join(", ")}, and ${more} more` : shown2.join(", ");
|
|
121526
121649
|
}
|
|
121527
|
-
function
|
|
121650
|
+
function plural6(count12, one, many = `${one}s`) {
|
|
121528
121651
|
return count12 === 1 ? one : many;
|
|
121529
121652
|
}
|
|
121530
121653
|
var MAX_DEPTH2, MAX_STEPS, MAX_ISSUES, TYPE_NAMES, Checker;
|
|
@@ -121588,12 +121711,12 @@ var init_validate = __esm({
|
|
|
121588
121711
|
const issues = [];
|
|
121589
121712
|
if (typeof schema.minItems === "number" && value.length < schema.minItems) {
|
|
121590
121713
|
issues.push(
|
|
121591
|
-
`${path2} must have at least ${schema.minItems} ${
|
|
121714
|
+
`${path2} must have at least ${schema.minItems} ${plural6(schema.minItems, "item")}.`
|
|
121592
121715
|
);
|
|
121593
121716
|
}
|
|
121594
121717
|
if (typeof schema.maxItems === "number" && value.length > schema.maxItems) {
|
|
121595
121718
|
issues.push(
|
|
121596
|
-
`${path2} must have at most ${schema.maxItems} ${
|
|
121719
|
+
`${path2} must have at most ${schema.maxItems} ${plural6(schema.maxItems, "item")}.`
|
|
121597
121720
|
);
|
|
121598
121721
|
}
|
|
121599
121722
|
if (schema.uniqueItems === true) {
|
|
@@ -121640,12 +121763,12 @@ var init_validate = __esm({
|
|
|
121640
121763
|
}
|
|
121641
121764
|
if (typeof schema.minProperties === "number" && present.length < schema.minProperties) {
|
|
121642
121765
|
issues.push(
|
|
121643
|
-
`${path2} must have at least ${schema.minProperties} ${
|
|
121766
|
+
`${path2} must have at least ${schema.minProperties} ${plural6(schema.minProperties, "property", "properties")}.`
|
|
121644
121767
|
);
|
|
121645
121768
|
}
|
|
121646
121769
|
if (typeof schema.maxProperties === "number" && present.length > schema.maxProperties) {
|
|
121647
121770
|
issues.push(
|
|
121648
|
-
`${path2} must have at most ${schema.maxProperties} ${
|
|
121771
|
+
`${path2} must have at most ${schema.maxProperties} ${plural6(schema.maxProperties, "property", "properties")}.`
|
|
121649
121772
|
);
|
|
121650
121773
|
}
|
|
121651
121774
|
const properties = isRecord10(schema.properties) ? schema.properties : {};
|
|
@@ -130773,6 +130896,14 @@ function buildProgram() {
|
|
|
130773
130896
|
const { repoLink: repoLink2 } = await Promise.resolve().then(() => (init_repo(), repo_exports));
|
|
130774
130897
|
await repoLink2(ref2, opts);
|
|
130775
130898
|
});
|
|
130899
|
+
repoCmd.command("scan").description(
|
|
130900
|
+
"List the agent harness files on a repository's default branch: instruction and rule files, skills, commands, subagent files, settings files and MCP configs. The repository need not be linked."
|
|
130901
|
+
).argument("<owner/name>", "The repository, or the GitLab project path").option("--gitlab", "Scan a GitLab project the workspace has connected").option("--json", "Output JSON").action(
|
|
130902
|
+
async (ref2, opts) => {
|
|
130903
|
+
const { repoScan: repoScan2 } = await Promise.resolve().then(() => (init_repo_scan(), repo_scan_exports));
|
|
130904
|
+
await repoScan2(ref2, opts);
|
|
130905
|
+
}
|
|
130906
|
+
);
|
|
130776
130907
|
repoCmd.command("unlink").description(
|
|
130777
130908
|
"Unlink a linked repository by its binding id. A repository workspace.toml lists is removed by a steering PR. The steering repository is refused."
|
|
130778
130909
|
).argument("<bindingId>", "The rpb_\u2026 binding id `oxagen repo list` shows").option("--json", "Output JSON").action(async (bindingId, opts) => {
|
package/package.json
CHANGED