@hyperdreamer/pi-webui 1.15.2 → 1.16.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 (62) hide show
  1. package/dist/client/assets/{CodeViewer-CHZziPur.js → CodeViewer-CCHq9DpL.js} +1 -1
  2. package/dist/client/assets/{UnifiedDiffViewer-j1-AFZ8f.js → UnifiedDiffViewer-JFQMCnzP.js} +1 -1
  3. package/dist/client/assets/{index-2RMTbgnM.js → index-WjewjFVt.js} +469 -469
  4. package/dist/client/index.html +1 -1
  5. package/dist/config.js +10 -0
  6. package/dist/config.js.map +1 -1
  7. package/dist/configMutationCoordinator.js +10 -1
  8. package/dist/configMutationCoordinator.js.map +1 -1
  9. package/dist/pi-webui-plugins/workspace-tasks/config.js +3 -132
  10. package/dist/pi-webui-plugins/workspace-tasks/pi-webui-plugin.js +14 -2
  11. package/dist/pi-webui-plugins/workspace-tasks/taskDomain.js +203 -0
  12. package/dist/pi-webui-plugins/workspace-tasks/taskRunner.js +3 -2
  13. package/dist/pi-webui-plugins/workspace-tasks/tasksPanelElement.js +947 -673
  14. package/dist/server/app.js +20 -4
  15. package/dist/server/app.js.map +1 -1
  16. package/dist/server/configRoutes.js +5 -0
  17. package/dist/server/configRoutes.js.map +1 -1
  18. package/dist/server/machines/machineProxyRoutes.js +4 -4
  19. package/dist/server/machines/machineProxyRoutes.js.map +1 -1
  20. package/dist/server/workspaceExplorerRoutes.js +64 -4
  21. package/dist/server/workspaceExplorerRoutes.js.map +1 -1
  22. package/dist/server/workspaceTasks/workspaceTasksCatalogService.js +318 -0
  23. package/dist/server/workspaceTasks/workspaceTasksCatalogService.js.map +1 -0
  24. package/dist/server/workspaceTasks/workspaceTasksComposition.js +67 -0
  25. package/dist/server/workspaceTasks/workspaceTasksComposition.js.map +1 -0
  26. package/dist/server/workspaceTasks/workspaceTasksErrors.js +34 -0
  27. package/dist/server/workspaceTasks/workspaceTasksErrors.js.map +1 -0
  28. package/dist/server/workspaceTasks/workspaceTasksGlobalCatalogAdapter.js +169 -0
  29. package/dist/server/workspaceTasks/workspaceTasksGlobalCatalogAdapter.js.map +1 -0
  30. package/dist/server/workspaceTasks/workspaceTasksGlobalMutationGate.js +75 -0
  31. package/dist/server/workspaceTasks/workspaceTasksGlobalMutationGate.js.map +1 -0
  32. package/dist/server/workspaceTasks/workspaceTasksMoveProtocol.js +313 -0
  33. package/dist/server/workspaceTasks/workspaceTasksMoveProtocol.js.map +1 -0
  34. package/dist/server/workspaceTasks/workspaceTasksMoveRegistry.js +352 -0
  35. package/dist/server/workspaceTasks/workspaceTasksMoveRegistry.js.map +1 -0
  36. package/dist/server/workspaceTasks/workspaceTasksProxyRoutes.js +63 -0
  37. package/dist/server/workspaceTasks/workspaceTasksProxyRoutes.js.map +1 -0
  38. package/dist/server/workspaceTasks/workspaceTasksRoutes.js +153 -0
  39. package/dist/server/workspaceTasks/workspaceTasksRoutes.js.map +1 -0
  40. package/dist/server/workspaceTasks/workspaceTasksWorkspaceCatalogAdapter.js +171 -0
  41. package/dist/server/workspaceTasks/workspaceTasksWorkspaceCatalogAdapter.js.map +1 -0
  42. package/dist/server/workspaceTasks/workspaceTasksWorkspaceFile.js +227 -0
  43. package/dist/server/workspaceTasks/workspaceTasksWorkspaceFile.js.map +1 -0
  44. package/dist/server/workspaceTasks/workspaceTasksWorkspacePathGate.js +42 -0
  45. package/dist/server/workspaceTasks/workspaceTasksWorkspacePathGate.js.map +1 -0
  46. package/dist/server/workspaces/fileContentService.js +116 -6
  47. package/dist/server/workspaces/fileContentService.js.map +1 -1
  48. package/dist/shared/apiTypes.d.ts +132 -0
  49. package/dist/shared/apiTypes.js.map +1 -1
  50. package/dist/shared/federatedRoutes.js +15 -0
  51. package/dist/shared/federatedRoutes.js.map +1 -1
  52. package/dist/shared/workspaceFiles.js +2 -0
  53. package/dist/shared/workspaceFiles.js.map +1 -1
  54. package/dist/shared/workspaceTasks.d.ts +53 -0
  55. package/dist/shared/workspaceTasks.js +203 -0
  56. package/dist/shared/workspaceTasks.js.map +1 -0
  57. package/dist/shared/workspaceTasksApi.js +379 -0
  58. package/dist/shared/workspaceTasksApi.js.map +1 -0
  59. package/docs/config.md +22 -4
  60. package/docs/plugins.md +24 -13
  61. package/package.json +1 -1
  62. package/dist/pi-webui-plugins/workspace-tasks/workspaceTasksClient.js +0 -242
