@h-rig/cli 0.0.6-alpha.80 → 0.0.6-alpha.81
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/bin/rig.js +17034 -11249
- package/dist/src/app/board.js +32 -3
- package/dist/src/app/drone-ui.js +1 -1
- package/dist/src/app/theme.js +1 -0
- package/dist/src/app-opentui/adapters/common.d.ts +53 -0
- package/dist/src/app-opentui/adapters/common.js +149 -0
- package/dist/src/app-opentui/adapters/doctor.d.ts +11 -0
- package/dist/src/app-opentui/adapters/doctor.js +780 -0
- package/dist/src/app-opentui/adapters/fleet.d.ts +16 -0
- package/dist/src/app-opentui/adapters/fleet.js +874 -0
- package/dist/src/app-opentui/adapters/inbox.d.ts +33 -0
- package/dist/src/app-opentui/adapters/inbox.js +1454 -0
- package/dist/src/app-opentui/adapters/init.d.ts +13 -0
- package/dist/src/app-opentui/adapters/init.js +2357 -0
- package/dist/src/app-opentui/adapters/pi-attach.d.ts +16 -0
- package/dist/src/app-opentui/adapters/pi-attach.js +1295 -0
- package/dist/src/app-opentui/adapters/run-detail.d.ts +20 -0
- package/dist/src/app-opentui/adapters/run-detail.js +893 -0
- package/dist/src/app-opentui/adapters/server.d.ts +14 -0
- package/dist/src/app-opentui/adapters/server.js +798 -0
- package/dist/src/app-opentui/adapters/tasks.d.ts +55 -0
- package/dist/src/app-opentui/adapters/tasks.js +3472 -0
- package/dist/src/app-opentui/bootstrap.d.ts +16 -0
- package/dist/src/app-opentui/bootstrap.js +19509 -0
- package/dist/src/app-opentui/drone.d.ts +12 -0
- package/dist/src/app-opentui/drone.js +227 -0
- package/dist/src/app-opentui/events.d.ts +7 -0
- package/dist/src/app-opentui/events.js +28 -0
- package/dist/src/app-opentui/index.d.ts +8 -0
- package/dist/src/app-opentui/index.js +3477 -0
- package/dist/src/app-opentui/intent.d.ts +3 -0
- package/dist/src/app-opentui/intent.js +211 -0
- package/dist/src/app-opentui/layout.d.ts +15 -0
- package/dist/src/app-opentui/layout.js +44 -0
- package/dist/src/app-opentui/list-search.d.ts +8 -0
- package/dist/src/app-opentui/list-search.js +43 -0
- package/dist/src/app-opentui/pi-host-child.d.ts +2 -0
- package/dist/src/app-opentui/pi-host-child.js +778 -0
- package/dist/src/app-opentui/pi-pty-host.d.ts +64 -0
- package/dist/src/app-opentui/pi-pty-host.js +384 -0
- package/dist/src/app-opentui/registry.d.ts +4 -0
- package/dist/src/app-opentui/registry.js +6835 -0
- package/dist/src/app-opentui/render/graphics.d.ts +39 -0
- package/dist/src/app-opentui/render/graphics.js +537 -0
- package/dist/src/app-opentui/render/image-visual-layer-native-canvas.d.ts +2 -0
- package/dist/src/app-opentui/render/image-visual-layer-native-canvas.js +1480 -0
- package/dist/src/app-opentui/render/image-visual-layer-worker.d.ts +1 -0
- package/dist/src/app-opentui/render/image-visual-layer-worker.js +1541 -0
- package/dist/src/app-opentui/render/image-visual-layer.d.ts +93 -0
- package/dist/src/app-opentui/render/image-visual-layer.js +945 -0
- package/dist/src/app-opentui/render/panels.d.ts +10 -0
- package/dist/src/app-opentui/render/panels.js +201 -0
- package/dist/src/app-opentui/render/scene.d.ts +16 -0
- package/dist/src/app-opentui/render/scene.js +110 -0
- package/dist/src/app-opentui/render/text.d.ts +10 -0
- package/dist/src/app-opentui/render/text.js +121 -0
- package/dist/src/app-opentui/render/type-bar.d.ts +14 -0
- package/dist/src/app-opentui/render/type-bar.js +137 -0
- package/dist/src/app-opentui/runtime.d.ts +2 -0
- package/dist/src/app-opentui/runtime.js +3406 -0
- package/dist/src/app-opentui/scenes/doctor.d.ts +2 -0
- package/dist/src/app-opentui/scenes/doctor.js +91 -0
- package/dist/src/app-opentui/scenes/error.d.ts +2 -0
- package/dist/src/app-opentui/scenes/error.js +190 -0
- package/dist/src/app-opentui/scenes/fleet.d.ts +3 -0
- package/dist/src/app-opentui/scenes/fleet.js +207 -0
- package/dist/src/app-opentui/scenes/handoff.d.ts +2 -0
- package/dist/src/app-opentui/scenes/handoff.js +147 -0
- package/dist/src/app-opentui/scenes/help.d.ts +3 -0
- package/dist/src/app-opentui/scenes/help.js +138 -0
- package/dist/src/app-opentui/scenes/inbox.d.ts +2 -0
- package/dist/src/app-opentui/scenes/inbox.js +118 -0
- package/dist/src/app-opentui/scenes/init.d.ts +2 -0
- package/dist/src/app-opentui/scenes/init.js +94 -0
- package/dist/src/app-opentui/scenes/main.d.ts +2 -0
- package/dist/src/app-opentui/scenes/main.js +96 -0
- package/dist/src/app-opentui/scenes/run-detail.d.ts +2 -0
- package/dist/src/app-opentui/scenes/run-detail.js +139 -0
- package/dist/src/app-opentui/scenes/server.d.ts +2 -0
- package/dist/src/app-opentui/scenes/server.js +88 -0
- package/dist/src/app-opentui/scenes/tasks.d.ts +3 -0
- package/dist/src/app-opentui/scenes/tasks.js +230 -0
- package/dist/src/app-opentui/state.d.ts +4 -0
- package/dist/src/app-opentui/state.js +286 -0
- package/dist/src/app-opentui/theme.d.ts +36 -0
- package/dist/src/app-opentui/theme.js +88 -0
- package/dist/src/app-opentui/types.d.ts +188 -0
- package/dist/src/app-opentui/types.js +1 -0
- package/dist/src/commands/_async-ui.js +1 -1
- package/dist/src/commands/_operator-view.js +1 -1
- package/dist/src/commands/_pi-frontend.js +1 -1
- package/dist/src/commands/_spinner.js +1 -1
- package/dist/src/commands/browser.js +1 -1
- package/dist/src/commands/doctor.js +1 -1
- package/dist/src/commands/github.js +1 -1
- package/dist/src/commands/inbox.js +1 -1
- package/dist/src/commands/init.js +1 -1
- package/dist/src/commands/inspect.js +1 -1
- package/dist/src/commands/run.js +1 -1
- package/dist/src/commands/setup.js +1 -1
- package/dist/src/commands/stats.js +1 -1
- package/dist/src/commands/task.js +1 -1
- package/dist/src/commands.js +33 -4
- package/dist/src/index.js +33 -4
- package/package.json +11 -8
package/dist/src/app/board.js
CHANGED
|
@@ -50,6 +50,7 @@ function statusColor(status) {
|
|
|
50
50
|
case "validating":
|
|
51
51
|
case "reviewing":
|
|
52
52
|
case "closing-out":
|
|
53
|
+
case "stopping":
|
|
53
54
|
return cyan;
|
|
54
55
|
case "needs-attention":
|
|
55
56
|
case "needs_attention":
|
|
@@ -951,7 +952,7 @@ async function loadTaskRunProjectDefaults(projectRoot) {
|
|
|
951
952
|
|
|
952
953
|
// packages/cli/src/app/board.ts
|
|
953
954
|
var BOARD_REFRESH_MS = 5000;
|
|
954
|
-
var BOARD_TICK_MS =
|
|
955
|
+
var BOARD_TICK_MS = 16;
|
|
955
956
|
var BOARD_TASK_PAGE = 20;
|
|
956
957
|
function oneLine(message) {
|
|
957
958
|
return message.split(`
|
|
@@ -974,6 +975,7 @@ function statusRank(status) {
|
|
|
974
975
|
case "pending":
|
|
975
976
|
case "preparing":
|
|
976
977
|
case "adopted":
|
|
978
|
+
case "stopping":
|
|
977
979
|
return 2;
|
|
978
980
|
case "completed":
|
|
979
981
|
case "merged":
|
|
@@ -1013,6 +1015,10 @@ class RunsList {
|
|
|
1013
1015
|
selectedRun() {
|
|
1014
1016
|
return this.visibleRuns()[this.selected] ?? null;
|
|
1015
1017
|
}
|
|
1018
|
+
patchRun(runId, patch) {
|
|
1019
|
+
this.runs = this.runs.map((run) => run.runId === runId ? { ...run, ...patch } : run);
|
|
1020
|
+
this.clampSelection();
|
|
1021
|
+
}
|
|
1016
1022
|
cycleSort() {
|
|
1017
1023
|
this.sortMode = this.sortMode === "active" ? "recent" : this.sortMode === "recent" ? "status" : "active";
|
|
1018
1024
|
this.clampSelection();
|
|
@@ -1235,6 +1241,14 @@ class InboxView {
|
|
|
1235
1241
|
selectedItem() {
|
|
1236
1242
|
return this.items[this.selected] ?? null;
|
|
1237
1243
|
}
|
|
1244
|
+
patchItem(requestId, summary) {
|
|
1245
|
+
this.items = this.items.map((item) => item.requestId === requestId ? { ...item, summary } : item);
|
|
1246
|
+
}
|
|
1247
|
+
removeItem(requestId) {
|
|
1248
|
+
const previousIndex = this.selected;
|
|
1249
|
+
this.items = this.items.filter((item) => item.requestId !== requestId);
|
|
1250
|
+
this.selected = Math.max(0, Math.min(previousIndex, Math.max(0, this.items.length - 1)));
|
|
1251
|
+
}
|
|
1238
1252
|
invalidate() {}
|
|
1239
1253
|
render(width) {
|
|
1240
1254
|
return this.renderLines(width).map((line) => truncateToWidth(line, Math.max(10, width - 1)));
|
|
@@ -1456,9 +1470,14 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1456
1470
|
tui.stop();
|
|
1457
1471
|
};
|
|
1458
1472
|
let refreshInFlight = false;
|
|
1459
|
-
const refresh = async () => {
|
|
1473
|
+
const refresh = async (options2 = {}) => {
|
|
1460
1474
|
if (refreshInFlight)
|
|
1461
1475
|
return;
|
|
1476
|
+
if (!options2.quiet) {
|
|
1477
|
+
notice = "refreshing fleet\u2026";
|
|
1478
|
+
renderFooter();
|
|
1479
|
+
tui.requestRender();
|
|
1480
|
+
}
|
|
1462
1481
|
if (!hasRigProject(context.projectRoot)) {
|
|
1463
1482
|
list.loading = false;
|
|
1464
1483
|
list.noProject = true;
|
|
@@ -1541,6 +1560,7 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1541
1560
|
};
|
|
1542
1561
|
const resolveApproval = async (item, decision) => {
|
|
1543
1562
|
notice = `${decision === "approve" ? "approving" : "rejecting"} ${item.requestId.slice(0, 12)}\u2026`;
|
|
1563
|
+
inboxView.patchItem(item.requestId, `${decision === "approve" ? "approving" : "rejecting"}\u2026 ${item.summary}`);
|
|
1544
1564
|
renderFooter();
|
|
1545
1565
|
tui.requestRender();
|
|
1546
1566
|
try {
|
|
@@ -1549,8 +1569,10 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1549
1569
|
headers: { "content-type": "application/json" },
|
|
1550
1570
|
body: JSON.stringify({ runId: item.runId, requestId: item.requestId, decision, note: null })
|
|
1551
1571
|
});
|
|
1572
|
+
inboxView.removeItem(item.requestId);
|
|
1552
1573
|
notice = `${decision === "approve" ? "approved" : "rejected"} \u2014 drone resumes`;
|
|
1553
1574
|
} catch (error) {
|
|
1575
|
+
inboxView.patchItem(item.requestId, item.summary);
|
|
1554
1576
|
notice = `resolve failed: ${oneLine(error instanceof Error ? error.message : String(error))}`;
|
|
1555
1577
|
}
|
|
1556
1578
|
renderFooter();
|
|
@@ -1559,6 +1581,7 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1559
1581
|
};
|
|
1560
1582
|
const answerInput = async (item, text) => {
|
|
1561
1583
|
notice = `answering ${item.requestId.slice(0, 12)}\u2026`;
|
|
1584
|
+
inboxView.patchItem(item.requestId, `answering\u2026 ${item.summary}`);
|
|
1562
1585
|
renderFooter();
|
|
1563
1586
|
tui.requestRender();
|
|
1564
1587
|
try {
|
|
@@ -1571,8 +1594,10 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1571
1594
|
answers: { [item.questionId ?? "response"]: text }
|
|
1572
1595
|
})
|
|
1573
1596
|
});
|
|
1597
|
+
inboxView.removeItem(item.requestId);
|
|
1574
1598
|
notice = "answer sent \u2014 drone resumes";
|
|
1575
1599
|
} catch (error) {
|
|
1600
|
+
inboxView.patchItem(item.requestId, item.summary);
|
|
1576
1601
|
notice = `answer failed: ${oneLine(error instanceof Error ? error.message : String(error))}`;
|
|
1577
1602
|
}
|
|
1578
1603
|
renderFooter();
|
|
@@ -1721,6 +1746,7 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1721
1746
|
const run = list.selectedRun();
|
|
1722
1747
|
if (run) {
|
|
1723
1748
|
notice = `stop requested for ${run.runId.slice(0, 8)}\u2026`;
|
|
1749
|
+
list.patchRun(run.runId, { status: "stopping" });
|
|
1724
1750
|
renderFooter();
|
|
1725
1751
|
tui.requestRender();
|
|
1726
1752
|
stopRunViaServer(context, run.runId).then(() => refresh()).catch(() => refresh());
|
|
@@ -1728,6 +1754,9 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1728
1754
|
return { consume: true };
|
|
1729
1755
|
}
|
|
1730
1756
|
if (data === "r") {
|
|
1757
|
+
notice = "refreshing fleet\u2026";
|
|
1758
|
+
renderFooter();
|
|
1759
|
+
tui.requestRender();
|
|
1731
1760
|
refresh();
|
|
1732
1761
|
return { consume: true };
|
|
1733
1762
|
}
|
|
@@ -1757,7 +1786,7 @@ async function runOperatorBoard(context, options = {}) {
|
|
|
1757
1786
|
refresh();
|
|
1758
1787
|
}, BOARD_REFRESH_MS);
|
|
1759
1788
|
tui.start();
|
|
1760
|
-
refresh();
|
|
1789
|
+
refresh({ quiet: true });
|
|
1761
1790
|
await new Promise((resolve3) => {
|
|
1762
1791
|
const poll = setInterval(() => {
|
|
1763
1792
|
if (stopped) {
|
package/dist/src/app/drone-ui.js
CHANGED
|
@@ -105,7 +105,7 @@ function createTtySpinner(input) {
|
|
|
105
105
|
output.write("\r\x1B[2K");
|
|
106
106
|
};
|
|
107
107
|
render();
|
|
108
|
-
const timer = isTty ? setInterval(render, input.intervalMs ??
|
|
108
|
+
const timer = isTty ? setInterval(render, input.intervalMs ?? 16) : null;
|
|
109
109
|
return {
|
|
110
110
|
setLabel(next) {
|
|
111
111
|
label = next;
|
package/dist/src/app/theme.js
CHANGED
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import type { RunnerContext } from "../../runner";
|
|
2
|
+
import type { AppEvent, AppIntent, AppRuntime, AppSceneId } from "../types";
|
|
3
|
+
export type AppStateLike = {
|
|
4
|
+
readonly projectRoot?: string;
|
|
5
|
+
readonly scene?: AppSceneId;
|
|
6
|
+
readonly status?: string;
|
|
7
|
+
readonly tick?: number;
|
|
8
|
+
readonly argv?: readonly string[];
|
|
9
|
+
readonly data?: Record<string, unknown>;
|
|
10
|
+
readonly footer?: Record<string, unknown>;
|
|
11
|
+
readonly [key: string]: unknown;
|
|
12
|
+
};
|
|
13
|
+
export type AppAdapterEvent = AppEvent;
|
|
14
|
+
export type AppRendererHandoff = {
|
|
15
|
+
readonly suspend?: () => void | Promise<void>;
|
|
16
|
+
readonly resume?: () => void | Promise<void>;
|
|
17
|
+
readonly destroy?: () => void | Promise<void>;
|
|
18
|
+
};
|
|
19
|
+
export type AppAdapterContext = {
|
|
20
|
+
readonly projectRoot?: string;
|
|
21
|
+
readonly rig?: Pick<RunnerContext, "projectRoot" | "runId" | "outputMode">;
|
|
22
|
+
readonly renderer?: AppRendererHandoff;
|
|
23
|
+
readonly ensureRuntime?: () => Promise<RunnerContext>;
|
|
24
|
+
emit(event: AppAdapterEvent): void;
|
|
25
|
+
getState(): AppStateLike;
|
|
26
|
+
};
|
|
27
|
+
export declare function adapterContextFromRuntime(runtime: AppRuntime, renderer?: AppRendererHandoff): AppAdapterContext;
|
|
28
|
+
export type NormalizedAppError = {
|
|
29
|
+
readonly message: string;
|
|
30
|
+
readonly hint?: string;
|
|
31
|
+
};
|
|
32
|
+
export type CapturedConsole = {
|
|
33
|
+
readonly result: unknown;
|
|
34
|
+
readonly output: readonly string[];
|
|
35
|
+
};
|
|
36
|
+
export declare function projectRootOf(ctx: AppAdapterContext): string;
|
|
37
|
+
export declare function runtimeOf(ctx: AppAdapterContext): Promise<RunnerContext>;
|
|
38
|
+
export declare function normalizeAppError(error: unknown): NormalizedAppError;
|
|
39
|
+
export declare function emitStarted(ctx: AppAdapterContext, label: string, optimistic?: Record<string, unknown>): void;
|
|
40
|
+
export declare function emitProgress(ctx: AppAdapterContext, label: string, detail?: string, data?: Record<string, unknown>): void;
|
|
41
|
+
export declare function emitCompleted(ctx: AppAdapterContext, label: string, data?: Record<string, unknown>): void;
|
|
42
|
+
export declare function emitFailed(ctx: AppAdapterContext, label: string, error: unknown, data?: Record<string, unknown>): void;
|
|
43
|
+
export declare function patchData(ctx: AppAdapterContext, data: Record<string, unknown>): void;
|
|
44
|
+
export declare function patchFooter(ctx: AppAdapterContext, footer: Record<string, unknown>): void;
|
|
45
|
+
export declare function captureConsole<T>(fn: () => Promise<T> | T): Promise<{
|
|
46
|
+
result: T;
|
|
47
|
+
output: readonly string[];
|
|
48
|
+
}>;
|
|
49
|
+
export declare function releaseRendererForExternalTui(ctx: AppAdapterContext): Promise<void>;
|
|
50
|
+
export declare function arrayFromPayload(value: unknown): Record<string, unknown>[];
|
|
51
|
+
export declare function stringField(record: Record<string, unknown>, keys: readonly string[], fallback?: string): string;
|
|
52
|
+
export declare function compactRecord(record: Record<string, unknown>, keys: readonly string[]): Record<string, unknown>;
|
|
53
|
+
export declare function payloadString(intent: AppIntent, key: string): string | undefined;
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
// packages/cli/src/app-opentui/adapters/common.ts
|
|
3
|
+
function adapterContextFromRuntime(runtime, renderer) {
|
|
4
|
+
return {
|
|
5
|
+
projectRoot: runtime.getState().projectRoot,
|
|
6
|
+
renderer,
|
|
7
|
+
ensureRuntime: () => runtime.getRunnerContext(),
|
|
8
|
+
emit: (event) => runtime.emit(event),
|
|
9
|
+
getState: () => runtime.getState()
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
function projectRootOf(ctx) {
|
|
13
|
+
const root = ctx.rig?.projectRoot ?? ctx.projectRoot ?? ctx.getState().projectRoot;
|
|
14
|
+
if (typeof root === "string" && root.trim())
|
|
15
|
+
return root;
|
|
16
|
+
throw new Error("Rig app adapter requires a projectRoot.");
|
|
17
|
+
}
|
|
18
|
+
async function runtimeOf(ctx) {
|
|
19
|
+
if (ctx.rig && "runId" in ctx.rig && ctx.ensureRuntime === undefined) {
|
|
20
|
+
return ctx.rig;
|
|
21
|
+
}
|
|
22
|
+
if (ctx.ensureRuntime)
|
|
23
|
+
return ctx.ensureRuntime();
|
|
24
|
+
throw new Error("Rig app adapter requires ensureRuntime() before this action can run.");
|
|
25
|
+
}
|
|
26
|
+
function normalizeAppError(error) {
|
|
27
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
28
|
+
const rawHint = error instanceof Error ? error.hint : undefined;
|
|
29
|
+
return {
|
|
30
|
+
message,
|
|
31
|
+
...typeof rawHint === "string" && rawHint.trim() ? { hint: rawHint.trim() } : {}
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
function emitStarted(ctx, label, optimistic) {
|
|
35
|
+
ctx.emit({ type: "action.started", label, ...optimistic ? { optimistic } : {} });
|
|
36
|
+
}
|
|
37
|
+
function emitProgress(ctx, label, detail, data) {
|
|
38
|
+
ctx.emit({ type: "action.progress", label, ...detail ? { detail } : {}, ...data ? { data } : {} });
|
|
39
|
+
}
|
|
40
|
+
function emitCompleted(ctx, label, data) {
|
|
41
|
+
ctx.emit({ type: "action.completed", label, ...data ? { data } : {} });
|
|
42
|
+
}
|
|
43
|
+
function emitFailed(ctx, label, error, data) {
|
|
44
|
+
if (data)
|
|
45
|
+
patchData(ctx, data);
|
|
46
|
+
const normalized = normalizeAppError(error);
|
|
47
|
+
ctx.emit({
|
|
48
|
+
type: "action.failed",
|
|
49
|
+
label,
|
|
50
|
+
message: normalized.message,
|
|
51
|
+
...normalized.hint ? { hint: normalized.hint } : {},
|
|
52
|
+
cause: error
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
function patchData(ctx, data) {
|
|
56
|
+
ctx.emit({ type: "data.patch", data });
|
|
57
|
+
}
|
|
58
|
+
function patchFooter(ctx, footer) {
|
|
59
|
+
ctx.emit({ type: "footer.patch", footer });
|
|
60
|
+
}
|
|
61
|
+
async function captureConsole(fn) {
|
|
62
|
+
const output = [];
|
|
63
|
+
const original = {
|
|
64
|
+
log: console.log,
|
|
65
|
+
info: console.info,
|
|
66
|
+
warn: console.warn,
|
|
67
|
+
error: console.error
|
|
68
|
+
};
|
|
69
|
+
const capture = (...parts) => {
|
|
70
|
+
output.push(parts.map((part) => typeof part === "string" ? part : JSON.stringify(part)).join(" "));
|
|
71
|
+
};
|
|
72
|
+
console.log = capture;
|
|
73
|
+
console.info = capture;
|
|
74
|
+
console.warn = capture;
|
|
75
|
+
console.error = capture;
|
|
76
|
+
try {
|
|
77
|
+
const result = await fn();
|
|
78
|
+
return { result, output };
|
|
79
|
+
} finally {
|
|
80
|
+
console.log = original.log;
|
|
81
|
+
console.info = original.info;
|
|
82
|
+
console.warn = original.warn;
|
|
83
|
+
console.error = original.error;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
async function releaseRendererForExternalTui(ctx) {
|
|
87
|
+
const renderer = ctx.renderer;
|
|
88
|
+
if (!renderer)
|
|
89
|
+
return;
|
|
90
|
+
if (renderer.suspend) {
|
|
91
|
+
await renderer.suspend();
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
if (renderer.destroy) {
|
|
95
|
+
await renderer.destroy();
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
function arrayFromPayload(value) {
|
|
99
|
+
if (Array.isArray(value)) {
|
|
100
|
+
return value.filter((entry) => Boolean(entry && typeof entry === "object" && !Array.isArray(entry)));
|
|
101
|
+
}
|
|
102
|
+
if (value && typeof value === "object" && !Array.isArray(value)) {
|
|
103
|
+
const entries = value.entries;
|
|
104
|
+
if (Array.isArray(entries))
|
|
105
|
+
return arrayFromPayload(entries);
|
|
106
|
+
}
|
|
107
|
+
return [];
|
|
108
|
+
}
|
|
109
|
+
function stringField(record, keys, fallback = "") {
|
|
110
|
+
for (const key of keys) {
|
|
111
|
+
const value = record[key];
|
|
112
|
+
if (typeof value === "string" && value.trim())
|
|
113
|
+
return value.trim();
|
|
114
|
+
if (typeof value === "number" && Number.isFinite(value))
|
|
115
|
+
return String(value);
|
|
116
|
+
}
|
|
117
|
+
return fallback;
|
|
118
|
+
}
|
|
119
|
+
function compactRecord(record, keys) {
|
|
120
|
+
const out = {};
|
|
121
|
+
for (const key of keys) {
|
|
122
|
+
const value = record[key];
|
|
123
|
+
if (value !== undefined && value !== null && value !== "")
|
|
124
|
+
out[key] = value;
|
|
125
|
+
}
|
|
126
|
+
return out;
|
|
127
|
+
}
|
|
128
|
+
function payloadString(intent, key) {
|
|
129
|
+
const value = intent.action.payload?.[key];
|
|
130
|
+
return typeof value === "string" && value.trim() ? value.trim() : undefined;
|
|
131
|
+
}
|
|
132
|
+
export {
|
|
133
|
+
stringField,
|
|
134
|
+
runtimeOf,
|
|
135
|
+
releaseRendererForExternalTui,
|
|
136
|
+
projectRootOf,
|
|
137
|
+
payloadString,
|
|
138
|
+
patchFooter,
|
|
139
|
+
patchData,
|
|
140
|
+
normalizeAppError,
|
|
141
|
+
emitStarted,
|
|
142
|
+
emitProgress,
|
|
143
|
+
emitFailed,
|
|
144
|
+
emitCompleted,
|
|
145
|
+
compactRecord,
|
|
146
|
+
captureConsole,
|
|
147
|
+
arrayFromPayload,
|
|
148
|
+
adapterContextFromRuntime
|
|
149
|
+
};
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { AppAdapter } from "../types";
|
|
2
|
+
import { type AppAdapterContext } from "./common";
|
|
3
|
+
export declare function createDoctorAdapter(): AppAdapter;
|
|
4
|
+
export type AppDoctorCheck = {
|
|
5
|
+
readonly id: string;
|
|
6
|
+
readonly label: string;
|
|
7
|
+
readonly status: "pass" | "warn" | "fail";
|
|
8
|
+
readonly detail?: string;
|
|
9
|
+
readonly remediation?: string;
|
|
10
|
+
};
|
|
11
|
+
export declare function runDoctorChecksForApp(ctx: AppAdapterContext): Promise<AppDoctorCheck[]>;
|