ushman-ledger 1.2.1 → 1.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (67) hide show
  1. package/AGENTS.md +7 -5
  2. package/ARCHITECTURE.md +85 -0
  3. package/CHANGELOG.md +11 -0
  4. package/README.md +114 -5
  5. package/TROUBLESHOOTING.md +184 -0
  6. package/dist/blobs.d.ts +3 -0
  7. package/dist/blobs.d.ts.map +1 -1
  8. package/dist/blobs.js +41 -15
  9. package/dist/builders.d.ts +33 -0
  10. package/dist/builders.d.ts.map +1 -1
  11. package/dist/builders.js +10 -1
  12. package/dist/cli.d.ts.map +1 -1
  13. package/dist/cli.js +176 -59
  14. package/dist/coverage.d.ts.map +1 -1
  15. package/dist/coverage.js +3 -2
  16. package/dist/doctor.d.ts +17 -4
  17. package/dist/doctor.d.ts.map +1 -1
  18. package/dist/doctor.js +263 -62
  19. package/dist/handle.d.ts.map +1 -1
  20. package/dist/handle.js +67 -30
  21. package/dist/helpers.d.ts +1 -0
  22. package/dist/helpers.d.ts.map +1 -1
  23. package/dist/helpers.js +23 -0
  24. package/dist/index.d.ts +4 -2
  25. package/dist/index.d.ts.map +1 -1
  26. package/dist/index.js +4 -2
  27. package/dist/list.d.ts +34 -1
  28. package/dist/list.d.ts.map +1 -1
  29. package/dist/list.js +19 -9
  30. package/dist/patch-resolver.d.ts.map +1 -1
  31. package/dist/patch-resolver.js +193 -53
  32. package/dist/process.d.ts +2 -0
  33. package/dist/process.d.ts.map +1 -0
  34. package/dist/process.js +16 -0
  35. package/dist/read-index.d.ts +7 -7
  36. package/dist/read-index.d.ts.map +1 -1
  37. package/dist/read-index.js +18 -13
  38. package/dist/record.js +2 -2
  39. package/dist/recovery.d.ts +8 -0
  40. package/dist/recovery.d.ts.map +1 -1
  41. package/dist/recovery.js +142 -30
  42. package/dist/render/retro.d.ts.map +1 -1
  43. package/dist/render/retro.js +4 -1
  44. package/dist/runtime-config.d.ts +14 -0
  45. package/dist/runtime-config.d.ts.map +1 -0
  46. package/dist/runtime-config.js +97 -0
  47. package/dist/schema/entry-core.d.ts +5 -2
  48. package/dist/schema/entry-core.d.ts.map +1 -1
  49. package/dist/schema/entry-core.js +3 -0
  50. package/dist/schema/entry-read.d.ts +57 -0
  51. package/dist/schema/entry-read.d.ts.map +1 -1
  52. package/dist/schema/entry-read.js +9 -1
  53. package/dist/schema/entry-write.d.ts +51 -0
  54. package/dist/schema/entry-write.d.ts.map +1 -1
  55. package/dist/schema/entry-write.js +9 -1
  56. package/dist/storage/filesystem.d.ts +15 -2
  57. package/dist/storage/filesystem.d.ts.map +1 -1
  58. package/dist/storage/filesystem.js +234 -37
  59. package/dist/storage/lock.d.ts.map +1 -1
  60. package/dist/storage/lock.js +38 -16
  61. package/dist/text-lines.d.ts +8 -0
  62. package/dist/text-lines.d.ts.map +1 -0
  63. package/dist/text-lines.js +20 -0
  64. package/dist/version.d.ts +1 -1
  65. package/dist/version.d.ts.map +1 -1
  66. package/dist/version.js +2 -1
  67. package/package.json +4 -2
package/dist/index.d.ts CHANGED
@@ -1,11 +1,13 @@
1
- export { type BuildRecordInput, buildChangeLogRecord, buildCorrectionRecord, buildOperatorDecisionRecord, buildStripDecisionRevertedRecord, buildValidatorResultRecord, } from './builders.ts';
1
+ export { type BuildRecordInput, buildChangeLogRecord, buildCorrectionRecord, buildOperatorDecisionRecord, buildStageWriteRecord, buildStripDecisionRevertedRecord, buildValidatorResultRecord, } from './builders.ts';
2
2
  export { runLedgerCli } from './cli.ts';
3
3
  export { type CoverageReport, computeCoverage } from './coverage.ts';
4
+ export { DOCTOR_FINDING_CODES, type DoctorFinding, type DoctorFindingCode, type DoctorFindingMetadataValue, type DoctorReport, runLedgerDoctor, } from './doctor.ts';
4
5
  export { type LedgerHandle, type LedgerRenderOptions, type LedgerRenderToOptions, openLedger, type RenderTarget, type RenderWriter, } from './handle.ts';
5
6
  export type { LedgerFilter } from './list.ts';
6
7
  export { appendCleanupWaveNote, appendDecompositionWaveNote, appendNote, appendOpenIssueNote, appendSemanticCleanupSummaryNote, appendVerifiedFlowNote, type NoteBody, } from './note.ts';
7
8
  export { deriveFilesChangedFromPatch } from './patch-resolver.ts';
8
- export { type AgentPatchDiff, AgentPatchDiffSchema, AgentPatchEntrySchema, AgentPatchRecordSchema, type ChangeLogEntry, ChangeLogEntrySchema, type ChangeLogFileChange, ChangeLogFileChangeSchema, type ChangeLogParityStatus, ChangeLogParityStatusSchema, type ChangeLogRecord, ChangeLogRecordSchema, type ChangeLogSmokeResult, ChangeLogSmokeResultSchema, type ChangeLogSubkind, ChangeLogSubkindSchema, CorrectionEntrySchema, CorrectionRecordSchema, EmitterSchema, type LedgerEntry, LedgerEntrySchema, type LedgerKind, type LedgerLinks, LedgerLinksSchema, type LedgerPhase, LedgerPhaseSchema, type LedgerRecord, LedgerRecordSchema, type NoteEntry, NoteEntrySchema, type OperatorDecisionAction, OperatorDecisionActionSchema, OperatorDecisionEntrySchema, type OperatorDecisionPayload, OperatorDecisionPayloadSchema, OperatorDecisionRecordSchema, OperatorPatchEntrySchema, OperatorPatchRecordSchema, parseLedgerEntry, parseLedgerRecord, RuntimeEventEntrySchema, StripDecisionRevertedEntrySchema, type StripDecisionRevertedPayload, StripDecisionRevertedPayloadSchema, StripDecisionRevertedRecordSchema, ToolInvocationEntrySchema, ToolInvocationRecordSchema, ValidatorResultEntrySchema, ValidatorResultRecordSchema, } from './schema/entry.ts';
9
+ export { getLedgerRuntimeConfig, type LedgerRuntimeConfig, validateLedgerRuntimeConfig } from './runtime-config.ts';
10
+ export { type AgentPatchDiff, AgentPatchDiffSchema, AgentPatchEntrySchema, AgentPatchRecordSchema, type ChangeLogEntry, ChangeLogEntrySchema, type ChangeLogFileChange, ChangeLogFileChangeSchema, type ChangeLogParityStatus, ChangeLogParityStatusSchema, type ChangeLogRecord, ChangeLogRecordSchema, type ChangeLogSmokeResult, ChangeLogSmokeResultSchema, type ChangeLogSubkind, ChangeLogSubkindSchema, CorrectionEntrySchema, CorrectionRecordSchema, EmitterSchema, type LedgerEntry, LedgerEntrySchema, type LedgerKind, type LedgerLinks, LedgerLinksSchema, type LedgerPhase, LedgerPhaseSchema, type LedgerRecord, LedgerRecordSchema, type NoteEntry, NoteEntrySchema, type OperatorDecisionAction, OperatorDecisionActionSchema, OperatorDecisionEntrySchema, type OperatorDecisionPayload, OperatorDecisionPayloadSchema, OperatorDecisionRecordSchema, OperatorPatchEntrySchema, OperatorPatchRecordSchema, parseLedgerEntry, parseLedgerRecord, RuntimeEventEntrySchema, STAGE_WRITE_STAGES, type StageWriteStage, StageWriteEntrySchema, StageWriteRecordSchema, StripDecisionRevertedEntrySchema, type StripDecisionRevertedPayload, StripDecisionRevertedPayloadSchema, StripDecisionRevertedRecordSchema, ToolInvocationEntrySchema, ToolInvocationRecordSchema, ValidatorResultEntrySchema, ValidatorResultRecordSchema, } from './schema/entry.ts';
9
11
  export { type NoteSubkind, NoteSubkindSchema } from './schema/note.ts';