@@ -1,242 +0,0 @@
1
- // Generated from pi-webui-plugins/workspace-tasks/workspaceTasksClient.ts. Do not edit directly.
2
- import { TASKS_CONFIG_PATH, parseTasksConfigText, serializeWorkspaceTasksConfig, } from "./config.js";
3
- export const tasksConfigMissingMessage = "No workspace tasks configured here.";
4
- export const tasksConfigMissingHint = `${TASKS_CONFIG_PATH} is optional. Create it in this workspace if you want custom tasks.`;
5
- export const tasksConfigInvalidMessage = "Workspace tasks configuration is invalid.";
6
- export const tasksConfigInvalidHint = `Fix ${TASKS_CONFIG_PATH}, then click Refresh.`;
7
- export const tasksConfigUnavailableMessage = "Could not load workspace tasks.";
8
- export const tasksConfigRefreshHint = `Fix ${TASKS_CONFIG_PATH}, then click Refresh.`;
9
- const configCache = new Map();
10
- const workspaceRuntimes = new Map();
11
- const subscribers = new Set();
12
- let stateEpoch = 0;
13
- export function loadWorkspaceTasksConfig(files) {
14
- return readCurrentWorkspaceTasksConfig(files);
15
- }
16
- export function getWorkspaceTasksCacheEntry(workspaceKey) {
17
- return configCache.get(workspaceKey);
18
- }
19
- export function ensureWorkspaceTasksConfig(files, workspaceKey) {
20
- const cached = configCache.get(workspaceKey);
21
- if (cached !== undefined)
22
- return cached;
23
- const runtime = getWorkspaceRuntime(workspaceKey);
24
- const loadingEntry = {
25
- state: { kind: "loading" },
26
- refreshRequired: runtime.refreshRequired,
27
- };
28
- configCache.set(workspaceKey, loadingEntry);
29
- void enqueueWorkspaceOperation(workspaceKey, async (operation) => {
30
- const state = await loadWorkspaceTasksConfigSafely(files);
31
- if (state.kind === "unavailable")
32
- operation.runtime.refreshRequired = true;
33
- publishState(operation, state, operation.runtime.refreshRequired);
34
- }).catch(() => undefined);
35
- return loadingEntry;
36
- }
37
- export function refreshWorkspaceTasksConfig(files, workspaceKey) {
38
- return enqueueWorkspaceOperation(workspaceKey, async (operation) => {
39
- const state = await loadWorkspaceTasksConfigSafely(files);
40
- operation.runtime.refreshRequired = state.kind === "unavailable";
41
- publishState(operation, state, operation.runtime.refreshRequired);
42
- return state;
43
- }, (operation) => {
44
- if (!isCurrentOperation(operation))
45
- return;
46
- configCache.set(workspaceKey, {
47
- state: { kind: "loading" },
48
- refreshRequired: operation.runtime.refreshRequired,
49
- });
50
- });
51
- }
52
- export function guardedWriteWorkspaceTasksConfig(files, workspaceKey, sourceSnapshot, nextConfig) {
53
- return enqueueWorkspaceOperation(workspaceKey, async (operation) => {
54
- if (operation.runtime.refreshRequired) {
55
- return blockMutation(operation, "A successful Refresh is required before another workspace task mutation.");
56
- }
57
- const preflight = await loadWorkspaceTasksConfigSafely(files);
58
- if (preflight.kind === "unavailable") {
59
- return blockMutation(operation, unavailableDetail(preflight));
60
- }
61
- const currentSnapshot = preflight.snapshot;
62
- if (!snapshotsEqual(sourceSnapshot, currentSnapshot)) {
63
- return blockMutation(operation, `The ${TASKS_CONFIG_PATH} file changed outside this panel. Refresh before trying again.`, "conflict");
64
- }
65
- const payload = serializeWorkspaceTasksConfig(nextConfig);
66
- try {
67
- await files.writeFile(TASKS_CONFIG_PATH, payload);
68
- }
69
- catch (error) {
70
- return blockMutation(operation, `Unable to write ${TASKS_CONFIG_PATH}: ${formatUnknownError(error)}`, "write-failed");
71
- }
72
- const postWrite = await loadWorkspaceTasksConfigSafely(files);
73
- if (postWrite.kind === "loaded" && postWrite.snapshot.content === payload) {
74
- operation.runtime.refreshRequired = false;
75
- publishState(operation, postWrite, false);
76
- return { kind: "written", state: postWrite };
77
- }
78
- const detail = postWriteReloadDetail(postWrite);
79
- blockMutation(operation, detail, undefined, postWrite);
80
- return { kind: "written-but-unreloaded", detail };
81
- });
82
- }
83
- export function subscribeWorkspaceTasksConfig(listener) {
84
- subscribers.add(listener);
85
- return () => {
86
- subscribers.delete(listener);
87
- };
88
- }
89
- export function clearWorkspaceTasksStateForTesting() {
90
- stateEpoch += 1;
91
- configCache.clear();
92
- workspaceRuntimes.clear();
93
- }
94
- async function readCurrentWorkspaceTasksConfig(files) {
95
- let file;
96
- try {
97
- file = await files.readFile(TASKS_CONFIG_PATH);
98
- }
99
- catch (error) {
100
- if (isMissingWorkspaceFileError(error))
101
- return missing();
102
- return unavailable(`Unable to read ${TASKS_CONFIG_PATH}: ${formatUnknownError(error)}`);
103
- }
104
- if (file.binary)
105
- return unavailable(`${TASKS_CONFIG_PATH} must be a text file`);
106
- if (file.truncated)
107
- return unavailable(`${TASKS_CONFIG_PATH} is too large and was truncated`);
108
- const result = parseTasksConfigText(file.content);
109
- if (!result.ok) {
110
- return {
111
- kind: "invalid",
112
- message: tasksConfigInvalidMessage,
113
- hint: tasksConfigInvalidHint,
114
- detail: result.error,
115
- snapshot: { kind: "text", content: file.content },
116
- };
117
- }
118
- return {
119
- kind: "loaded",
120
- config: result.config,
121
- path: TASKS_CONFIG_PATH,
122
- snapshot: { kind: "text", content: file.content },
123
- };
124
- }
125
- async function loadWorkspaceTasksConfigSafely(files) {
126
- try {
127
- return await readCurrentWorkspaceTasksConfig(files);
128
- }
129
- catch (error) {
130
- return unavailable(`Unable to read ${TASKS_CONFIG_PATH}: ${formatUnknownError(error)}`);
131
- }
132
- }
133
- function enqueueWorkspaceOperation(workspaceKey, operation, onRequest) {
134
- const runtime = getWorkspaceRuntime(workspaceKey);
135
- const context = {
136
- key: workspaceKey,
137
- runtime,
138
- generation: runtime.requestGeneration + 1,
139
- epoch: stateEpoch,
140
- };
141
- runtime.requestGeneration = context.generation;
142
- onRequest?.(context);
143
- const result = runtime.tail.then(() => operation(context));
144
- runtime.tail = result.then(() => undefined, () => undefined);
145
- return result;
146
- }
147
- function getWorkspaceRuntime(workspaceKey) {
148
- const existing = workspaceRuntimes.get(workspaceKey);
149
- if (existing !== undefined)
150
- return existing;
151
- const runtime = {
152
- requestGeneration: 0,
153
- refreshRequired: false,
154
- tail: Promise.resolve(),
155
- };
156
- workspaceRuntimes.set(workspaceKey, runtime);
157
- return runtime;
158
- }
159
- function publishState(operation, state, refreshRequired) {
160
- if (!isCurrentOperation(operation))
161
- return;
162
- configCache.set(operation.key, { state, refreshRequired });
163
- notifySubscribers(operation.key);
164
- }
165
- function blockMutation(operation, detail, kind = "preflight-unavailable", postWriteState) {
166
- operation.runtime.refreshRequired = true;
167
- if (isCurrentOperation(operation)) {
168
- const existing = configCache.get(operation.key);
169
- if (postWriteState !== undefined) {
170
- configCache.set(operation.key, { state: postWriteState, refreshRequired: true });
171
- }
172
- else if (existing !== undefined) {
173
- configCache.set(operation.key, { ...existing, refreshRequired: true });
174
- }
175
- notifySubscribers(operation.key);
176
- }
177
- return { kind, detail };
178
- }
179
- function isCurrentOperation(operation) {
180
- return operation.epoch === stateEpoch
181
- && workspaceRuntimes.get(operation.key) === operation.runtime
182
- && operation.runtime.requestGeneration === operation.generation;
183
- }
184
- function notifySubscribers(workspaceKey) {
185
- for (const listener of subscribers)
186
- listener(workspaceKey);
187
- }
188
- function snapshotsEqual(left, right) {
189
- if (left.kind !== right.kind)
190
- return false;
191
- if (left.kind === "missing" || right.kind === "missing")
192
- return true;
193
- return left.content === right.content;
194
- }
195
- function postWriteReloadDetail(result) {
196
- if (result.kind === "loaded")
197
- return `Unable to reload ${TASKS_CONFIG_PATH}: the post-write snapshot did not match the canonical payload.`;
198
- if (result.kind === "missing")
199
- return `Unable to reload ${TASKS_CONFIG_PATH}: the file is missing after the write.`;
200
- if (result.kind === "invalid")
201
- return `Unable to reload ${TASKS_CONFIG_PATH}: ${result.detail}`;
202
- return `Unable to reload ${TASKS_CONFIG_PATH}: ${unavailableDetail(result)}`;
203
- }
204
- function missing() {
205
- return {
206
- kind: "missing",
207
- message: tasksConfigMissingMessage,
208
- hint: tasksConfigMissingHint,
209
- snapshot: { kind: "missing" },
210
- };
211
- }
212
- function unavailable(detail) {
213
- return {
214
- kind: "unavailable",
215
- message: tasksConfigUnavailableMessage,
216
- hint: tasksConfigRefreshHint,
217
- detail,
218
- };
219
- }
220
- function unavailableDetail(result) {
221
- return result.detail ?? tasksConfigUnavailableMessage;
222
- }
223
- function isMissingWorkspaceFileError(error) {
224
- const message = errorField(error, "message");
225
- const code = errorField(error, "code");
226
- return message === "Path does not exist"
227
- || code?.toLowerCase() === "enoent"
228
- || message?.toLowerCase() === "enoent"
229
- || message?.toLowerCase().includes("no such file or directory") === true
230
- || code?.toLowerCase().includes("no such file or directory") === true;
231
- }
232
- function errorField(error, field) {
233
- if (typeof error === "object" && error !== null && hasStringField(error, field))
234
- return error[field];
235
- return error instanceof Error && field === "message" ? error.message : undefined;
236
- }
237
- function hasStringField(value, field) {
238
- return field in value && typeof Reflect.get(value, field) === "string";
239
- }
240
- function formatUnknownError(error) {
241
- return error instanceof Error ? error.message : String(error);
242
- }