@agentxm/workspace-operations 0.28.4-bootstrap.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/LICENSE +110 -0
- package/README.md +12 -0
- package/dist/src/index.d.ts +31 -0
- package/dist/src/index.js +42 -0
- package/dist/src/live.d.ts +13 -0
- package/dist/src/live.js +12 -0
- package/dist/src/operations/augment-plan.d.ts +25 -0
- package/dist/src/operations/augment-plan.js +51 -0
- package/dist/src/operations/load-workspace.d.ts +43 -0
- package/dist/src/operations/load-workspace.js +77 -0
- package/dist/src/operations/scan-plan-readiness.d.ts +22 -0
- package/dist/src/operations/scan-plan-readiness.js +41 -0
- package/dist/src/operations/transaction.d.ts +58 -0
- package/dist/src/operations/transaction.js +359 -0
- package/dist/src/operations/transition-lock.d.ts +66 -0
- package/dist/src/operations/transition-lock.js +291 -0
- package/dist/src/plan/apply-plan.d.ts +45 -0
- package/dist/src/plan/apply-plan.js +238 -0
- package/dist/src/plan/errors.d.ts +85 -0
- package/dist/src/plan/errors.js +101 -0
- package/dist/src/plan/execution-candidate.d.ts +20 -0
- package/dist/src/plan/execution-candidate.js +95 -0
- package/dist/src/plan/interruption-signal.d.ts +18 -0
- package/dist/src/plan/interruption-signal.js +13 -0
- package/dist/src/plan/job-step-message.d.ts +7 -0
- package/dist/src/plan/job-step-message.js +7 -0
- package/dist/src/plan/operation-events.d.ts +62 -0
- package/dist/src/plan/operation-events.js +41 -0
- package/dist/src/plan/operation-journal.d.ts +69 -0
- package/dist/src/plan/operation-journal.js +52 -0
- package/dist/src/plan/operation-resolution.d.ts +219 -0
- package/dist/src/plan/operation-resolution.js +324 -0
- package/dist/src/plan/plan-execution.d.ts +75 -0
- package/dist/src/plan/plan-execution.js +117 -0
- package/dist/src/plan/plan.d.ts +248 -0
- package/dist/src/plan/plan.js +95 -0
- package/dist/src/plan/resolve-plan-interaction.d.ts +79 -0
- package/dist/src/plan/resolve-plan-interaction.js +52 -0
- package/dist/src/plan/resolve-plan.d.ts +42 -0
- package/dist/src/plan/resolve-plan.js +694 -0
- package/dist/src/plan/step-failure-conversions.d.ts +33 -0
- package/dist/src/plan/step-failure-conversions.js +177 -0
- package/dist/src/testing.d.ts +11 -0
- package/dist/src/testing.js +11 -0
- package/package.json +61 -0
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Conversions from typed workspace failures into `StepFailure` values that a
|
|
3
|
+
* plan resolution embeds. Category, detail, and suggestion strings are the
|
|
4
|
+
* plan pipeline's serialized contract: they must stay byte-identical to the
|
|
5
|
+
* CLI boundary's `AppError` renderings of the same failures, so machine
|
|
6
|
+
* output does not depend on which side of the seam rendered the failure.
|
|
7
|
+
*
|
|
8
|
+
* @experimental This API is unstable and may change without notice.
|
|
9
|
+
*/
|
|
10
|
+
import type { ConfiguredAgentOutcomesUnavailable, WorkspaceRestorationIncomplete, WorkspaceStateReadFailure, WorkspaceTransactionFailure } from "@agentxm/workspace-state";
|
|
11
|
+
import { StepFailure, type CandidateFingerprintFailed } from "./errors.js";
|
|
12
|
+
/** Translate a scoped settings- or lockfile-read failure, naming the fix. */
|
|
13
|
+
export declare const workspaceStateReadFailureToStepFailure: (error: WorkspaceStateReadFailure) => StepFailure;
|
|
14
|
+
/**
|
|
15
|
+
* Translate a transaction-machinery failure, reproducing each step's detail.
|
|
16
|
+
* A `StepFailure` passes through unchanged: producers inside the transition
|
|
17
|
+
* already speak the serialized vocabulary.
|
|
18
|
+
*/
|
|
19
|
+
export declare const workspaceTransactionFailureToStepFailure: (failure: WorkspaceTransactionFailure | StepFailure) => StepFailure;
|
|
20
|
+
/** Translate an execution-material fingerprint failure. */
|
|
21
|
+
export declare const candidateFingerprintFailedToStepFailure: (error: CandidateFingerprintFailed) => StepFailure;
|
|
22
|
+
/**
|
|
23
|
+
* Translate a provider failure: the implementation chose the category and
|
|
24
|
+
* wording at construction, so the fields carry over 1:1.
|
|
25
|
+
*/
|
|
26
|
+
export declare const configuredAgentOutcomesUnavailableToStepFailure: (error: ConfiguredAgentOutcomesUnavailable) => StepFailure;
|
|
27
|
+
/**
|
|
28
|
+
* Render the typed restoration failure: the deciding transition cause, the
|
|
29
|
+
* retained-state consequence, and the preserved snapshot directory when one
|
|
30
|
+
* exists.
|
|
31
|
+
*/
|
|
32
|
+
export declare const restorationIncompleteToStepFailure: (error: WorkspaceRestorationIncomplete) => StepFailure;
|
|
33
|
+
//# sourceMappingURL=step-failure-conversions.d.ts.map
|
|
@@ -0,0 +1,177 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Conversions from typed workspace failures into `StepFailure` values that a
|
|
3
|
+
* plan resolution embeds. Category, detail, and suggestion strings are the
|
|
4
|
+
* plan pipeline's serialized contract: they must stay byte-identical to the
|
|
5
|
+
* CLI boundary's `AppError` renderings of the same failures, so machine
|
|
6
|
+
* output does not depend on which side of the seam rendered the failure.
|
|
7
|
+
*
|
|
8
|
+
* @experimental This API is unstable and may change without notice.
|
|
9
|
+
*/
|
|
10
|
+
import * as Cause from "effect/Cause";
|
|
11
|
+
import * as Option from "effect/Option";
|
|
12
|
+
import { STALE_CANDIDATE_DETAIL, StaleExecutionCandidate, StepFailure, } from "./errors.js";
|
|
13
|
+
/** Translate a scoped settings- or lockfile-read failure, naming the fix. */
|
|
14
|
+
export const workspaceStateReadFailureToStepFailure = (error) => {
|
|
15
|
+
switch (error._tag) {
|
|
16
|
+
case "SettingsDecodeError":
|
|
17
|
+
return new StepFailure({
|
|
18
|
+
category: "validation",
|
|
19
|
+
detail: `Invalid workspace settings at ${error.path}: ${error.issues.join("; ")}`,
|
|
20
|
+
suggestions: [
|
|
21
|
+
{ description: "Edit the settings file to fix the invalid value, then re-run." },
|
|
22
|
+
],
|
|
23
|
+
cause: error,
|
|
24
|
+
});
|
|
25
|
+
case "SettingsParseError":
|
|
26
|
+
return new StepFailure({
|
|
27
|
+
category: "validation",
|
|
28
|
+
detail: `Workspace settings at ${error.path} are not valid JSON`,
|
|
29
|
+
suggestions: [{ description: "Fix the JSON syntax in the settings file, then re-run." }],
|
|
30
|
+
cause: error,
|
|
31
|
+
});
|
|
32
|
+
case "SettingsIoError":
|
|
33
|
+
return new StepFailure({
|
|
34
|
+
category: "validation",
|
|
35
|
+
detail: `Workspace settings at ${error.path} could not be read`,
|
|
36
|
+
suggestions: [
|
|
37
|
+
{
|
|
38
|
+
description: "Repair the settings file permissions or restore the file, then re-run.",
|
|
39
|
+
},
|
|
40
|
+
],
|
|
41
|
+
cause: error,
|
|
42
|
+
});
|
|
43
|
+
case "LockfileIoError":
|
|
44
|
+
case "LockfileParseError":
|
|
45
|
+
case "LockfileDecodeError":
|
|
46
|
+
return new StepFailure({
|
|
47
|
+
category: "validation",
|
|
48
|
+
detail: `Failed to read the workspace lockfile. Fix the file's permissions or restore it from version control, then rerun.`,
|
|
49
|
+
cause: error,
|
|
50
|
+
});
|
|
51
|
+
case "WorkspaceRootEscape":
|
|
52
|
+
return new StepFailure({
|
|
53
|
+
category: "internal",
|
|
54
|
+
detail: `Failed to read workspace workspace`,
|
|
55
|
+
cause: error,
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
};
|
|
59
|
+
/**
|
|
60
|
+
* Translate a transaction-machinery failure, reproducing each step's detail.
|
|
61
|
+
* A `StepFailure` passes through unchanged: producers inside the transition
|
|
62
|
+
* already speak the serialized vocabulary.
|
|
63
|
+
*/
|
|
64
|
+
export const workspaceTransactionFailureToStepFailure = (failure) => {
|
|
65
|
+
if (failure instanceof StepFailure)
|
|
66
|
+
return failure;
|
|
67
|
+
switch (failure._tag) {
|
|
68
|
+
case "WorkspaceSnapshotError": {
|
|
69
|
+
const detail = () => {
|
|
70
|
+
switch (failure.step) {
|
|
71
|
+
case "inspect-target":
|
|
72
|
+
return `Failed to inspect transaction target ${failure.target}`;
|
|
73
|
+
case "create-store":
|
|
74
|
+
return "Failed to create the rollback snapshot directory";
|
|
75
|
+
case "copy":
|
|
76
|
+
return `Failed to snapshot transaction target ${failure.target}`;
|
|
77
|
+
case "inspect-ancestor":
|
|
78
|
+
return `Failed to inspect transaction ancestor ${failure.target}`;
|
|
79
|
+
}
|
|
80
|
+
};
|
|
81
|
+
return new StepFailure({ category: "internal", detail: detail(), cause: failure.cause });
|
|
82
|
+
}
|
|
83
|
+
case "WorkspaceDirectoryError":
|
|
84
|
+
return new StepFailure({
|
|
85
|
+
category: "internal",
|
|
86
|
+
detail: failure.step === "inspect"
|
|
87
|
+
? `Failed to inspect workspace state directory ${failure.path}`
|
|
88
|
+
: `Failed to create workspace state directory ${failure.path}`,
|
|
89
|
+
cause: failure.cause,
|
|
90
|
+
});
|
|
91
|
+
case "TransitionLockError": {
|
|
92
|
+
const detail = () => {
|
|
93
|
+
switch (failure.step) {
|
|
94
|
+
case "create-scratch":
|
|
95
|
+
return `Failed to create workspace scratch directory ${failure.path}`;
|
|
96
|
+
case "acquire":
|
|
97
|
+
return `Failed to acquire the workspace transition lock at ${failure.path}`;
|
|
98
|
+
case "record-holder":
|
|
99
|
+
return `Failed to record the workspace transition holder at ${failure.path}`;
|
|
100
|
+
case "inspect-timestamp":
|
|
101
|
+
return `Failed to inspect the workspace transition lock timestamp at ${failure.path}`;
|
|
102
|
+
case "missing-timestamp":
|
|
103
|
+
return `Workspace transition lock at ${failure.path} has no modification time`;
|
|
104
|
+
case "preserve-timestamp":
|
|
105
|
+
return `Failed to preserve the workspace transition lock timestamp at ${failure.path}`;
|
|
106
|
+
case "release":
|
|
107
|
+
return `Failed to release workspace transition lock at ${failure.path}`;
|
|
108
|
+
}
|
|
109
|
+
};
|
|
110
|
+
return new StepFailure({ category: "internal", detail: detail(), cause: failure.cause });
|
|
111
|
+
}
|
|
112
|
+
case "TransitionLockUnavailable":
|
|
113
|
+
return new StepFailure({
|
|
114
|
+
category: "conflict",
|
|
115
|
+
detail: `another operation holds the workspace transition${failure.holder === undefined
|
|
116
|
+
? ""
|
|
117
|
+
: ` (${failure.holder.command} (pid ${failure.holder.pid}))`}; waited ${Math.round(failure.waitedMillis / 1000)}s`,
|
|
118
|
+
});
|
|
119
|
+
case "WorkspaceTransitionCompromised":
|
|
120
|
+
return new StepFailure({
|
|
121
|
+
category: "conflict",
|
|
122
|
+
detail: `The workspace transition at ${failure.lockPath} was compromised; the operation stopped.`,
|
|
123
|
+
cause: failure.cause,
|
|
124
|
+
});
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
/** Translate an execution-material fingerprint failure. */
|
|
128
|
+
export const candidateFingerprintFailedToStepFailure = (error) => new StepFailure({
|
|
129
|
+
category: "internal",
|
|
130
|
+
detail: `Failed to fingerprint execution material at ${error.target}`,
|
|
131
|
+
cause: error.cause,
|
|
132
|
+
});
|
|
133
|
+
/**
|
|
134
|
+
* Translate a provider failure: the implementation chose the category and
|
|
135
|
+
* wording at construction, so the fields carry over 1:1.
|
|
136
|
+
*/
|
|
137
|
+
export const configuredAgentOutcomesUnavailableToStepFailure = (error) => new StepFailure({
|
|
138
|
+
category: error.category,
|
|
139
|
+
detail: error.detail,
|
|
140
|
+
...(error.suggestions === undefined ? {} : { suggestions: error.suggestions }),
|
|
141
|
+
...(error.cause === undefined ? {} : { cause: error.cause }),
|
|
142
|
+
});
|
|
143
|
+
/** Render the first deciding line of a transition cause for the boundary text. */
|
|
144
|
+
const firstCauseLine = (cause) => {
|
|
145
|
+
const failure = Option.getOrUndefined(Cause.findErrorOption(cause));
|
|
146
|
+
if (failure instanceof StepFailure)
|
|
147
|
+
return failure.detail;
|
|
148
|
+
if (failure instanceof StaleExecutionCandidate)
|
|
149
|
+
return STALE_CANDIDATE_DETAIL;
|
|
150
|
+
return Cause.pretty(cause).split(/\r?\n/, 1)[0]?.trim() || "The transition did not complete";
|
|
151
|
+
};
|
|
152
|
+
const sentence = (text) => (/[.!?]$/.test(text) ? text : `${text}.`);
|
|
153
|
+
/** Render the deciding transition cause before restoration consequences. */
|
|
154
|
+
const transitionFailureText = (error) => error.terminationCause === "interruption"
|
|
155
|
+
? "Transition was interrupted."
|
|
156
|
+
: `Transition failed: ${sentence(firstCauseLine(error.transitionCause))}`;
|
|
157
|
+
/**
|
|
158
|
+
* Render the typed restoration failure: the deciding transition cause, the
|
|
159
|
+
* retained-state consequence, and the preserved snapshot directory when one
|
|
160
|
+
* exists.
|
|
161
|
+
*/
|
|
162
|
+
export const restorationIncompleteToStepFailure = (error) => new StepFailure({
|
|
163
|
+
category: "conflict",
|
|
164
|
+
detail: `${transitionFailureText(error)} Workspace restoration did not complete; the affected paths keep the state the failure left${error.snapshotDir === undefined
|
|
165
|
+
? "."
|
|
166
|
+
: `, and their pre-change snapshots are preserved at ${error.snapshotDir}.`}`,
|
|
167
|
+
suggestions: [
|
|
168
|
+
{
|
|
169
|
+
description: "Re-run the command; the next mutation plans from the current workspace state.",
|
|
170
|
+
},
|
|
171
|
+
],
|
|
172
|
+
cause: {
|
|
173
|
+
transition: Cause.pretty(error.transitionCause),
|
|
174
|
+
restoration: error.restorationCause,
|
|
175
|
+
},
|
|
176
|
+
});
|
|
177
|
+
//# sourceMappingURL=step-failure-conversions.js.map
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @agentxm/workspace-operations deterministic test layers.
|
|
3
|
+
*
|
|
4
|
+
* In-memory implementations of this package's own ports for tests and
|
|
5
|
+
* executable specifications. Production source never imports this module.
|
|
6
|
+
*
|
|
7
|
+
* @experimental This API is unstable and may change without notice.
|
|
8
|
+
* @packageDocumentation
|
|
9
|
+
*/
|
|
10
|
+
export { ResolvePlanInteractionTest, type ResolvePlanInteractionTestState, } from "./plan/resolve-plan-interaction.js";
|
|
11
|
+
//# sourceMappingURL=testing.d.ts.map
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @agentxm/workspace-operations deterministic test layers.
|
|
3
|
+
*
|
|
4
|
+
* In-memory implementations of this package's own ports for tests and
|
|
5
|
+
* executable specifications. Production source never imports this module.
|
|
6
|
+
*
|
|
7
|
+
* @experimental This API is unstable and may change without notice.
|
|
8
|
+
* @packageDocumentation
|
|
9
|
+
*/
|
|
10
|
+
export { ResolvePlanInteractionTest, } from "./plan/resolve-plan-interaction.js";
|
|
11
|
+
//# sourceMappingURL=testing.js.map
|
package/package.json
ADDED
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@agentxm/workspace-operations",
|
|
3
|
+
"version": "0.28.4-bootstrap.0",
|
|
4
|
+
"description": "AXM workspace operations kernel: plans, execution candidates, operation resolutions, and workspace transactions for the axm CLI. Unstable and unsupported — use the axm.sh CLI.",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"license": "FSL-1.1-MIT",
|
|
7
|
+
"homepage": "https://axm.sh",
|
|
8
|
+
"bugs": {
|
|
9
|
+
"url": "https://github.com/agentxm/axm/issues"
|
|
10
|
+
},
|
|
11
|
+
"author": "AgentXM <hello@agentxm.ai> (https://agentxm.ai)",
|
|
12
|
+
"repository": {
|
|
13
|
+
"type": "git",
|
|
14
|
+
"url": "https://github.com/agentxm/axm.git",
|
|
15
|
+
"directory": "packages/workspace-operations"
|
|
16
|
+
},
|
|
17
|
+
"sideEffects": false,
|
|
18
|
+
"exports": {
|
|
19
|
+
".": {
|
|
20
|
+
"types": "./dist/src/index.d.ts",
|
|
21
|
+
"default": "./dist/src/index.js"
|
|
22
|
+
},
|
|
23
|
+
"./live": {
|
|
24
|
+
"types": "./dist/src/live.d.ts",
|
|
25
|
+
"default": "./dist/src/live.js"
|
|
26
|
+
},
|
|
27
|
+
"./testing": {
|
|
28
|
+
"types": "./dist/src/testing.d.ts",
|
|
29
|
+
"default": "./dist/src/testing.js"
|
|
30
|
+
}
|
|
31
|
+
},
|
|
32
|
+
"files": [
|
|
33
|
+
"dist/src/",
|
|
34
|
+
"!**/*.map"
|
|
35
|
+
],
|
|
36
|
+
"publishConfig": {
|
|
37
|
+
"access": "public"
|
|
38
|
+
},
|
|
39
|
+
"engines": {
|
|
40
|
+
"node": ">=22.19.0"
|
|
41
|
+
},
|
|
42
|
+
"nx": {
|
|
43
|
+
"includedScripts": []
|
|
44
|
+
},
|
|
45
|
+
"dependencies": {
|
|
46
|
+
"effect": "4.0.0-rc.112",
|
|
47
|
+
"proper-lockfile": "^4.1.2",
|
|
48
|
+
"@agentxm/workspace-state": "^0.28.4-bootstrap.0",
|
|
49
|
+
"@agentxm/registry-protocol": "^0.28.4-bootstrap.0",
|
|
50
|
+
"@agentxm/extension-model": "^0.28.4-bootstrap.0"
|
|
51
|
+
},
|
|
52
|
+
"devDependencies": {
|
|
53
|
+
"@effect/platform-node": "4.0.0-rc.112",
|
|
54
|
+
"@effect/vitest": "4.0.0-rc.112",
|
|
55
|
+
"@types/proper-lockfile": "^4.1.4",
|
|
56
|
+
"@typescript/native": "npm:typescript@^7.0.2",
|
|
57
|
+
"typescript": "npm:@typescript/typescript6@^6.0.2",
|
|
58
|
+
"vitest": "^4.1.10",
|
|
59
|
+
"yaml": "^2.9.0"
|
|
60
|
+
}
|
|
61
|
+
}
|