@basou/cli 0.62.0 → 0.63.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +52 -9
- package/dist/index.js.map +1 -1
- package/dist/program.js +52 -9
- package/dist/program.js.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -136,11 +136,13 @@ import {
|
|
|
136
136
|
acquireLock,
|
|
137
137
|
appendChainedEventLocked,
|
|
138
138
|
assertBasouRootSafe,
|
|
139
|
+
assertLockStoreSafe,
|
|
139
140
|
assertSessionDirSafe,
|
|
140
141
|
basouPaths,
|
|
141
142
|
EVENT_SCHEMA_VERSION,
|
|
142
143
|
enumerateApprovals,
|
|
143
144
|
findErrorCode,
|
|
145
|
+
inspectApprovalEntry,
|
|
144
146
|
inspectSessionEntry,
|
|
145
147
|
isLazyExpired,
|
|
146
148
|
LOCAL_CLI_EVENT_SOURCE,
|
|
@@ -192,6 +194,11 @@ async function doRunApprovalList(options, ctx) {
|
|
|
192
194
|
const paths = basouPaths(repositoryRoot);
|
|
193
195
|
await assertWorkspaceInitialized(paths.root);
|
|
194
196
|
const ids = await enumerateApprovals(paths);
|
|
197
|
+
for (const entry of ids.unfollowed) {
|
|
198
|
+
console.error(
|
|
199
|
+
`Skipped ${entry.id} in ${entry.location}: not a file (a symlink or a directory is not followed)`
|
|
200
|
+
);
|
|
201
|
+
}
|
|
195
202
|
const now = /* @__PURE__ */ new Date();
|
|
196
203
|
const records = [];
|
|
197
204
|
const resolvedSet = new Set(ids.resolved);
|
|
@@ -259,7 +266,8 @@ async function doRunApprovalShow(idInput, options, ctx) {
|
|
|
259
266
|
const repositoryRoot = await resolveRepositoryRootForApproval(cwd, "show");
|
|
260
267
|
const paths = basouPaths(repositoryRoot);
|
|
261
268
|
await assertWorkspaceInitialized(paths.root);
|
|
262
|
-
const { id } = await resolveApprovalId(paths, idInput);
|
|
269
|
+
const { id, unfollowed } = await resolveApprovalId(paths, idInput);
|
|
270
|
+
for (const entry2 of unfollowed) console.error(`Warning: ${describeUnfollowed(entry2)}`);
|
|
263
271
|
const loaded = await loadApproval(paths, id);
|
|
264
272
|
if (loaded === null) {
|
|
265
273
|
throw new Error(`Approval not found: ${idInput}`);
|
|
@@ -328,6 +336,15 @@ async function doRunApprovalResolve(idInput, options, ctx, decision) {
|
|
|
328
336
|
if (location === "resolved") {
|
|
329
337
|
throw new Error(`Approval already resolved: ${idInput}`);
|
|
330
338
|
}
|
|
339
|
+
const resolvedEntry = await inspectApprovalEntry(paths, "resolved", id);
|
|
340
|
+
if (resolvedEntry === "file") {
|
|
341
|
+
throw new Error(`Approval already resolved: ${idInput}`);
|
|
342
|
+
}
|
|
343
|
+
if (resolvedEntry !== "missing") {
|
|
344
|
+
throw new Error(
|
|
345
|
+
`Approval ${id} cannot be resolved: its entry in resolved is not a file (a symlink or a directory is not followed)`
|
|
346
|
+
);
|
|
347
|
+
}
|
|
331
348
|
const pendingPath = join(paths.approvals.pending, `${id}.yaml`);
|
|
332
349
|
let pendingRaw;
|
|
333
350
|
try {
|
|
@@ -354,6 +371,7 @@ async function doRunApprovalResolve(idInput, options, ctx, decision) {
|
|
|
354
371
|
const now = /* @__PURE__ */ new Date();
|
|
355
372
|
const occurredAt = now.toISOString();
|
|
356
373
|
const eventId = prefixedUlid("evt");
|
|
374
|
+
await assertLockStoreSafe(paths);
|
|
357
375
|
try {
|
|
358
376
|
await mkdir(paths.approvals.resolved, { recursive: true });
|
|
359
377
|
} catch (error) {
|
|
@@ -469,20 +487,31 @@ async function resolveApprovalId(paths, input) {
|
|
|
469
487
|
}
|
|
470
488
|
byId.set(id2, "resolved");
|
|
471
489
|
}
|
|
472
|
-
|
|
490
|
+
const matched = new Set(byId.keys());
|
|
491
|
+
for (const entry of enumeration.unfollowed) {
|
|
492
|
+
if (entry.id.startsWith(normalized)) matched.add(entry.id);
|
|
493
|
+
}
|
|
494
|
+
if (matched.size === 0) {
|
|
473
495
|
throw new Error(`Approval not found: ${input}`);
|
|
474
496
|
}
|
|
475
|
-
if (
|
|
497
|
+
if (matched.size > 1) {
|
|
476
498
|
throw new Error(
|
|
477
|
-
`Ambiguous approval id '${input}': matched ${
|
|
499
|
+
`Ambiguous approval id '${input}': matched ${matched.size} approvals. Disambiguate with a longer prefix.`
|
|
478
500
|
);
|
|
479
501
|
}
|
|
480
|
-
const
|
|
481
|
-
if (
|
|
502
|
+
const id = matched.values().next().value;
|
|
503
|
+
if (id === void 0) {
|
|
482
504
|
throw new Error(`Approval not found: ${input}`);
|
|
483
505
|
}
|
|
484
|
-
const
|
|
485
|
-
|
|
506
|
+
const location = byId.get(id);
|
|
507
|
+
if (location === void 0) {
|
|
508
|
+
throw new Error(`Approval ${id} is not a file; a symlink or a directory there is not followed`);
|
|
509
|
+
}
|
|
510
|
+
const unfollowed = enumeration.unfollowed.filter((entry) => entry.id === id);
|
|
511
|
+
return { id, location, unfollowed };
|
|
512
|
+
}
|
|
513
|
+
function describeUnfollowed(entry) {
|
|
514
|
+
return `${entry.id} in ${entry.location} is not a file (a symlink or a directory is not followed)`;
|
|
486
515
|
}
|
|
487
516
|
function isApprovalEvent(ev) {
|
|
488
517
|
return ev.type === "approval_requested" || ev.type === "approval_approved" || ev.type === "approval_rejected" || ev.type === "approval_expired";
|
|
@@ -2082,6 +2111,7 @@ import { join as join6 } from "path";
|
|
|
2082
2111
|
import {
|
|
2083
2112
|
acquireLock as acquireLock3,
|
|
2084
2113
|
assertBasouRootSafe as assertBasouRootSafe4,
|
|
2114
|
+
assertLockStoreSafe as assertLockStoreSafe2,
|
|
2085
2115
|
assertSessionStoreSafe,
|
|
2086
2116
|
basouPaths as basouPaths6,
|
|
2087
2117
|
ChildProcessRunner,
|
|
@@ -2122,6 +2152,7 @@ async function runExec(command, args, options, ctx = {}) {
|
|
|
2122
2152
|
await assertBasouRootSafe4(paths.root);
|
|
2123
2153
|
const manifest = await readManifest3(paths);
|
|
2124
2154
|
await assertSessionStoreSafe(paths);
|
|
2155
|
+
await assertLockStoreSafe2(paths);
|
|
2125
2156
|
const sessionId = prefixedUlid3("ses");
|
|
2126
2157
|
const sessionDir = join6(paths.sessions, sessionId);
|
|
2127
2158
|
await mkdir2(sessionDir, { recursive: true });
|
|
@@ -2920,6 +2951,7 @@ async function loadHostsConfig(configPath = DEFAULT_HOSTS_CONFIG_PATH) {
|
|
|
2920
2951
|
// src/lib/provenance-actions.ts
|
|
2921
2952
|
import {
|
|
2922
2953
|
assertApprovalStoreSafe,
|
|
2954
|
+
assertLockStoreSafe as assertLockStoreSafe4,
|
|
2923
2955
|
assertTaskStoreSafe,
|
|
2924
2956
|
readMarkdownFile as readMarkdownFile5,
|
|
2925
2957
|
renderDecisions as renderDecisions2,
|
|
@@ -2938,6 +2970,7 @@ import { createInterface } from "readline";
|
|
|
2938
2970
|
import {
|
|
2939
2971
|
AGENT_INFRA_DIRS as AGENT_INFRA_DIRS2,
|
|
2940
2972
|
assertBasouRootSafe as assertBasouRootSafe6,
|
|
2973
|
+
assertLockStoreSafe as assertLockStoreSafe3,
|
|
2941
2974
|
assertSessionStoreSafe as assertSessionStoreSafe2,
|
|
2942
2975
|
basouPaths as basouPaths8,
|
|
2943
2976
|
CLAUDE_IMPORT_SOURCE,
|
|
@@ -3111,6 +3144,7 @@ async function resolveImportTarget(ctx) {
|
|
|
3111
3144
|
}
|
|
3112
3145
|
async function importDerivedSessions(paths, manifest, options, sourceKind, candidates, projectPaths, boundaryDeclared) {
|
|
3113
3146
|
await assertSessionStoreSafe2(paths);
|
|
3147
|
+
if (options.dryRun !== true) await assertLockStoreSafe3(paths);
|
|
3114
3148
|
const { byExternalId: existingByExternalId, notDirectories } = await loadExistingByExternalId(
|
|
3115
3149
|
paths,
|
|
3116
3150
|
sourceKind
|
|
@@ -3692,6 +3726,7 @@ async function refreshAll(args) {
|
|
|
3692
3726
|
if (!dryRun) {
|
|
3693
3727
|
await assertTaskStoreSafe(paths);
|
|
3694
3728
|
await assertApprovalStoreSafe(paths);
|
|
3729
|
+
await assertLockStoreSafe4(paths);
|
|
3695
3730
|
}
|
|
3696
3731
|
const claudeCode = await importClaudeCode(options, ctx);
|
|
3697
3732
|
const codex = await importCodex(options, ctx);
|
|
@@ -8714,6 +8749,7 @@ import { homedir as homedir10 } from "os";
|
|
|
8714
8749
|
import { join as join13 } from "path";
|
|
8715
8750
|
import {
|
|
8716
8751
|
assertApprovalStoreSafe as assertApprovalStoreSafe2,
|
|
8752
|
+
assertLockStoreSafe as assertLockStoreSafe5,
|
|
8717
8753
|
assertTaskStoreSafe as assertTaskStoreSafe2,
|
|
8718
8754
|
findErrorCode as findErrorCode8
|
|
8719
8755
|
} from "@basou/core";
|
|
@@ -8778,6 +8814,7 @@ function hms(date) {
|
|
|
8778
8814
|
async function runImports(deps) {
|
|
8779
8815
|
await assertTaskStoreSafe2(deps.paths);
|
|
8780
8816
|
await assertApprovalStoreSafe2(deps.paths);
|
|
8817
|
+
await assertLockStoreSafe5(deps.paths);
|
|
8781
8818
|
const claude = await importClaudeCode(deps.importOptions, deps.ctx);
|
|
8782
8819
|
const codex = await importCodex(deps.importOptions, deps.ctx);
|
|
8783
8820
|
return { claude, codex, changed: changedCount(claude) + changedCount(codex) };
|
|
@@ -9605,6 +9642,7 @@ import { join as join14 } from "path";
|
|
|
9605
9642
|
import {
|
|
9606
9643
|
acquireLock as acquireLock5,
|
|
9607
9644
|
assertBasouRootSafe as assertBasouRootSafe12,
|
|
9645
|
+
assertLockStoreSafe as assertLockStoreSafe6,
|
|
9608
9646
|
assertSessionStoreSafe as assertSessionStoreSafe3,
|
|
9609
9647
|
basouPaths as basouPaths17,
|
|
9610
9648
|
ChildProcessRunner as ChildProcessRunner2,
|
|
@@ -9682,6 +9720,7 @@ async function runTrackedTool(args, options, ctx, adapter) {
|
|
|
9682
9720
|
await assertBasouRootSafe12(paths.root);
|
|
9683
9721
|
const manifest = await readManifest10(paths);
|
|
9684
9722
|
await assertSessionStoreSafe3(paths);
|
|
9723
|
+
await assertLockStoreSafe6(paths);
|
|
9685
9724
|
const sessionId = prefixedUlid4("ses");
|
|
9686
9725
|
const sessionDir = join14(paths.sessions, sessionId);
|
|
9687
9726
|
await mkdir3(sessionDir, { recursive: true });
|
|
@@ -10068,6 +10107,7 @@ import {
|
|
|
10068
10107
|
acquireLock as acquireLock6,
|
|
10069
10108
|
appendEventToExistingSession as appendEventToExistingSession3,
|
|
10070
10109
|
assertBasouRootSafe as assertBasouRootSafe13,
|
|
10110
|
+
assertLockStoreSafe as assertLockStoreSafe7,
|
|
10071
10111
|
basouPaths as basouPaths18,
|
|
10072
10112
|
displayPath as displayPath3,
|
|
10073
10113
|
EVENT_SCHEMA_VERSION as EVENT_SCHEMA_VERSION6,
|
|
@@ -10703,6 +10743,7 @@ async function doRunSessionRechain(options, ctx) {
|
|
|
10703
10743
|
const repositoryRoot = await resolveRepositoryRootForSession(cwd, "rechain");
|
|
10704
10744
|
const paths = basouPaths18(repositoryRoot);
|
|
10705
10745
|
await assertWorkspaceInitialized11(paths.root);
|
|
10746
|
+
await assertLockStoreSafe7(paths);
|
|
10706
10747
|
const sessionIds = options.session !== void 0 ? [await resolveSessionId3(paths, options.session)] : await enumerateAllSessionNames(paths);
|
|
10707
10748
|
const dryRun = options.dryRun === true;
|
|
10708
10749
|
const rows = [];
|
|
@@ -10991,6 +11032,7 @@ import { join as join16 } from "path";
|
|
|
10991
11032
|
import {
|
|
10992
11033
|
archiveTask,
|
|
10993
11034
|
assertBasouRootSafe as assertBasouRootSafe16,
|
|
11035
|
+
assertLockStoreSafe as assertLockStoreSafe8,
|
|
10994
11036
|
basouPaths as basouPaths21,
|
|
10995
11037
|
createTaskWithEvent,
|
|
10996
11038
|
deleteTask,
|
|
@@ -11528,6 +11570,7 @@ async function doRunTaskReconcile(options, ctx) {
|
|
|
11528
11570
|
const repositoryRoot = await resolveRepositoryRootForTask(cwd, "reconcile");
|
|
11529
11571
|
const paths = basouPaths21(repositoryRoot);
|
|
11530
11572
|
await assertWorkspaceInitialized13(paths.root);
|
|
11573
|
+
await assertLockStoreSafe8(paths);
|
|
11531
11574
|
const manifest = await readManifest13(paths);
|
|
11532
11575
|
const nowProvider = ctx.nowProvider ?? (() => /* @__PURE__ */ new Date());
|
|
11533
11576
|
const write = options.write === true;
|
|
@@ -14199,7 +14242,7 @@ async function assertWorkspaceInitialized15(basouRoot) {
|
|
|
14199
14242
|
function readBuildStamp() {
|
|
14200
14243
|
if (false) return void 0;
|
|
14201
14244
|
try {
|
|
14202
|
-
return JSON.parse('{"version":"0.
|
|
14245
|
+
return JSON.parse('{"version":"0.63.0","commit":"5a404e5","committedAt":"2026-10-03T10:49:51+09:00"}');
|
|
14203
14246
|
} catch {
|
|
14204
14247
|
return void 0;
|
|
14205
14248
|
}
|