10
12
  export { resolveLedgerPaths } from './storage/filesystem.ts';
11
13
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,KAAK,gBAAgB,EACrB,oBAAoB,EACpB,qBAAqB,EACrB,2BAA2B,EAC3B,gCAAgC,EAChC,0BAA0B,GAC7B,MAAM,eAAe,CAAC;AACvB,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AACxC,OAAO,EAAE,KAAK,cAAc,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AACrE,OAAO,EACH,KAAK,YAAY,EACjB,KAAK,mBAAmB,EACxB,KAAK,qBAAqB,EAC1B,UAAU,EACV,KAAK,YAAY,EACjB,KAAK,YAAY,GACpB,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC;AAC9C,OAAO,EACH,qBAAqB,EACrB,2BAA2B,EAC3B,UAAU,EACV,mBAAmB,EACnB,gCAAgC,EAChC,sBAAsB,EACtB,KAAK,QAAQ,GAChB,MAAM,WAAW,CAAC;AACnB,OAAO,EAAE,2BAA2B,EAAE,MAAM,qBAAqB,CAAC;AAClE,OAAO,EACH,KAAK,cAAc,EACnB,oBAAoB,EACpB,qBAAqB,EACrB,sBAAsB,EACtB,KAAK,cAAc,EACnB,oBAAoB,EACpB,KAAK,mBAAmB,EACxB,yBAAyB,EACzB,KAAK,qBAAqB,EAC1B,2BAA2B,EAC3B,KAAK,eAAe,EACpB,qBAAqB,EACrB,KAAK,oBAAoB,EACzB,0BAA0B,EAC1B,KAAK,gBAAgB,EACrB,sBAAsB,EACtB,qBAAqB,EACrB,sBAAsB,EACtB,aAAa,EACb,KAAK,WAAW,EAChB,iBAAiB,EACjB,KAAK,UAAU,EACf,KAAK,WAAW,EAChB,iBAAiB,EACjB,KAAK,WAAW,EAChB,iBAAiB,EACjB,KAAK,YAAY,EACjB,kBAAkB,EAClB,KAAK,SAAS,EACd,eAAe,EACf,KAAK,sBAAsB,EAC3B,4BAA4B,EAC5B,2BAA2B,EAC3B,KAAK,uBAAuB,EAC5B,6BAA6B,EAC7B,4BAA4B,EAC5B,wBAAwB,EACxB,yBAAyB,EACzB,gBAAgB,EAChB,iBAAiB,EACjB,uBAAuB,EACvB,gCAAgC,EAChC,KAAK,4BAA4B,EACjC,kCAAkC,EAClC,iCAAiC,EACjC,yBAAyB,EACzB,0BAA0B,EAC1B,0BAA0B,EAC1B,2BAA2B,GAC9B,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EAAE,KAAK,WAAW,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAC;AACvE,OAAO,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,KAAK,gBAAgB,EACrB,oBAAoB,EACpB,qBAAqB,EACrB,2BAA2B,EAC3B,qBAAqB,EACrB,gCAAgC,EAChC,0BAA0B,GAC7B,MAAM,eAAe,CAAC;AACvB,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AACxC,OAAO,EAAE,KAAK,cAAc,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AACrE,OAAO,EACH,oBAAoB,EACpB,KAAK,aAAa,EAClB,KAAK,iBAAiB,EACtB,KAAK,0BAA0B,EAC/B,KAAK,YAAY,EACjB,eAAe,GAClB,MAAM,aAAa,CAAC;AACrB,OAAO,EACH,KAAK,YAAY,EACjB,KAAK,mBAAmB,EACxB,KAAK,qBAAqB,EAC1B,UAAU,EACV,KAAK,YAAY,EACjB,KAAK,YAAY,GACpB,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC;AAC9C,OAAO,EACH,qBAAqB,EACrB,2BAA2B,EAC3B,UAAU,EACV,mBAAmB,EACnB,gCAAgC,EAChC,sBAAsB,EACtB,KAAK,QAAQ,GAChB,MAAM,WAAW,CAAC;AACnB,OAAO,EAAE,2BAA2B,EAAE,MAAM,qBAAqB,CAAC;AAClE,OAAO,EAAE,sBAAsB,EAAE,KAAK,mBAAmB,EAAE,2BAA2B,EAAE,MAAM,qBAAqB,CAAC;AACpH,OAAO,EACH,KAAK,cAAc,EACnB,oBAAoB,EACpB,qBAAqB,EACrB,sBAAsB,EACtB,KAAK,cAAc,EACnB,oBAAoB,EACpB,KAAK,mBAAmB,EACxB,yBAAyB,EACzB,KAAK,qBAAqB,EAC1B,2BAA2B,EAC3B,KAAK,eAAe,EACpB,qBAAqB,EACrB,KAAK,oBAAoB,EACzB,0BAA0B,EAC1B,KAAK,gBAAgB,EACrB,sBAAsB,EACtB,qBAAqB,EACrB,sBAAsB,EACtB,aAAa,EACb,KAAK,WAAW,EAChB,iBAAiB,EACjB,KAAK,UAAU,EACf,KAAK,WAAW,EAChB,iBAAiB,EACjB,KAAK,WAAW,EAChB,iBAAiB,EACjB,KAAK,YAAY,EACjB,kBAAkB,EAClB,KAAK,SAAS,EACd,eAAe,EACf,KAAK,sBAAsB,EAC3B,4BAA4B,EAC5B,2BAA2B,EAC3B,KAAK,uBAAuB,EAC5B,6BAA6B,EAC7B,4BAA4B,EAC5B,wBAAwB,EACxB,yBAAyB,EACzB,gBAAgB,EAChB,iBAAiB,EACjB,uBAAuB,EACvB,kBAAkB,EAClB,KAAK,eAAe,EACpB,qBAAqB,EACrB,sBAAsB,EACtB,gCAAgC,EAChC,KAAK,4BAA4B,EACjC,kCAAkC,EAClC,iCAAiC,EACjC,yBAAyB,EACzB,0BAA0B,EAC1B,0BAA0B,EAC1B,2BAA2B,GAC9B,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EAAE,KAAK,WAAW,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAC;AACvE,OAAO,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC"}
package/dist/index.js CHANGED
@@ -1,9 +1,11 @@
1
- export { buildChangeLogRecord, buildCorrectionRecord, buildOperatorDecisionRecord, buildStripDecisionRevertedRecord, buildValidatorResultRecord, } from "./builders.js";
1
+ export { buildChangeLogRecord, buildCorrectionRecord, buildOperatorDecisionRecord, buildStageWriteRecord, buildStripDecisionRevertedRecord, buildValidatorResultRecord, } from "./builders.js";
2
2
  export { runLedgerCli } from "./cli.js";
3
3
  export { computeCoverage } from "./coverage.js";
4
+ export { DOCTOR_FINDING_CODES, runLedgerDoctor, } from "./doctor.js";
4
5
  export { openLedger, } from "./handle.js";
5
6
  export { appendCleanupWaveNote, appendDecompositionWaveNote, appendNote, appendOpenIssueNote, appendSemanticCleanupSummaryNote, appendVerifiedFlowNote, } from "./note.js";
6
7
  export { deriveFilesChangedFromPatch } from "./patch-resolver.js";
7
- export { AgentPatchDiffSchema, AgentPatchEntrySchema, AgentPatchRecordSchema, ChangeLogEntrySchema, ChangeLogFileChangeSchema, ChangeLogParityStatusSchema, ChangeLogRecordSchema, ChangeLogSmokeResultSchema, ChangeLogSubkindSchema, CorrectionEntrySchema, CorrectionRecordSchema, EmitterSchema, LedgerEntrySchema, LedgerLinksSchema, LedgerPhaseSchema, LedgerRecordSchema, NoteEntrySchema, OperatorDecisionActionSchema, OperatorDecisionEntrySchema, OperatorDecisionPayloadSchema, OperatorDecisionRecordSchema, OperatorPatchEntrySchema, OperatorPatchRecordSchema, parseLedgerEntry, parseLedgerRecord, RuntimeEventEntrySchema, StripDecisionRevertedEntrySchema, StripDecisionRevertedPayloadSchema, StripDecisionRevertedRecordSchema, ToolInvocationEntrySchema, ToolInvocationRecordSchema, ValidatorResultEntrySchema, ValidatorResultRecordSchema, } from "./schema/entry.js";
8
+ export { getLedgerRuntimeConfig, validateLedgerRuntimeConfig } from "./runtime-config.js";
9
+ export { AgentPatchDiffSchema, AgentPatchEntrySchema, AgentPatchRecordSchema, ChangeLogEntrySchema, ChangeLogFileChangeSchema, ChangeLogParityStatusSchema, ChangeLogRecordSchema, ChangeLogSmokeResultSchema, ChangeLogSubkindSchema, CorrectionEntrySchema, CorrectionRecordSchema, EmitterSchema, LedgerEntrySchema, LedgerLinksSchema, LedgerPhaseSchema, LedgerRecordSchema, NoteEntrySchema, OperatorDecisionActionSchema, OperatorDecisionEntrySchema, OperatorDecisionPayloadSchema, OperatorDecisionRecordSchema, OperatorPatchEntrySchema, OperatorPatchRecordSchema, parseLedgerEntry, parseLedgerRecord, RuntimeEventEntrySchema, STAGE_WRITE_STAGES, StageWriteEntrySchema, StageWriteRecordSchema, StripDecisionRevertedEntrySchema, StripDecisionRevertedPayloadSchema, StripDecisionRevertedRecordSchema, ToolInvocationEntrySchema, ToolInvocationRecordSchema, ValidatorResultEntrySchema, ValidatorResultRecordSchema, } from "./schema/entry.js";
8
10
  export { NoteSubkindSchema } from "./schema/note.js";
9
11
  export { resolveLedgerPaths } from "./storage/filesystem.js";
package/dist/list.d.ts CHANGED
@@ -8,9 +8,10 @@ export type LedgerFilter = {
8
8
  readonly since?: string;
9
9
  };
10
10
  export declare const getOrderedEntryLocations: (manifest: LedgerManifest, readIndex: LedgerReadIndex, filter: LedgerFilter, direction?: "asc" | "desc") => ManifestEntryLocation[];
11
- export declare const readManifestEntryBatch: ({ allowMissing, entryLocations, workspaceRoot, }: {
11
+ export declare const readManifestEntryBatch: ({ allowMissing, entryLocations, entryReadConcurrency, workspaceRoot, }: {
12
12
  readonly allowMissing?: boolean;
13
13
  readonly entryLocations: readonly ManifestEntryLocation[];
14
+ readonly entryReadConcurrency?: number;
14
15
  readonly workspaceRoot: string;
15
16
  }) => Promise<({
16
17
  entry: {
@@ -75,6 +76,38 @@ export declare const readManifestEntryBatch: ({ allowMissing, entryLocations, wo
75
76
  schemaVersion: "ushman-ledger-entry/v1";
76
77
  summary: string;
77
78
  ts: string;
79
+ } | {
80
+ filePath: string;
81
+ kind: "stage-write";
82
+ rationale: string;
83
+ stage: "intake" | "seed" | "vendor-extract" | "cleanup" | "candidate-promotion";
84
+ details?: {
85
+ [x: string]: unknown;
86
+ } | undefined;
87
+ emitter: {
88
+ tool: string;
89
+ user?: string | undefined;
90
+ version: string;
91
+ };
92
+ id: string;
93
+ links: {
94
+ affectedFiles?: string[] | undefined;
95
+ blobs?: string[] | undefined;
96
+ briefId?: string | undefined;
97
+ correctsLedgerId?: string | undefined;
98
+ gitRef?: string | undefined;
99
+ idempotencyKey?: string | undefined;
100
+ stripDecisionId?: string | undefined;
101
+ supersedesLedgerId?: string | undefined;
102
+ validatorVerdictId?: string | undefined;
103
+ } & {
104
+ [key: string]: unknown;
105
+ };
106
+ phase: "capture" | "intake" | "seed" | "vendor-extract" | "cleanup" | "parity" | "characterize" | "equiv" | "analyze" | "recover" | "ship" | "migration";
107
+ prevEntryId: string | null;
108
+ schemaVersion: "ushman-ledger-entry/v1";
109
+ summary: string;
110
+ ts: string;
78
111
  } | {
79
112
  agent: {
80
113
  name: string;
@@ -1 +1 @@
1
- {"version":3,"file":"list.d.ts","sourceRoot":"","sources":["../src/list.ts"],"names":[],"mappings":"AACA,OAAO,EACH,KAAK,eAAe,EACpB,KAAK,qBAAqB,EAG7B,MAAM,iBAAiB,CAAC;AAEzB,OAAO,EAAE,KAAK,WAAW,EAAE,KAAK,UAAU,EAAE,KAAK,WAAW,EAAoB,MAAM,mBAAmB,CAAC;AAC1G,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAG3D,MAAM,MAAM,YAAY,GAAG;IACvB,QAAQ,CAAC,IAAI,CAAC,EAAE,UAAU,CAAC;IAC3B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,KAAK,CAAC,EAAE,WAAW,CAAC;IAC7B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;CAC3B,CAAC;AAmDF,eAAO,MAAM,wBAAwB,GACjC,UAAU,cAAc,EACxB,WAAW,eAAe,EAC1B,QAAQ,YAAY,EACpB,YAAW,KAAK,GAAG,MAAc,4BAgBpC,CAAC;AAgCF,eAAO,MAAM,sBAAsB,GAAU,kDAI1C;IACC,QAAQ,CAAC,YAAY,CAAC,EAAE,OAAO,CAAC;IAChC,QAAQ,CAAC,cAAc,EAAE,SAAS,qBAAqB,EAAE,CAAC;IAC1D,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;CAClC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KAQI,CAAC;AAiDN,eAAO,MAAM,0BAA0B,GACnC,eAAe,MAAM,EACrB,UAAU,cAAc,EACxB,WAAW,eAAe,EAC1B,SAAQ,YAAiB,EACzB,YAAW,KAAK,GAAG,MAAc,KAClC,aAAa,CAAC,WAAW,CAwB3B,CAAC;AAEF,eAAO,MAAM,WAAW,GACpB,eAAe,MAAM,EACrB,SAAQ,YAAiB,KAC1B,aAAa,CAAC,WAAW,CAG3B,CAAC;AAEF,eAAO,MAAM,cAAc,GAAU,eAAe,MAAM,EAAE,SAAQ,YAAiB,KAAG,OAAO,CAAC,WAAW,EAAE,CAM5G,CAAC"}
1
+ {"version":3,"file":"list.d.ts","sourceRoot":"","sources":["../src/list.ts"],"names":[],"mappings":"AACA,OAAO,EACH,KAAK,eAAe,EACpB,KAAK,qBAAqB,EAG7B,MAAM,iBAAiB,CAAC;AAGzB,OAAO,EAAE,KAAK,WAAW,EAAE,KAAK,UAAU,EAAE,KAAK,WAAW,EAAoB,MAAM,mBAAmB,CAAC;AAC1G,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAG3D,MAAM,MAAM,YAAY,GAAG;IACvB,QAAQ,CAAC,IAAI,CAAC,EAAE,UAAU,CAAC;IAC3B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,KAAK,CAAC,EAAE,WAAW,CAAC;IAC7B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;CAC3B,CAAC;AAgDF,eAAO,MAAM,wBAAwB,GACjC,UAAU,cAAc,EACxB,WAAW,eAAe,EAC1B,QAAQ,YAAY,EACpB,YAAW,KAAK,GAAG,MAAc,4BAgBpC,CAAC;AAiCF,eAAO,MAAM,sBAAsB,GAAU,wEAK1C;IACC,QAAQ,CAAC,YAAY,CAAC,EAAE,OAAO,CAAC;IAChC,QAAQ,CAAC,cAAc,EAAE,SAAS,qBAAqB,EAAE,CAAC;IAC1D,QAAQ,CAAC,oBAAoB,CAAC,EAAE,MAAM,CAAC;IACvC,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;CAClC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KAQI,CAAC;AAkDN,eAAO,MAAM,0BAA0B,GACnC,eAAe,MAAM,EACrB,UAAU,cAAc,EACxB,WAAW,eAAe,EAC1B,SAAQ,YAAiB,EACzB,YAAW,KAAK,GAAG,MAAc,KAClC,aAAa,CAAC,WAAW,CAkC3B,CAAC;AAEF,eAAO,MAAM,WAAW,GACpB,eAAe,MAAM,EACrB,SAAQ,YAAiB,KAC1B,aAAa,CAAC,WAAW,CAG3B,CAAC;AAEF,eAAO,MAAM,cAAc,GAAU,eAAe,MAAM,EAAE,SAAQ,YAAiB,KAAG,OAAO,CAAC,WAAW,EAAE,CAM5G,CAAC"}
package/dist/list.js CHANGED
@@ -1,6 +1,7 @@
1
1
  import { mapWithConcurrencyLimit } from "./async.js";
2
2
  import { matchesReadIndexFilter, } from "./read-index.js";
3
3
  import { loadLedgerState } from "./recovery.js";
4
+ import { getLedgerRuntimeConfig } from "./runtime-config.js";
4
5
  import { parseLedgerEntry } from "./schema/entry.js";
5
6
  import { readPhaseEntryText } from "./storage/filesystem.js";
6
7
  const matchesFilter = (entry, filter) => {
@@ -15,8 +16,6 @@ const matchesFilter = (entry, filter) => {
15
16
  }
16
17
  return true;
17
18
  };
18
- const ENTRY_READ_BATCH_SIZE = 32;
19
- const ENTRY_READ_CONCURRENCY = 16;
20
19
  const getFilteredReadIndexEntries = ({ direction, filter, manifest, readIndex, }) => {
21
20
  const sourceEntries = direction === 'asc' ? readIndex.entries : [...readIndex.entries].reverse();
22
21
  const filteredEntries = [];
@@ -71,20 +70,21 @@ const readManifestEntry = async ({ allowMissing, entryId, location, workspaceRoo
71
70
  throw error;
72
71
  }
73
72
  };
74
- export const readManifestEntryBatch = async ({ allowMissing = false, entryLocations, workspaceRoot, }) => mapWithConcurrencyLimit(entryLocations, ENTRY_READ_CONCURRENCY, async ([entryId, location]) => readManifestEntry({
73
+ export const readManifestEntryBatch = async ({ allowMissing = false, entryLocations, entryReadConcurrency = getLedgerRuntimeConfig().scanConcurrency, workspaceRoot, }) => mapWithConcurrencyLimit(entryLocations, entryReadConcurrency, async ([entryId, location]) => readManifestEntry({
75
74
  allowMissing,
76
75
  entryId,
77
76
  location,
78
77
  workspaceRoot,
79
78
  }));
80
- const collectLimitedEntries = async ({ direction, filter, manifest, readIndex, workspaceRoot, }) => {
79
+ const collectLimitedEntries = async ({ batchSize, direction, entryReadConcurrency, filter, manifest, readIndex, workspaceRoot, }) => {
81
80
  const collectedEntries = [];
82
81
  const orderedEntries = getOrderedEntryLocations(manifest, readIndex, filter, 'desc');
83
82
  const limit = filter.limit ?? 0;
84
- for (let index = 0; index < orderedEntries.length && collectedEntries.length < limit; index += ENTRY_READ_BATCH_SIZE) {
85
- const batch = orderedEntries.slice(index, index + ENTRY_READ_BATCH_SIZE);
83
+ for (let index = 0; index < orderedEntries.length && collectedEntries.length < limit; index += batchSize) {
84
+ const batch = orderedEntries.slice(index, index + batchSize);
86
85
  const resolvedEntries = await readManifestEntryBatch({
87
86
  entryLocations: batch,
87
+ entryReadConcurrency,
88
88
  workspaceRoot,
89
89
  });
90
90
  for (const resolvedEntry of resolvedEntries) {
@@ -105,17 +105,27 @@ const collectLimitedEntries = async ({ direction, filter, manifest, readIndex, w
105
105
  return collectedEntries;
106
106
  };
107
107
  export const iterateEntriesFromManifest = async function* (workspaceRoot, manifest, readIndex, filter = {}, direction = 'asc') {
108
+ const { scanBatchSize, scanConcurrency } = getLedgerRuntimeConfig();
108
109
  if (filter.limit) {
109
- for (const entry of await collectLimitedEntries({ direction, filter, manifest, readIndex, workspaceRoot })) {
110
+ for (const entry of await collectLimitedEntries({
111
+ batchSize: scanBatchSize,
112
+ direction,
113
+ entryReadConcurrency: scanConcurrency,
114
+ filter,
115
+ manifest,
116
+ readIndex,
117
+ workspaceRoot,
118
+ })) {
110
119
  yield entry;
111
120
  }
112
121
  return;
113
122
  }
114
123
  const orderedEntries = getOrderedEntryLocations(manifest, readIndex, filter, direction);
115
- for (let index = 0; index < orderedEntries.length; index += ENTRY_READ_BATCH_SIZE) {
116
- const batch = orderedEntries.slice(index, index + ENTRY_READ_BATCH_SIZE);
124
+ for (let index = 0; index < orderedEntries.length; index += scanBatchSize) {
125
+ const batch = orderedEntries.slice(index, index + scanBatchSize);
117
126
  const resolvedEntries = await readManifestEntryBatch({
118
127
  entryLocations: batch,
128
+ entryReadConcurrency: scanConcurrency,
119
129
  workspaceRoot,
120
130
  });
121
131
  for (const resolvedEntry of resolvedEntries) {
@@ -1 +1 @@
1
- {"version":3,"file":"patch-resolver.d.ts","sourceRoot":"","sources":["../src/patch-resolver.ts"],"names":[],"mappings":"AAIA,OAAO,EACH,KAAK,cAAc,EACnB,KAAK,mBAAmB,EACxB,KAAK,WAAW,EAChB,KAAK,YAAY,EAEpB,MAAM,mBAAmB,CAAC;AAI3B,KAAK,gBAAgB,GAAG,OAAO,CAAC,YAAY,EAAE;IAAE,IAAI,EAAE,aAAa,CAAA;CAAE,CAAC,CAAC;AACvE,KAAK,mBAAmB,GAAG,OAAO,CAAC,YAAY,EAAE;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,CAAC,CAAC;AAQ7E,KAAK,wBAAwB,GAAG,IAAI,CAAC,gBAAgB,EAAE,UAAU,GAAG,UAAU,GAAG,OAAO,CAAC,GAAG;IACxF,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;IAC9B,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;CAC/B,CAAC;AACF,KAAK,2BAA2B,GAAG,IAAI,CAAC,mBAAmB,EAAE,UAAU,GAAG,UAAU,GAAG,OAAO,CAAC,GAAG;IAC9F,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;IAC9B,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;CAC/B,CAAC;AAEF,MAAM,MAAM,mBAAmB,GAAG,wBAAwB,GAAG,2BAA2B,CAAC;AAqKzF;;;;;;;;;;;GAWG;AACH,eAAO,MAAM,2BAA2B,GAAI,WAAW,MAAM,KAAG,mBAAmB,EAuClF,CAAC;AAmBF,wBAAgB,kBAAkB,CAAC,IAAI,EAAE;IACrC,QAAQ,CAAC,MAAM,EAAE,gBAAgB,CAAC;IAClC,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;CAClC,GAAG,OAAO,CAAC,wBAAwB,CAAC,CAAC;AACtC,wBAAgB,kBAAkB,CAAC,IAAI,EAAE;IACrC,QAAQ,CAAC,MAAM,EAAE,mBAAmB,CAAC;IACrC,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;CAClC,GAAG,OAAO,CAAC,2BAA2B,CAAC,CAAC"}
1
+ {"version":3,"file":"patch-resolver.d.ts","sourceRoot":"","sources":["../src/patch-resolver.ts"],"names":[],"mappings":"AAIA,OAAO,EACH,KAAK,cAAc,EACnB,KAAK,mBAAmB,EACxB,KAAK,WAAW,EAChB,KAAK,YAAY,EAEpB,MAAM,mBAAmB,CAAC;AAK3B,KAAK,gBAAgB,GAAG,OAAO,CAAC,YAAY,EAAE;IAAE,IAAI,EAAE,aAAa,CAAA;CAAE,CAAC,CAAC;AACvE,KAAK,mBAAmB,GAAG,OAAO,CAAC,YAAY,EAAE;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,CAAC,CAAC;AAQ7E,KAAK,wBAAwB,GAAG,IAAI,CAAC,gBAAgB,EAAE,UAAU,GAAG,UAAU,GAAG,OAAO,CAAC,GAAG;IACxF,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;IAC9B,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;CAC/B,CAAC;AACF,KAAK,2BAA2B,GAAG,IAAI,CAAC,mBAAmB,EAAE,UAAU,GAAG,UAAU,GAAG,OAAO,CAAC,GAAG;IAC9F,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;IAC9B,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;CAC/B,CAAC;AAEF,MAAM,MAAM,mBAAmB,GAAG,wBAAwB,GAAG,2BAA2B,CAAC;AAsTzF;;;;;;;;;;;GAWG;AACH,eAAO,MAAM,2BAA2B,GAAI,WAAW,MAAM,KAAG,mBAAmB,EAuClF,CAAC;AAmBF,wBAAgB,kBAAkB,CAAC,IAAI,EAAE;IACrC,QAAQ,CAAC,MAAM,EAAE,gBAAgB,CAAC;IAClC,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;CAClC,GAAG,OAAO,CAAC,wBAAwB,CAAC,CAAC;AACtC,wBAAgB,kBAAkB,CAAC,IAAI,EAAE;IACrC,QAAQ,CAAC,MAAM,EAAE,mBAAmB,CAAC;IACrC,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;CAClC,GAAG,OAAO,CAAC,2BAA2B,CAAC,CAAC"}
@@ -1,28 +1,94 @@
1
- import { readFile } from 'node:fs/promises';
1
+ import { readFile, stat } from 'node:fs/promises';
2
2
  import path from 'node:path';
3
3
  import * as v from 'valibot';
4
- import { resolveBlobPath, storePatchBlob } from "./blobs.js";
4
+ import { assertPatchTextWithinLimit, readPatchTextFromFile, resolveBlobPath, storePatchBlob } from "./blobs.js";
5
5
  import { WorkspaceRelativePathSchema, } from "./schema/entry.js";
6
+ import { forEachLine } from "./text-lines.js";
6
7
  const readBlobText = async (workspaceRoot, blobSha256) => readFile(resolveBlobPath(workspaceRoot, blobSha256), 'utf8');
7
8
  const formatRecordContext = (record) => `${record.kind} "${record.summary}" [${record.phase}]`;
8
9
  const normalizeWorkspaceRelativePath = (value) => v.parse(WorkspaceRelativePathSchema, value.replaceAll('\\', '/'));
9
- const stripGitPathPrefix = (value) => {
10
+ const normalizeDiffPathToken = ({ headerPrefixes, side, value, }) => {
10
11
  const normalized = value.trim().replace(/^"([^"]*)"$/u, '$1');
11
12
  if (normalized === '/dev/null') {
12
13
  return null;
13
14
  }
14
- if (normalized.startsWith('a/') || normalized.startsWith('b/')) {
15
- return normalized.slice(2);
15
+ const expectedPrefix = side === 'old' ? headerPrefixes?.oldPrefix : headerPrefixes?.newPrefix;
16
+ if (expectedPrefix && normalized.startsWith(expectedPrefix)) {
17
+ return normalized.slice(expectedPrefix.length);
16
18
  }
17
19
  return normalized;
18
20
  };
19
- const inferHeaderPath = (line) => {
20
- const match = /^diff --git (?:"a\/([^"]+)"|a\/(\S+)) (?:"b\/([^"]+)"|b\/(\S+))$/u.exec(line.trim());
21
- if (!match) {
21
+ const splitPrefixCandidate = (value) => {
22
+ const slashIndex = value.indexOf('/');
23
+ if (slashIndex <= 0) {
22
24
  return null;
23
25
  }
24
- const rightPath = match[3] ?? match[4];
25
- return rightPath ? stripGitPathPrefix(`b/${rightPath}`) : null;
26
+ return {
27
+ prefix: value.slice(0, slashIndex + 1),
28
+ suffix: value.slice(slashIndex + 1),
29
+ };
30
+ };
31
+ const readDiffHeaderToken = (headerBody, startIndex) => {
32
+ let index = startIndex;
33
+ while (headerBody[index] === ' ') {
34
+ index += 1;
35
+ }
36
+ if (index >= headerBody.length) {
37
+ return null;
38
+ }
39
+ if (headerBody[index] === '"') {
40
+ const endIndex = headerBody.indexOf('"', index + 1);
41
+ if (endIndex === -1) {
42
+ return null;
43
+ }
44
+ return {
45
+ nextIndex: endIndex + 1,
46
+ token: headerBody.slice(index + 1, endIndex),
47
+ };
48
+ }
49
+ let endIndex = index;
50
+ while (endIndex < headerBody.length && headerBody[endIndex] !== ' ') {
51
+ endIndex += 1;
52
+ }
53
+ return {
54
+ nextIndex: endIndex + 1,
55
+ token: headerBody.slice(index, endIndex),
56
+ };
57
+ };
58
+ const resolveHeaderPrefixes = (oldPath, newPath) => {
59
+ if (oldPath.startsWith('a/') && newPath.startsWith('b/')) {
60
+ return {
61
+ newPrefix: 'b/',
62
+ oldPrefix: 'a/',
63
+ };
64
+ }
65
+ const oldCandidate = splitPrefixCandidate(oldPath);
66
+ const newCandidate = splitPrefixCandidate(newPath);
67
+ if (!oldCandidate ||
68
+ !newCandidate ||
69
+ oldCandidate.prefix === newCandidate.prefix ||
70
+ oldCandidate.suffix !== newCandidate.suffix) {
71
+ return null;
72
+ }
73
+ return {
74
+ newPrefix: newCandidate.prefix,
75
+ oldPrefix: oldCandidate.prefix,
76
+ };
77
+ };
78
+ const parseDiffHeaderPaths = (line) => {
79
+ const headerBody = line.trim().slice('diff --git '.length);
80
+ const firstToken = readDiffHeaderToken(headerBody, 0);
81
+ const secondToken = firstToken ? readDiffHeaderToken(headerBody, firstToken.nextIndex) : null;
82
+ if (!firstToken?.token || !secondToken?.token) {
83
+ return null;
84
+ }
85
+ const oldPath = firstToken.token;
86
+ const newPath = secondToken.token;
87
+ return {
88
+ headerPrefixes: resolveHeaderPrefixes(oldPath, newPath),
89
+ newPath,
90
+ oldPath,
91
+ };
26
92
  };
27
93
  const finalizeFileChange = (current, filesChanged) => {
28
94
  if (!current) {
@@ -38,19 +104,33 @@ const finalizeFileChange = (current, filesChanged) => {
38
104
  removed: current.removed > 0 ? current.removed : undefined,
39
105
  });
40
106
  };
41
- const createDiffFileAccumulator = (line) => ({
42
- added: 0,
43
- headerPath: inferHeaderPath(line),
44
- minusPath: null,
45
- plusPath: null,
46
- removed: 0,
47
- });
107
+ const createDiffFileAccumulator = (line) => {
108
+ const headerPaths = parseDiffHeaderPaths(line);
109
+ return {
110
+ added: 0,
111
+ headerPath: headerPaths
112
+ ? normalizeDiffPathToken({
113
+ headerPrefixes: headerPaths.headerPrefixes,
114
+ side: 'new',
115
+ value: headerPaths.newPath,
116
+ })
117
+ : null,
118
+ headerPrefixes: headerPaths?.headerPrefixes ?? null,
119
+ minusPath: null,
120
+ plusPath: null,
121
+ removed: 0,
122
+ };
123
+ };
48
124
  const applyPatchMetadataLine = (current, line) => {
49
125
  if (line.startsWith('+++ ')) {
50
126
  return {
51
127
  next: {
52
128
  ...current,
53
- plusPath: stripGitPathPrefix(line.slice(4)),
129
+ plusPath: normalizeDiffPathToken({
130
+ headerPrefixes: current.headerPrefixes,
131
+ side: 'new',
132
+ value: line.slice(4),
133
+ }),
54
134
  },
55
135
  };
56
136
  }
@@ -58,7 +138,35 @@ const applyPatchMetadataLine = (current, line) => {
58
138
  return {
59
139
  next: {
60
140
  ...current,
61
- minusPath: stripGitPathPrefix(line.slice(4)),
141
+ minusPath: normalizeDiffPathToken({
142
+ headerPrefixes: current.headerPrefixes,
143
+ side: 'old',
144
+ value: line.slice(4),
145
+ }),
146
+ },
147
+ };
148
+ }
149
+ if (line.startsWith('rename from ')) {
150
+ return {
151
+ next: {
152
+ ...current,
153
+ minusPath: normalizeDiffPathToken({
154
+ headerPrefixes: null,
155
+ side: 'old',
156
+ value: line.slice('rename from '.length),
157
+ }),
158
+ },
159
+ };
160
+ }
161
+ if (line.startsWith('rename to ')) {
162
+ return {
163
+ next: {
164
+ ...current,
165
+ plusPath: normalizeDiffPathToken({
166
+ headerPrefixes: null,
167
+ side: 'new',
168
+ value: line.slice('rename to '.length),
169
+ }),
62
170
  },
63
171
  };
64
172
  }
@@ -74,16 +182,12 @@ const applyPatchMetadataLine = (current, line) => {
74
182
  };
75
183
  const applyPatchHunkLine = (current, line) => {
76
184
  if (line.startsWith('+')) {
77
- return {
78
- ...current,
79
- added: current.added + 1,
80
- };
185
+ current.added += 1;
186
+ return current;
81
187
  }
82
188
  if (line.startsWith('-')) {
83
- return {
84
- ...current,
85
- removed: current.removed + 1,
86
- };
189
+ current.removed += 1;
190
+ return current;
87
191
  }
88
192
  return current;
89
193
  };
@@ -91,36 +195,56 @@ const mergeBlobLink = (links, blobSha256) => ({
91
195
  ...links,
92
196
  blobs: [...new Set([...(links?.blobs ?? []), blobSha256])],
93
197
  });
94
- const resolvePatchSource = async ({ record, workspaceRoot, }) => {
95
- if (record.diffPath) {
96
- const resolvedPath = path.resolve(workspaceRoot, record.diffPath);
198
+ const resolvePatchSourceFromFile = async (record, workspaceRoot) => {
199
+ const resolvedPath = path.resolve(workspaceRoot, record.diffPath);
200
+ try {
97
201
  return {
98
- patchText: await readFile(resolvedPath, 'utf8'),
202
+ patchText: await readPatchTextFromFile(resolvedPath),
99
203
  source: 'file',
100
204
  sourceLabel: resolvedPath,
101
205
  };
102
206
  }
103
- if (record.diffText) {
207
+ catch (error) {
208
+ throw new Error(`Failed to read diff file ${resolvedPath} for ${formatRecordContext(record)}: ${error instanceof Error ? error.message : String(error)}`);
209
+ }
210
+ };
211
+ const resolvePatchSourceFromInlineText = (record) => {
212
+ try {
213
+ assertPatchTextWithinLimit(record.diffText, 'inline diff text');
104
214
  return {
105
215
  patchText: record.diffText,
106
216
  source: 'inline',
107
217
  sourceLabel: 'inline diff text',
108
218
  };
109
219
  }
110
- if (record.diff) {
111
- try {
112
- return {
113
- patchText: await readBlobText(workspaceRoot, record.diff.blobSha256),
114
- source: 'blob',
115
- sourceLabel: `blob ${record.diff.blobSha256}`,
116
- };
117
- }
118
- catch (error) {
119
- if (error.code === 'ENOENT') {
120
- throw new Error(`Patch blob ${record.diff.blobSha256} was not found for ${formatRecordContext(record)}. Store it first or use diffPath.`);
121
- }
122
- throw error;
220
+ catch (error) {
221
+ throw new Error(`Failed to validate inline diff text for ${formatRecordContext(record)}: ${error instanceof Error ? error.message : String(error)}`);
222
+ }
223
+ };
224
+ const resolvePatchSourceFromStoredBlob = async (record, workspaceRoot) => {
225
+ try {
226
+ return {
227
+ patchText: await readBlobText(workspaceRoot, record.diff?.blobSha256),
228
+ source: 'blob',
229
+ sourceLabel: `blob ${record.diff?.blobSha256}`,
230
+ };
231
+ }
232
+ catch (error) {
233
+ if (error.code === 'ENOENT') {
234
+ throw new Error(`Patch blob ${record.diff?.blobSha256} was not found for ${formatRecordContext(record)}. Store it first or use diffPath.`);
123
235
  }
236
+ throw error;
237
+ }
238
+ };
239
+ const resolvePatchSource = async ({ record, workspaceRoot, }) => {
240
+ if (record.diffPath) {
241
+ return resolvePatchSourceFromFile(record, workspaceRoot);
242
+ }
243
+ if (record.diffText) {
244
+ return resolvePatchSourceFromInlineText(record);
245
+ }
246
+ if (record.diff) {
247
+ return resolvePatchSourceFromStoredBlob(record, workspaceRoot);
124
248
  }
125
249
  throw new Error(`${record.kind} records require diff, diffPath, or diffText.`);
126
250
  };
@@ -140,34 +264,34 @@ export const deriveFilesChangedFromPatch = (patchText) => {
140
264
  const filesChanged = [];
141
265
  let current;
142
266
  let insideHunk = false;
143
- for (const line of patchText.split(/\r?\n/u)) {
267
+ forEachLine(patchText, (line) => {
144
268
  if (line.startsWith('diff --git ')) {
145
269
  finalizeFileChange(current, filesChanged);
146
270
  current = createDiffFileAccumulator(line);
147
271
  insideHunk = false;
148
- continue;
272
+ return;
149
273
  }
150
274
  if (!current) {
151
- continue;
275
+ return;
152
276
  }
153
277
  if (insideHunk) {
154
278
  if (line.startsWith('@@')) {
155
- continue;
279
+ return;
156
280
  }
157
281
  current = applyPatchHunkLine(current, line);
158
- continue;
282
+ return;
159
283
  }
160
284
  const metadataUpdate = applyPatchMetadataLine(current, line);
161
285
  current = metadataUpdate.next;
162
286
  if (metadataUpdate.startHunk) {
163
287
  insideHunk = true;
164
- continue;
288
+ return;
165
289
  }
166
290
  if (!insideHunk) {
167
- continue;
291
+ return;
168
292
  }
169
293
  current = applyPatchHunkLine(current, line);
170
- }
294
+ });
171
295
  finalizeFileChange(current, filesChanged);
172
296
  return filesChanged;
173
297
  };
@@ -180,6 +304,22 @@ const buildResolvedPatchRecord = ({ links, record, storedDiff, }) => {
180
304
  };
181
305
  };
182
306
  export async function resolvePatchRecord({ record, workspaceRoot, }) {
307
+ if (record.diff && !record.diffPath && !record.diffText) {
308
+ try {
309
+ await stat(resolveBlobPath(workspaceRoot, record.diff.blobSha256));
310
+ }
311
+ catch (error) {
312
+ if (error.code === 'ENOENT') {
313
+ throw new Error(`Patch blob ${record.diff.blobSha256} was not found for ${formatRecordContext(record)}. Store it first or use diffPath.`);
314
+ }
315
+ throw new Error(`Failed to read patch blob ${record.diff.blobSha256} for ${formatRecordContext(record)}: ${error instanceof Error ? error.message : String(error)}`);
316
+ }
317
+ return buildResolvedPatchRecord({
318
+ links: mergeBlobLink(record.links, record.diff.blobSha256),
319
+ record,
320
+ storedDiff: record.diff,
321
+ });
322
+ }
183
323
  const { patchText, sourceLabel } = await resolvePatchSource({
184
324
  record,
185
325
  workspaceRoot,
@@ -0,0 +1,2 @@
1
+ export declare const isProcessAlive: (pid: number) => boolean;
2
+ //# sourceMappingURL=process.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"process.d.ts","sourceRoot":"","sources":["../src/process.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,cAAc,GAAI,KAAK,MAAM,YAczC,CAAC"}
@@ -0,0 +1,16 @@
1
+ export const isProcessAlive = (pid) => {
2
+ try {
3
+ process.kill(pid, 0);
4
+ return true;
5
+ }
6
+ catch (error) {
7
+ const code = error.code;
8
+ if (code === 'EPERM') {
9
+ return true;
10
+ }
11
+ if (code === 'ESRCH') {
12
+ return false;
13
+ }
14
+ throw error;
15
+ }
16
+ };
@@ -3,14 +3,14 @@ import { type LedgerEntry, type LedgerKind, type LedgerPhase } from './schema/en
3
3
  import type { LedgerManifest } from './schema/manifest.ts';
4
4
  declare const ReadIndexEntrySchema: v.ObjectSchema<{
5
5
  readonly id: v.SchemaWithPipe<readonly [v.StringSchema<undefined>, v.MinLengthAction<string, 1, undefined>]>;
6
- readonly kind: v.PicklistSchema<readonly ["tool-invocation", "agent-patch", "operator-patch", "operator-decision", "validator-result", "runtime-event", "note", "correction", "strip-decision-reverted", "change-log"], undefined>;
6
+ readonly kind: v.PicklistSchema<readonly ["tool-invocation", "stage-write", "agent-patch", "operator-patch", "operator-decision", "validator-result", "runtime-event", "note", "correction", "strip-decision-reverted", "change-log"], undefined>;
7
7
  readonly ts: v.SchemaWithPipe<readonly [v.StringSchema<undefined>, v.IsoTimestampAction<string, undefined>]>;
8
8
  }, undefined>;
9
9
  declare const LedgerReadIndexSchema: v.SchemaWithPipe<readonly [v.ObjectSchema<{
10
10
  readonly coveredFiles: v.OptionalSchema<v.ArraySchema<v.StringSchema<undefined>, undefined>, readonly []>;
11
11
  readonly entries: v.OptionalSchema<v.ArraySchema<v.ObjectSchema<{
12
12
  readonly id: v.SchemaWithPipe<readonly [v.StringSchema<undefined>, v.MinLengthAction<string, 1, undefined>]>;
13
- readonly kind: v.PicklistSchema<readonly ["tool-invocation", "agent-patch", "operator-patch", "operator-decision", "validator-result", "runtime-event", "note", "correction", "strip-decision-reverted", "change-log"], undefined>;
13
+ readonly kind: v.PicklistSchema<readonly ["tool-invocation", "stage-write", "agent-patch", "operator-patch", "operator-decision", "validator-result", "runtime-event", "note", "correction", "strip-decision-reverted", "change-log"], undefined>;
14
14
  readonly ts: v.SchemaWithPipe<readonly [v.StringSchema<undefined>, v.IsoTimestampAction<string, undefined>]>;
15
15
  }, undefined>, undefined>, readonly []>;
16
16
  readonly entryCount: v.SchemaWithPipe<readonly [v.NumberSchema<undefined>, v.IntegerAction<number, undefined>, v.MinValueAction<number, 0, undefined>]>;
@@ -21,7 +21,7 @@ declare const LedgerReadIndexSchema: v.SchemaWithPipe<readonly [v.ObjectSchema<{
21
21
  coveredFiles: string[];
22
22
  entries: {
23
23
  id: string;
24
- kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
24
+ kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "stage-write" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
25
25
  ts: string;
26
26
  }[];
27
27
  entryCount: number;
@@ -32,7 +32,7 @@ declare const LedgerReadIndexSchema: v.SchemaWithPipe<readonly [v.ObjectSchema<{
32
32
  coveredFiles: string[];
33
33
  entries: {
34
34
  id: string;
35
- kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
35
+ kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "stage-write" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
36
36
  ts: string;
37
37
  }[];
38
38
  entryCount: number;
@@ -50,7 +50,7 @@ export declare const buildReadIndexFromManifest: (workspaceRoot: string, manifes
50
50
  coveredFiles: string[];
51
51
  entries: {
52
52
  id: string;
53
- kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
53
+ kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "stage-write" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
54
54
  ts: string;
55
55
  }[];
56
56
  entryCount: number;
@@ -65,7 +65,7 @@ export declare const ensureReadIndexUnderLock: (workspaceRoot: string, manifest:
65
65
  coveredFiles: string[];
66
66
  entries: {
67
67
  id: string;
68
- kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
68
+ kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "stage-write" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
69
69
  ts: string;
70
70
  }[];
71
71
  entryCount: number;
@@ -81,7 +81,7 @@ export declare const appendEntryToReadIndex: ({ entry, readIndex, sequence, }: {
81
81
  coveredFiles: string[];
82
82
  entries: {
83
83
  id: string;
84
- kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
84
+ kind: "operator-decision" | "validator-result" | "change-log" | "tool-invocation" | "stage-write" | "agent-patch" | "operator-patch" | "runtime-event" | "note" | "correction" | "strip-decision-reverted";
85
85
  ts: string;
86
86
  }[];
87
87
  entryCount: number;
@@ -1 +1 @@
1
- {"version":3,"file":"read-index.d.ts","sourceRoot":"","sources":["../src/read-index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,CAAC,MAAM,SAAS,CAAC;AAG7B,OAAO,EAAgB,KAAK,WAAW,EAAE,KAAK,UAAU,EAAE,KAAK,WAAW,EAAoB,MAAM,mBAAmB,CAAC;AACxH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAO3D,QAAA,MAAM,oBAAoB;;;;aAIxB,CAAC;AAEH,QAAA,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;sDAc1B,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,CAAC,CAAC,WAAW,CAAC,OAAO,qBAAqB,CAAC,CAAC;AAC1E,MAAM,MAAM,cAAc,GAAG,CAAC,CAAC,WAAW,CAAC,OAAO,oBAAoB,CAAC,CAAC;AACxE,MAAM,MAAM,qBAAqB,GAAG,SAAS,CAAC,MAAM,EAAE;IAAE,KAAK,EAAE,WAAW,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;AA0HhG,eAAO,MAAM,0BAA0B,GAAU,eAAe,MAAM,EAAE,UAAU,cAAc;;;;;;;;;;;EAuB/F,CAAC;AAYF,eAAO,MAAM,kBAAkB,GAAI,OAAO,eAAe,EAAE,UAAU,cAAc,YAG1C,CAAC;AAE1C,eAAO,MAAM,aAAa,GAAU,eAAe,MAAM,KAAG,OAAO,CAAC,eAAe,GAAG,IAAI,CAWzF,CAAC;AAEF,eAAO,MAAM,aAAa,GAAU,eAAe,MAAM,EAAE,WAAW,eAAe,kBAGpF,CAAC;AAEF,eAAO,MAAM,wBAAwB,GAAU,eAAe,MAAM,EAAE,UAAU,cAAc;;;;;;;;;;;EAiB7F,CAAC;AAEF,eAAO,MAAM,sBAAsB,GAAI,iCAIpC;IACC,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;IAC5B,QAAQ,CAAC,SAAS,EAAE,eAAe,CAAC;IACpC,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;CAC7B;;;;;;;;;;;CAYA,CAAC;AAEF,eAAO,MAAM,sBAAsB,GAAI,uCAIpC;IACC,QAAQ,CAAC,MAAM,EAAE;QACb,QAAQ,CAAC,IAAI,CAAC,EAAE,UAAU,CAAC;QAC3B,QAAQ,CAAC,KAAK,CAAC,EAAE,WAAW,CAAC;QAC7B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;KAC3B,CAAC;IACF,QAAQ,CAAC,QAAQ,EAAE,cAAc,CAAC;IAClC,QAAQ,CAAC,cAAc,EAAE,cAAc,CAAC;CAC3C,YAeA,CAAC"}
1
+ {"version":3,"file":"read-index.d.ts","sourceRoot":"","sources":["../src/read-index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,CAAC,MAAM,SAAS,CAAC;AAI7B,OAAO,EAAgB,KAAK,WAAW,EAAE,KAAK,UAAU,EAAE,KAAK,WAAW,EAAoB,MAAM,mBAAmB,CAAC;AACxH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAK3D,QAAA,MAAM,oBAAoB;;;;aAIxB,CAAC;AAEH,QAAA,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;sDAc1B,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,CAAC,CAAC,WAAW,CAAC,OAAO,qBAAqB,CAAC,CAAC;AAC1E,MAAM,MAAM,cAAc,GAAG,CAAC,CAAC,WAAW,CAAC,OAAO,oBAAoB,CAAC,CAAC;AACxE,MAAM,MAAM,qBAAqB,GAAG,SAAS,CAAC,MAAM,EAAE;IAAE,KAAK,EAAE,WAAW,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;AAmIhG,eAAO,MAAM,0BAA0B,GAAU,eAAe,MAAM,EAAE,UAAU,cAAc;;;;;;;;;;;EAyB/F,CAAC;AAYF,eAAO,MAAM,kBAAkB,GAAI,OAAO,eAAe,EAAE,UAAU,cAAc,YAG1C,CAAC;AAE1C,eAAO,MAAM,aAAa,GAAU,eAAe,MAAM,KAAG,OAAO,CAAC,eAAe,GAAG,IAAI,CAWzF,CAAC;AAEF,eAAO,MAAM,aAAa,GAAU,eAAe,MAAM,EAAE,WAAW,eAAe,kBAGpF,CAAC;AAEF,eAAO,MAAM,wBAAwB,GAAU,eAAe,MAAM,EAAE,UAAU,cAAc;;;;;;;;;;;EAiB7F,CAAC;AAEF,eAAO,MAAM,sBAAsB,GAAI,iCAIpC;IACC,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;IAC5B,QAAQ,CAAC,SAAS,EAAE,eAAe,CAAC;IACpC,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;CAC7B;;;;;;;;;;;CASA,CAAC;AAEF,eAAO,MAAM,sBAAsB,GAAI,uCAIpC;IACC,QAAQ,CAAC,MAAM,EAAE;QACb,QAAQ,CAAC,IAAI,CAAC,EAAE,UAAU,CAAC;QAC3B,QAAQ,CAAC,KAAK,CAAC,EAAE,WAAW,CAAC;QAC7B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;KAC3B,CAAC;IACF,QAAQ,CAAC,QAAQ,EAAE,cAAc,CAAC;IAClC,QAAQ,CAAC,cAAc,EAAE,cAAc,CAAC;CAC3C,YAeA,CAAC"}