@sagmans/dsh-tui 0.1.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 +21 -0
- package/README.md +266 -0
- package/cordis.patch.yml +123 -0
- package/lib/agent/fork.d.ts +24 -0
- package/lib/agent/fork.d.ts.map +1 -0
- package/lib/agent/fork.js +25 -0
- package/lib/agent/fork.js.map +1 -0
- package/lib/agent/history.d.ts +78 -0
- package/lib/agent/history.d.ts.map +1 -0
- package/lib/agent/history.js +179 -0
- package/lib/agent/history.js.map +1 -0
- package/lib/agent/host.d.ts +58 -0
- package/lib/agent/host.d.ts.map +1 -0
- package/lib/agent/host.js +59 -0
- package/lib/agent/host.js.map +1 -0
- package/lib/agent/model.d.ts +61 -0
- package/lib/agent/model.d.ts.map +1 -0
- package/lib/agent/model.js +92 -0
- package/lib/agent/model.js.map +1 -0
- package/lib/agent/present.d.ts +12 -0
- package/lib/agent/present.d.ts.map +1 -0
- package/lib/agent/present.js +52 -0
- package/lib/agent/present.js.map +1 -0
- package/lib/agent/presets.d.ts +75 -0
- package/lib/agent/presets.d.ts.map +1 -0
- package/lib/agent/presets.js +117 -0
- package/lib/agent/presets.js.map +1 -0
- package/lib/agent/projections.d.ts +16 -0
- package/lib/agent/projections.d.ts.map +1 -0
- package/lib/agent/projections.js +31 -0
- package/lib/agent/projections.js.map +1 -0
- package/lib/agent/status.d.ts +46 -0
- package/lib/agent/status.d.ts.map +1 -0
- package/lib/agent/status.js +67 -0
- package/lib/agent/status.js.map +1 -0
- package/lib/cards.d.ts +88 -0
- package/lib/cards.d.ts.map +1 -0
- package/lib/cards.js +218 -0
- package/lib/cards.js.map +1 -0
- package/lib/compat/probe.d.ts +33 -0
- package/lib/compat/probe.d.ts.map +1 -0
- package/lib/compat/probe.js +74 -0
- package/lib/compat/probe.js.map +1 -0
- package/lib/config.d.ts +13 -0
- package/lib/config.d.ts.map +1 -0
- package/lib/config.js +49 -0
- package/lib/config.js.map +1 -0
- package/lib/contracts.d.ts +32 -0
- package/lib/contracts.d.ts.map +1 -0
- package/lib/contracts.js +2 -0
- package/lib/contracts.js.map +1 -0
- package/lib/export.d.ts +15 -0
- package/lib/export.d.ts.map +1 -0
- package/lib/export.js +52 -0
- package/lib/export.js.map +1 -0
- package/lib/gates.d.ts +85 -0
- package/lib/gates.d.ts.map +1 -0
- package/lib/gates.js +216 -0
- package/lib/gates.js.map +1 -0
- package/lib/identity.d.ts +33 -0
- package/lib/identity.d.ts.map +1 -0
- package/lib/identity.js +49 -0
- package/lib/identity.js.map +1 -0
- package/lib/index.d.ts +24 -0
- package/lib/index.d.ts.map +1 -0
- package/lib/index.js +1196 -0
- package/lib/index.js.map +1 -0
- package/lib/input/completion.d.ts +22 -0
- package/lib/input/completion.d.ts.map +1 -0
- package/lib/input/completion.js +27 -0
- package/lib/input/completion.js.map +1 -0
- package/lib/input/submission.d.ts +62 -0
- package/lib/input/submission.d.ts.map +1 -0
- package/lib/input/submission.js +80 -0
- package/lib/input/submission.js.map +1 -0
- package/lib/jobs.d.ts +64 -0
- package/lib/jobs.d.ts.map +1 -0
- package/lib/jobs.js +123 -0
- package/lib/jobs.js.map +1 -0
- package/lib/startup.d.ts +17 -0
- package/lib/startup.d.ts.map +1 -0
- package/lib/startup.js +67 -0
- package/lib/startup.js.map +1 -0
- package/lib/subagents.d.ts +74 -0
- package/lib/subagents.d.ts.map +1 -0
- package/lib/subagents.js +141 -0
- package/lib/subagents.js.map +1 -0
- package/lib/terminal/bell.d.ts +18 -0
- package/lib/terminal/bell.d.ts.map +1 -0
- package/lib/terminal/bell.js +16 -0
- package/lib/terminal/bell.js.map +1 -0
- package/lib/terminal/clipboard.d.ts +11 -0
- package/lib/terminal/clipboard.d.ts.map +1 -0
- package/lib/terminal/clipboard.js +18 -0
- package/lib/terminal/clipboard.js.map +1 -0
- package/lib/terminal/restore.d.ts +17 -0
- package/lib/terminal/restore.d.ts.map +1 -0
- package/lib/terminal/restore.js +43 -0
- package/lib/terminal/restore.js.map +1 -0
- package/lib/terminal/title.d.ts +22 -0
- package/lib/terminal/title.d.ts.map +1 -0
- package/lib/terminal/title.js +34 -0
- package/lib/terminal/title.js.map +1 -0
- package/lib/text.d.ts +19 -0
- package/lib/text.d.ts.map +1 -0
- package/lib/text.js +61 -0
- package/lib/text.js.map +1 -0
- package/lib/theme.d.ts +47 -0
- package/lib/theme.d.ts.map +1 -0
- package/lib/theme.js +84 -0
- package/lib/theme.js.map +1 -0
- package/lib/transcript.d.ts +91 -0
- package/lib/transcript.d.ts.map +1 -0
- package/lib/transcript.js +315 -0
- package/lib/transcript.js.map +1 -0
- package/lib/ui/dock.d.ts +36 -0
- package/lib/ui/dock.d.ts.map +1 -0
- package/lib/ui/dock.js +110 -0
- package/lib/ui/dock.js.map +1 -0
- package/lib/ui/markdown.d.ts +17 -0
- package/lib/ui/markdown.d.ts.map +1 -0
- package/lib/ui/markdown.js +35 -0
- package/lib/ui/markdown.js.map +1 -0
- package/lib/ui/picker.d.ts +103 -0
- package/lib/ui/picker.d.ts.map +1 -0
- package/lib/ui/picker.js +165 -0
- package/lib/ui/picker.js.map +1 -0
- package/lib/ui/rows.d.ts +30 -0
- package/lib/ui/rows.d.ts.map +1 -0
- package/lib/ui/rows.js +49 -0
- package/lib/ui/rows.js.map +1 -0
- package/lib/ui/status.d.ts +49 -0
- package/lib/ui/status.d.ts.map +1 -0
- package/lib/ui/status.js +90 -0
- package/lib/ui/status.js.map +1 -0
- package/lib/ui/view.d.ts +56 -0
- package/lib/ui/view.d.ts.map +1 -0
- package/lib/ui/view.js +184 -0
- package/lib/ui/view.js.map +1 -0
- package/lib/work.d.ts +39 -0
- package/lib/work.d.ts.map +1 -0
- package/lib/work.js +97 -0
- package/lib/work.js.map +1 -0
- package/package.json +109 -0
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
import { projectionRecord, projectionString } from "./projections.js";
|
|
2
|
+
/**
|
|
3
|
+
* Read a `/preset` argument.
|
|
4
|
+
*
|
|
5
|
+
* A bare command opens the picker because choosing by eye is the point of a
|
|
6
|
+
* selector; anything else is an id, which is the token the session log records.
|
|
7
|
+
*/
|
|
8
|
+
export function parsePresetArgument(argument) {
|
|
9
|
+
const id = argument.trim();
|
|
10
|
+
return id === '' ? { kind: 'pick' } : { kind: 'switch', id };
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* One-line gloss for the modes this deployment ships.
|
|
14
|
+
*
|
|
15
|
+
* The Web app translates the same four ids from its own locale bundle; a
|
|
16
|
+
* terminal has no such bundle, so the copy lives here. A preset this table does
|
|
17
|
+
* not name is not ours to describe: it speaks for itself through its metadata.
|
|
18
|
+
*/
|
|
19
|
+
const SHIPPED_GLOSS = {
|
|
20
|
+
standard: 'full agent: editing, shell, search, skills, planning, goals, subagents, workflows',
|
|
21
|
+
ptc: 'the same agent, with its tools reached through one TypeScript program',
|
|
22
|
+
minimal: 'one tool: a persistent shell',
|
|
23
|
+
cordis: 'harness authoring: runtime inspection and composition guidance',
|
|
24
|
+
};
|
|
25
|
+
/** How one preset appears in the picker. */
|
|
26
|
+
export function describePreset(preset, currentId) {
|
|
27
|
+
const gloss = SHIPPED_GLOSS[preset.id];
|
|
28
|
+
const described = preset.broken !== undefined
|
|
29
|
+
? `cannot start: ${preset.broken}`
|
|
30
|
+
: [gloss ?? preset.name, gloss === undefined ? preset.description : undefined,
|
|
31
|
+
preset.trust === 'user' ? 'authored here' : undefined]
|
|
32
|
+
.filter(part => part !== undefined && part !== '')
|
|
33
|
+
.join(' · ');
|
|
34
|
+
return {
|
|
35
|
+
label: preset.id,
|
|
36
|
+
description: described === '' ? undefined : described,
|
|
37
|
+
current: preset.id === currentId,
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
/** The projection key the roster advances and this surface reads. */
|
|
41
|
+
export const AGENT_PRESET_KEY = 'agentPreset';
|
|
42
|
+
/** The projection key a session's turn boundary lives under. */
|
|
43
|
+
const TURN_BOUNDARY_KEY = 'turnBoundary';
|
|
44
|
+
function asRecord(value) {
|
|
45
|
+
return typeof value === 'object' && value !== null ? value : undefined;
|
|
46
|
+
}
|
|
47
|
+
function textOr(value) {
|
|
48
|
+
return typeof value === 'string' && value !== '' ? value : undefined;
|
|
49
|
+
}
|
|
50
|
+
/** One roster row, or undefined when it names no usable id. */
|
|
51
|
+
function toSummary(value) {
|
|
52
|
+
const record = asRecord(value);
|
|
53
|
+
const id = textOr(record?.id);
|
|
54
|
+
if (id === undefined)
|
|
55
|
+
return undefined;
|
|
56
|
+
return {
|
|
57
|
+
id,
|
|
58
|
+
trust: record?.trust === 'user' ? 'user' : 'system',
|
|
59
|
+
name: textOr(record?.name),
|
|
60
|
+
description: textOr(record?.description),
|
|
61
|
+
broken: textOr(record?.broken),
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
function numberOr(value) {
|
|
65
|
+
return typeof value === 'number' && Number.isFinite(value) ? value : undefined;
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* Wrap the roster in the little of it a terminal needs.
|
|
69
|
+
*
|
|
70
|
+
* The seam is optional here: a composition that dropped the row still runs the
|
|
71
|
+
* surface, it just has no mode to choose. Every call is guarded because the
|
|
72
|
+
* service arrives from another package and its shape is this surface's
|
|
73
|
+
* assumption, not its contract.
|
|
74
|
+
*/
|
|
75
|
+
export function createPresetRoster(ctx) {
|
|
76
|
+
const service = ctx.get('agentPresets');
|
|
77
|
+
if (typeof service?.list !== 'function' || typeof service.mount !== 'function')
|
|
78
|
+
return undefined;
|
|
79
|
+
const defaultId = textOr(service.defaultId);
|
|
80
|
+
if (defaultId === undefined)
|
|
81
|
+
return undefined;
|
|
82
|
+
return {
|
|
83
|
+
defaultId,
|
|
84
|
+
list: async () => {
|
|
85
|
+
const rows = await service.list?.() ?? [];
|
|
86
|
+
return rows.flatMap(row => toSummary(row) ?? []);
|
|
87
|
+
},
|
|
88
|
+
resolve: async (id) => {
|
|
89
|
+
const resolved = await service.resolve?.(id);
|
|
90
|
+
const summary = toSummary(resolved);
|
|
91
|
+
if (summary === undefined) {
|
|
92
|
+
throw new Error(`agentPresets: the roster resolved ${id === undefined ? 'its default' : `"${id}"`} to nothing usable`);
|
|
93
|
+
}
|
|
94
|
+
return summary;
|
|
95
|
+
},
|
|
96
|
+
mount: async (agentCtx, id) => {
|
|
97
|
+
await service.mount?.(agentCtx, id);
|
|
98
|
+
},
|
|
99
|
+
select: async (agent, id) => {
|
|
100
|
+
const select = service.select;
|
|
101
|
+
if (typeof select !== 'function')
|
|
102
|
+
throw new Error('agentPresets: this roster cannot switch a session');
|
|
103
|
+
return await select.call(service, agent, id);
|
|
104
|
+
},
|
|
105
|
+
current: session => projectionString(ctx, session, AGENT_PRESET_KEY),
|
|
106
|
+
started: session => {
|
|
107
|
+
const boundary = projectionRecord(ctx, session, TURN_BOUNDARY_KEY);
|
|
108
|
+
if (boundary === undefined)
|
|
109
|
+
return false;
|
|
110
|
+
const open = boundary.openTurnStartSeq;
|
|
111
|
+
if (open !== null && open !== undefined)
|
|
112
|
+
return true;
|
|
113
|
+
return (numberOr(boundary.lastTurn) ?? 0) > 0;
|
|
114
|
+
},
|
|
115
|
+
};
|
|
116
|
+
}
|
|
117
|
+
//# sourceMappingURL=presets.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"presets.js","sourceRoot":"","sources":["../../src/agent/presets.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { Context } from '@deepseek-ai/cordis';
|
|
2
|
+
/**
|
|
3
|
+
* One session projection's state.
|
|
4
|
+
*
|
|
5
|
+
* A composition without a projection registry, and a session whose projection
|
|
6
|
+
* unit is not registered, both leave the key simply absent — and the surface
|
|
7
|
+
* reads projections while rendering, where a missing fact may cost a segment
|
|
8
|
+
* but never the session. A registered unit that throws is treated the same way
|
|
9
|
+
* for the same reason.
|
|
10
|
+
*/
|
|
11
|
+
export declare function projectionState(ctx: Context, session: unknown, key: string): unknown;
|
|
12
|
+
/** One projection's state when it is a record. */
|
|
13
|
+
export declare function projectionRecord(ctx: Context, session: unknown, key: string): Record<string, unknown> | undefined;
|
|
14
|
+
/** One projection's state when it is a non-empty string. */
|
|
15
|
+
export declare function projectionString(ctx: Context, session: unknown, key: string): string | undefined;
|
|
16
|
+
//# sourceMappingURL=projections.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"projections.d.ts","sourceRoot":"","sources":["../../src/agent/projections.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAA;AAOlD;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAAC,GAAG,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAQpF;AAED,kDAAkD;AAClD,wBAAgB,gBAAgB,CAC9B,GAAG,EAAE,OAAO,EACZ,OAAO,EAAE,OAAO,EAChB,GAAG,EAAE,MAAM,GACV,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CAGrC;AAED,4DAA4D;AAC5D,wBAAgB,gBAAgB,CAAC,GAAG,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAGhG"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* One session projection's state.
|
|
3
|
+
*
|
|
4
|
+
* A composition without a projection registry, and a session whose projection
|
|
5
|
+
* unit is not registered, both leave the key simply absent — and the surface
|
|
6
|
+
* reads projections while rendering, where a missing fact may cost a segment
|
|
7
|
+
* but never the session. A registered unit that throws is treated the same way
|
|
8
|
+
* for the same reason.
|
|
9
|
+
*/
|
|
10
|
+
export function projectionState(ctx, session, key) {
|
|
11
|
+
const projections = ctx.get('sessionProjections');
|
|
12
|
+
if (projections?.stateOf === undefined)
|
|
13
|
+
return undefined;
|
|
14
|
+
try {
|
|
15
|
+
return projections.stateOf(session, key);
|
|
16
|
+
}
|
|
17
|
+
catch {
|
|
18
|
+
return undefined;
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
/** One projection's state when it is a record. */
|
|
22
|
+
export function projectionRecord(ctx, session, key) {
|
|
23
|
+
const state = projectionState(ctx, session, key);
|
|
24
|
+
return typeof state === 'object' && state !== null ? state : undefined;
|
|
25
|
+
}
|
|
26
|
+
/** One projection's state when it is a non-empty string. */
|
|
27
|
+
export function projectionString(ctx, session, key) {
|
|
28
|
+
const state = projectionState(ctx, session, key);
|
|
29
|
+
return typeof state === 'string' && state !== '' ? state : undefined;
|
|
30
|
+
}
|
|
31
|
+
//# sourceMappingURL=projections.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"projections.js","sourceRoot":"","sources":["../../src/agent/projections.ts"],"names":[],"mappings":"AAOA;;;;;;;;GAQG;AACH,MAAM,UAAU,eAAe,CAAC,GAAY,EAAE,OAAgB,EAAE,GAAW;IACzE,MAAM,WAAW,GAAG,GAAG,CAAC,GAAG,CAAC,oBAAoB,CAA4B,CAAA;IAC5E,IAAI,WAAW,EAAE,OAAO,KAAK,SAAS;QAAE,OAAO,SAAS,CAAA;IACxD,IAAI,CAAC;QACH,OAAO,WAAW,CAAC,OAAO,CAAC,OAAO,EAAE,GAAG,CAAC,CAAA;IAC1C,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,SAAS,CAAA;IAClB,CAAC;AACH,CAAC;AAED,kDAAkD;AAClD,MAAM,UAAU,gBAAgB,CAC9B,GAAY,EACZ,OAAgB,EAChB,GAAW;IAEX,MAAM,KAAK,GAAG,eAAe,CAAC,GAAG,EAAE,OAAO,EAAE,GAAG,CAAC,CAAA;IAChD,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,CAAC,CAAC,CAAC,KAAgC,CAAC,CAAC,CAAC,SAAS,CAAA;AACnG,CAAC;AAED,4DAA4D;AAC5D,MAAM,UAAU,gBAAgB,CAAC,GAAY,EAAE,OAAgB,EAAE,GAAW;IAC1E,MAAM,KAAK,GAAG,eAAe,CAAC,GAAG,EAAE,OAAO,EAAE,GAAG,CAAC,CAAA;IAChD,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS,CAAA;AACtE,CAAC"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import type { Context } from '@deepseek-ai/cordis';
|
|
2
|
+
import type { SessionId } from '@deepseek-ai/dsh-session';
|
|
3
|
+
import type { StatusFacts } from '../ui/status.ts';
|
|
4
|
+
/** Whether a turn is running and when it started. */
|
|
5
|
+
export interface ActivityState {
|
|
6
|
+
readonly running: boolean;
|
|
7
|
+
readonly startedAt: number | undefined;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* The token-usage projection state.
|
|
11
|
+
*
|
|
12
|
+
* The unit projects `{ totals, last }` — a flat usage object is the wrong shape
|
|
13
|
+
* and reading it silently yields nothing, so the reader is pinned by a test.
|
|
14
|
+
*/
|
|
15
|
+
export declare function usageTotals(state: unknown): Record<string, unknown> | undefined;
|
|
16
|
+
/**
|
|
17
|
+
* Share of prompt tokens a provider served from cache.
|
|
18
|
+
*
|
|
19
|
+
* Read tokens against the uncached ones: a hit rate is what a reader can act on
|
|
20
|
+
* (it is what caching buys), while the raw counts belong in `/status`.
|
|
21
|
+
*/
|
|
22
|
+
export declare function cacheRate(usage: Record<string, unknown> | undefined): number | undefined;
|
|
23
|
+
/**
|
|
24
|
+
* Gather what the footer states.
|
|
25
|
+
*
|
|
26
|
+
* Every service is optional and every read is guarded: the footer is the least
|
|
27
|
+
* important thing on screen, and a composition that omits the model directory or
|
|
28
|
+
* the token meter should cost the reader a segment, not the session.
|
|
29
|
+
*/
|
|
30
|
+
/** Where the footer reads its facts from. */
|
|
31
|
+
export interface StatusSources {
|
|
32
|
+
readonly sessionId: () => SessionId;
|
|
33
|
+
readonly activity: () => ActivityState;
|
|
34
|
+
/**
|
|
35
|
+
* A route the reader chose for this session, which outranks the composition
|
|
36
|
+
* default: the footer must show the model the next step will actually use.
|
|
37
|
+
*/
|
|
38
|
+
readonly override?: (() => {
|
|
39
|
+
readonly provider?: string;
|
|
40
|
+
readonly model?: string;
|
|
41
|
+
readonly reasoningEffort?: string;
|
|
42
|
+
} | undefined) | undefined;
|
|
43
|
+
readonly home?: string | undefined;
|
|
44
|
+
}
|
|
45
|
+
export declare function createStatusFacts(ctx: Context, sources: StatusSources): () => StatusFacts;
|
|
46
|
+
//# sourceMappingURL=status.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"status.d.ts","sourceRoot":"","sources":["../../src/agent/status.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAA;AAClD,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,0BAA0B,CAAA;AACzD,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAA;AAIlD,qDAAqD;AACrD,MAAM,WAAW,aAAa;IAC5B,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAA;IACzB,QAAQ,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,CAAA;CACvC;AAiBD;;;;;GAKG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CAE/E;AAED;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,GAAG,MAAM,GAAG,SAAS,CAMxF;AAUD;;;;;;GAMG;AACH,6CAA6C;AAC7C,MAAM,WAAW,aAAa;IAC5B,QAAQ,CAAC,SAAS,EAAE,MAAM,SAAS,CAAA;IACnC,QAAQ,CAAC,QAAQ,EAAE,MAAM,aAAa,CAAA;IACtC;;;OAGG;IACH,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM;QACzB,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAA;QAC1B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAA;QACvB,QAAQ,CAAC,eAAe,CAAC,EAAE,MAAM,CAAA;KAClC,GAAG,SAAS,CAAC,GAAG,SAAS,CAAA;IAC1B,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,SAAS,CAAA;CACnC;AAED,wBAAgB,iBAAiB,CAAC,GAAG,EAAE,OAAO,EAAE,OAAO,EAAE,aAAa,GAAG,MAAM,WAAW,CAiCzF"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import { AGENT_PRESET_KEY } from "./presets.js";
|
|
2
|
+
import { projectionRecord, projectionString } from "./projections.js";
|
|
3
|
+
/**
|
|
4
|
+
* The token-usage projection state.
|
|
5
|
+
*
|
|
6
|
+
* The unit projects `{ totals, last }` — a flat usage object is the wrong shape
|
|
7
|
+
* and reading it silently yields nothing, so the reader is pinned by a test.
|
|
8
|
+
*/
|
|
9
|
+
export function usageTotals(state) {
|
|
10
|
+
return asRecord(asRecord(state)?.totals);
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Share of prompt tokens a provider served from cache.
|
|
14
|
+
*
|
|
15
|
+
* Read tokens against the uncached ones: a hit rate is what a reader can act on
|
|
16
|
+
* (it is what caching buys), while the raw counts belong in `/status`.
|
|
17
|
+
*/
|
|
18
|
+
export function cacheRate(usage) {
|
|
19
|
+
const read = numberOr(usage?.cacheReadTokens);
|
|
20
|
+
const uncached = numberOr(usage?.uncachedInputTokens);
|
|
21
|
+
if (read === undefined || uncached === undefined)
|
|
22
|
+
return undefined;
|
|
23
|
+
const total = read + uncached;
|
|
24
|
+
return total === 0 ? undefined : read / total;
|
|
25
|
+
}
|
|
26
|
+
function asRecord(value) {
|
|
27
|
+
return typeof value === 'object' && value !== null ? value : undefined;
|
|
28
|
+
}
|
|
29
|
+
function numberOr(value) {
|
|
30
|
+
return typeof value === 'number' && Number.isFinite(value) ? value : undefined;
|
|
31
|
+
}
|
|
32
|
+
export function createStatusFacts(ctx, sources) {
|
|
33
|
+
return () => {
|
|
34
|
+
const override = sources.override?.();
|
|
35
|
+
const selection = override ?? ctx.get('agentDefaultModel')?.currentSelection?.();
|
|
36
|
+
const session = ctx.get('sessions')?.get?.(sources.sessionId());
|
|
37
|
+
let preset;
|
|
38
|
+
if (session !== undefined) {
|
|
39
|
+
try {
|
|
40
|
+
preset = ctx.get('permissionPresets')?.current?.(session);
|
|
41
|
+
}
|
|
42
|
+
catch {
|
|
43
|
+
preset = undefined;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
const pressure = session === undefined ? undefined : projectionRecord(ctx, session, 'contextPressure');
|
|
47
|
+
const totals = session === undefined ? undefined : usageTotals(projectionRecord(ctx, session, 'tokenUsage'));
|
|
48
|
+
const state = sources.activity();
|
|
49
|
+
return {
|
|
50
|
+
activity: state.running ? 'working' : 'idle',
|
|
51
|
+
elapsedMs: state.startedAt === undefined ? undefined : Date.now() - state.startedAt,
|
|
52
|
+
provider: selection?.provider,
|
|
53
|
+
model: selection?.model,
|
|
54
|
+
effort: selection?.reasoningEffort,
|
|
55
|
+
agentPreset: session === undefined ? undefined : projectionString(ctx, session, AGENT_PRESET_KEY),
|
|
56
|
+
preset,
|
|
57
|
+
contextTokens: numberOr(pressure?.pressureTokens),
|
|
58
|
+
contextWindow: numberOr(pressure?.contextWindow),
|
|
59
|
+
cacheRate: cacheRate(totals),
|
|
60
|
+
uncachedInputTokens: numberOr(totals?.uncachedInputTokens),
|
|
61
|
+
outputTokens: numberOr(totals?.outputTokens),
|
|
62
|
+
cwd: process.cwd(),
|
|
63
|
+
home: sources.home,
|
|
64
|
+
};
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
//# sourceMappingURL=status.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"status.js","sourceRoot":"","sources":["../../src/agent/status.ts"],"names":[],"mappings":"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"}
|
package/lib/cards.d.ts
ADDED
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
import type { FileDiff, ToolCallView, ToolResultView } from '@deepseek-ai/dsh-tools';
|
|
2
|
+
/** What a tool's result presenter receives, plus the call arguments it was asked with. */
|
|
3
|
+
export interface ToolResultInput {
|
|
4
|
+
readonly argumentsJson: string;
|
|
5
|
+
readonly content: unknown;
|
|
6
|
+
readonly isError: boolean;
|
|
7
|
+
readonly meta: unknown;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* How the surface asks a tool to present itself.
|
|
11
|
+
*
|
|
12
|
+
* The seam is a plain interface so the transcript fold stays pure: the host
|
|
13
|
+
* adapter is the only part that touches the tool registry.
|
|
14
|
+
*/
|
|
15
|
+
export interface ToolPresenter {
|
|
16
|
+
call(name: string, argumentsJson: string): ToolCard | undefined;
|
|
17
|
+
result(name: string, input: ToolResultInput): ToolCard | undefined;
|
|
18
|
+
}
|
|
19
|
+
/** Which treatment a card gets; mirrors the tool's declared render intent. */
|
|
20
|
+
export type ToolCardKind = 'generic' | 'terminal' | 'diff' | 'search' | 'read' | 'web';
|
|
21
|
+
/** One renderable tool row: a header plus the detail rows kept for rendering. */
|
|
22
|
+
export interface ToolCard {
|
|
23
|
+
readonly kind: ToolCardKind;
|
|
24
|
+
readonly title: string;
|
|
25
|
+
/** Rows retained for rendering, already capped at CARD_DETAIL_MAX. */
|
|
26
|
+
readonly detail: readonly string[];
|
|
27
|
+
readonly failed: boolean;
|
|
28
|
+
/** Rows the tool actually presented, which retention may have cut short. */
|
|
29
|
+
readonly totalLines: number;
|
|
30
|
+
}
|
|
31
|
+
/** Detail rows a settled card shows before it is summarized. */
|
|
32
|
+
export declare const CARD_DETAIL_LIMIT = 10;
|
|
33
|
+
/**
|
|
34
|
+
* Detail rows retained on a card at all.
|
|
35
|
+
*
|
|
36
|
+
* A collapse key must be able to show more than the summary does, and a tool
|
|
37
|
+
* that prints a hundred thousand lines must not keep the whole transcript in
|
|
38
|
+
* memory for a reader who will never scroll that far.
|
|
39
|
+
*/
|
|
40
|
+
export declare const CARD_DETAIL_MAX = 200;
|
|
41
|
+
/** Character budget for one detail row, so a minified file cannot flood the viewport. */
|
|
42
|
+
export declare const CARD_LINE_LIMIT = 200;
|
|
43
|
+
/**
|
|
44
|
+
* The rows a card shows right now, and how many the reader is not seeing.
|
|
45
|
+
*
|
|
46
|
+
* Expansion is a view decision rather than a card field so one key press can
|
|
47
|
+
* change every card at once without rebuilding the transcript.
|
|
48
|
+
*/
|
|
49
|
+
export declare function cardDetailRows(card: ToolCard, expanded: boolean): {
|
|
50
|
+
lines: readonly string[];
|
|
51
|
+
hidden: number;
|
|
52
|
+
};
|
|
53
|
+
/**
|
|
54
|
+
* Build a card from raw lines.
|
|
55
|
+
*
|
|
56
|
+
* Every path that turns text into a card goes through here, so a tool with no
|
|
57
|
+
* presenter — or a result whose presenter declined — cannot keep a hundred
|
|
58
|
+
* thousand lines alive in the transcript.
|
|
59
|
+
*/
|
|
60
|
+
export declare function cardFromLines(kind: ToolCardKind, title: string, lines: readonly string[], failed: boolean): ToolCard;
|
|
61
|
+
/** Text lines carried by model-facing content blocks. */
|
|
62
|
+
export declare function contentLines(content: unknown): string[];
|
|
63
|
+
/**
|
|
64
|
+
* Collapse one call and its result into the single row the reader sees.
|
|
65
|
+
*
|
|
66
|
+
* The pending row already told the reader what the tool is doing, so the
|
|
67
|
+
* settled row keeps that header and swaps in the outcome; a result that
|
|
68
|
+
* presents nothing keeps the call's detail rather than blanking the row.
|
|
69
|
+
*/
|
|
70
|
+
export declare function mergeCards(call: ToolCard | undefined, result: ToolCard | undefined): ToolCard;
|
|
71
|
+
/**
|
|
72
|
+
* Render one file change as a bounded unified hunk.
|
|
73
|
+
*
|
|
74
|
+
* Only the changed middle is shown: a presenter has the prior and next text but
|
|
75
|
+
* no hunk list, so trimming the shared prefix and suffix yields the same region
|
|
76
|
+
* a full diff would highlight without paying for a line-diff computation on
|
|
77
|
+
* every frame.
|
|
78
|
+
*/
|
|
79
|
+
export declare function renderFileDiff(diff: FileDiff): string[];
|
|
80
|
+
/** Map a tool's pending-call intent to a card, falling back to the raw call name. */
|
|
81
|
+
export declare function cardOfCall(view: ToolCallView | undefined, fallbackName: string): ToolCard;
|
|
82
|
+
/** Map a tool's result intent to a card, falling back to the model-facing text. */
|
|
83
|
+
export declare function cardOfResult(view: ToolResultView | undefined, input: {
|
|
84
|
+
readonly fallbackTitle: string;
|
|
85
|
+
readonly failed: boolean;
|
|
86
|
+
readonly contentLines: readonly string[];
|
|
87
|
+
}): ToolCard;
|
|
88
|
+
//# sourceMappingURL=cards.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cards.d.ts","sourceRoot":"","sources":["../src/cards.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAGV,QAAQ,EAOR,YAAY,EACZ,cAAc,EAEf,MAAM,wBAAwB,CAAA;AAE/B,0FAA0F;AAC1F,MAAM,WAAW,eAAe;IAC9B,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAA;IAC9B,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAA;IACzB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAA;IACzB,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAA;CACvB;AAED;;;;;GAKG;AACH,MAAM,WAAW,aAAa;IAC5B,IAAI,CAAC,IAAI,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,GAAG,QAAQ,GAAG,SAAS,CAAA;IAC/D,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,eAAe,GAAG,QAAQ,GAAG,SAAS,CAAA;CACnE;AAED,8EAA8E;AAC9E,MAAM,MAAM,YAAY,GAAG,SAAS,GAAG,UAAU,GAAG,MAAM,GAAG,QAAQ,GAAG,MAAM,GAAG,KAAK,CAAA;AAEtF,iFAAiF;AACjF,MAAM,WAAW,QAAQ;IACvB,QAAQ,CAAC,IAAI,EAAE,YAAY,CAAA;IAC3B,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAA;IACtB,sEAAsE;IACtE,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAA;IAClC,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAA;IACxB,4EAA4E;IAC5E,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAA;CAC5B;AAED,gEAAgE;AAChE,eAAO,MAAM,iBAAiB,KAAK,CAAA;AAEnC;;;;;;GAMG;AACH,eAAO,MAAM,eAAe,MAAM,CAAA;AAElC,yFAAyF;AACzF,eAAO,MAAM,eAAe,MAAM,CAAA;AAUlC;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,OAAO,GAAG;IAAE,KAAK,EAAE,SAAS,MAAM,EAAE,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAG9G;AAED;;;;;;GAMG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,YAAY,EAClB,KAAK,EAAE,MAAM,EACb,KAAK,EAAE,SAAS,MAAM,EAAE,EACxB,MAAM,EAAE,OAAO,GACd,QAAQ,CAGV;AAED,yDAAyD;AACzD,wBAAgB,YAAY,CAAC,OAAO,EAAE,OAAO,GAAG,MAAM,EAAE,CAYvD;AAED;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,IAAI,EAAE,QAAQ,GAAG,SAAS,EAAE,MAAM,EAAE,QAAQ,GAAG,SAAS,GAAG,QAAQ,CAW7F;AAED;;;;;;;GAOG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,QAAQ,GAAG,MAAM,EAAE,CAsBvD;AAOD,qFAAqF;AACrF,wBAAgB,UAAU,CAAC,IAAI,EAAE,YAAY,GAAG,SAAS,EAAE,YAAY,EAAE,MAAM,GAAG,QAAQ,CA2BzF;AAED,mFAAmF;AACnF,wBAAgB,YAAY,CAC1B,IAAI,EAAE,cAAc,GAAG,SAAS,EAChC,KAAK,EAAE;IAAE,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAC;IAAC,QAAQ,CAAC,YAAY,EAAE,SAAS,MAAM,EAAE,CAAA;CAAE,GAC5G,QAAQ,CA6DV"}
|
package/lib/cards.js
ADDED
|
@@ -0,0 +1,218 @@
|
|
|
1
|
+
/** Detail rows a settled card shows before it is summarized. */
|
|
2
|
+
export const CARD_DETAIL_LIMIT = 10;
|
|
3
|
+
/**
|
|
4
|
+
* Detail rows retained on a card at all.
|
|
5
|
+
*
|
|
6
|
+
* A collapse key must be able to show more than the summary does, and a tool
|
|
7
|
+
* that prints a hundred thousand lines must not keep the whole transcript in
|
|
8
|
+
* memory for a reader who will never scroll that far.
|
|
9
|
+
*/
|
|
10
|
+
export const CARD_DETAIL_MAX = 200;
|
|
11
|
+
/** Character budget for one detail row, so a minified file cannot flood the viewport. */
|
|
12
|
+
export const CARD_LINE_LIMIT = 200;
|
|
13
|
+
function clipLine(text) {
|
|
14
|
+
return text.length <= CARD_LINE_LIMIT ? text : `${text.slice(0, CARD_LINE_LIMIT - 1)}…`;
|
|
15
|
+
}
|
|
16
|
+
function bound(lines) {
|
|
17
|
+
return { detail: lines.slice(0, CARD_DETAIL_MAX).map(clipLine), totalLines: lines.length };
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* The rows a card shows right now, and how many the reader is not seeing.
|
|
21
|
+
*
|
|
22
|
+
* Expansion is a view decision rather than a card field so one key press can
|
|
23
|
+
* change every card at once without rebuilding the transcript.
|
|
24
|
+
*/
|
|
25
|
+
export function cardDetailRows(card, expanded) {
|
|
26
|
+
const lines = card.detail.slice(0, expanded ? CARD_DETAIL_MAX : CARD_DETAIL_LIMIT);
|
|
27
|
+
return { lines, hidden: Math.max(0, card.totalLines - lines.length) };
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Build a card from raw lines.
|
|
31
|
+
*
|
|
32
|
+
* Every path that turns text into a card goes through here, so a tool with no
|
|
33
|
+
* presenter — or a result whose presenter declined — cannot keep a hundred
|
|
34
|
+
* thousand lines alive in the transcript.
|
|
35
|
+
*/
|
|
36
|
+
export function cardFromLines(kind, title, lines, failed) {
|
|
37
|
+
const bounded = bound(lines);
|
|
38
|
+
return { kind, title, detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
39
|
+
}
|
|
40
|
+
/** Text lines carried by model-facing content blocks. */
|
|
41
|
+
export function contentLines(content) {
|
|
42
|
+
if (!Array.isArray(content))
|
|
43
|
+
return [];
|
|
44
|
+
const lines = [];
|
|
45
|
+
for (const block of content) {
|
|
46
|
+
if (typeof block !== 'object' || block === null)
|
|
47
|
+
continue;
|
|
48
|
+
const record = block;
|
|
49
|
+
// Any block that carries text counts; a tool-result block also holds its
|
|
50
|
+
// model-facing content one level deeper.
|
|
51
|
+
if (typeof record.text === 'string')
|
|
52
|
+
lines.push(...record.text.split('\n'));
|
|
53
|
+
if (Array.isArray(record.content))
|
|
54
|
+
lines.push(...contentLines(record.content));
|
|
55
|
+
}
|
|
56
|
+
return lines;
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Collapse one call and its result into the single row the reader sees.
|
|
60
|
+
*
|
|
61
|
+
* The pending row already told the reader what the tool is doing, so the
|
|
62
|
+
* settled row keeps that header and swaps in the outcome; a result that
|
|
63
|
+
* presents nothing keeps the call's detail rather than blanking the row.
|
|
64
|
+
*/
|
|
65
|
+
export function mergeCards(call, result) {
|
|
66
|
+
const base = call ?? result;
|
|
67
|
+
if (base === undefined)
|
|
68
|
+
throw new Error('mergeCards requires at least one card');
|
|
69
|
+
if (call === undefined || result === undefined)
|
|
70
|
+
return base;
|
|
71
|
+
return {
|
|
72
|
+
kind: result.kind === 'generic' ? call.kind : result.kind,
|
|
73
|
+
title: call.title,
|
|
74
|
+
detail: result.detail.length > 0 ? result.detail : call.detail,
|
|
75
|
+
failed: result.failed,
|
|
76
|
+
totalLines: result.detail.length > 0 ? result.totalLines : call.totalLines,
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
/**
|
|
80
|
+
* Render one file change as a bounded unified hunk.
|
|
81
|
+
*
|
|
82
|
+
* Only the changed middle is shown: a presenter has the prior and next text but
|
|
83
|
+
* no hunk list, so trimming the shared prefix and suffix yields the same region
|
|
84
|
+
* a full diff would highlight without paying for a line-diff computation on
|
|
85
|
+
* every frame.
|
|
86
|
+
*/
|
|
87
|
+
export function renderFileDiff(diff) {
|
|
88
|
+
const before = diff.oldText === null ? [] : diff.oldText.split('\n');
|
|
89
|
+
const after = diff.newText.split('\n');
|
|
90
|
+
let head = 0;
|
|
91
|
+
while (head < before.length && head < after.length && before[head] === after[head])
|
|
92
|
+
head += 1;
|
|
93
|
+
let tail = 0;
|
|
94
|
+
while (tail < before.length - head
|
|
95
|
+
&& tail < after.length - head
|
|
96
|
+
&& before[before.length - 1 - tail] === after[after.length - 1 - tail])
|
|
97
|
+
tail += 1;
|
|
98
|
+
const removed = before.slice(head, before.length - tail);
|
|
99
|
+
const added = after.slice(head, after.length - tail);
|
|
100
|
+
// "new" keys off the absent prior text, not off an empty hunk: an unchanged
|
|
101
|
+
// file has no removals either and must not read as a creation.
|
|
102
|
+
const header = diff.oldText === null ? 'new' : `-${removed.length} +${added.length}`;
|
|
103
|
+
const lines = [`${diff.path} ${header}`];
|
|
104
|
+
if (head > 0)
|
|
105
|
+
lines.push(`@@ ${head} unchanged line${head === 1 ? '' : 's'} before`);
|
|
106
|
+
for (const line of removed)
|
|
107
|
+
lines.push(`-${line}`);
|
|
108
|
+
for (const line of added)
|
|
109
|
+
lines.push(`+${line}`);
|
|
110
|
+
if (tail > 0)
|
|
111
|
+
lines.push(`@@ ${tail} unchanged line${tail === 1 ? '' : 's'} after`);
|
|
112
|
+
return lines;
|
|
113
|
+
}
|
|
114
|
+
function title(view, fallback) {
|
|
115
|
+
const declared = view.title?.trim() ?? '';
|
|
116
|
+
return declared === '' ? fallback : declared;
|
|
117
|
+
}
|
|
118
|
+
/** Map a tool's pending-call intent to a card, falling back to the raw call name. */
|
|
119
|
+
export function cardOfCall(view, fallbackName) {
|
|
120
|
+
if (view === undefined) {
|
|
121
|
+
return { kind: 'generic', title: fallbackName, detail: [], failed: false, totalLines: 0 };
|
|
122
|
+
}
|
|
123
|
+
switch (view.card) {
|
|
124
|
+
case 'terminal': {
|
|
125
|
+
const terminal = view;
|
|
126
|
+
const lines = terminal.description === undefined || terminal.description === '' ? [] : [terminal.description];
|
|
127
|
+
if (terminal.cwd !== undefined && terminal.cwd !== '')
|
|
128
|
+
lines.push(`cwd ${terminal.cwd}`);
|
|
129
|
+
return { kind: 'terminal', title: title(terminal, fallbackName), detail: bound(lines).detail, failed: false, totalLines: 0 };
|
|
130
|
+
}
|
|
131
|
+
case 'diff': {
|
|
132
|
+
const diff = view;
|
|
133
|
+
const lines = diff.diffs.flatMap(renderFileDiff);
|
|
134
|
+
const bounded = bound(lines);
|
|
135
|
+
return { kind: 'diff', title: title(diff, fallbackName), detail: bounded.detail, failed: false, totalLines: bounded.totalLines };
|
|
136
|
+
}
|
|
137
|
+
default: {
|
|
138
|
+
const generic = view;
|
|
139
|
+
const lines = contentLines(generic.content);
|
|
140
|
+
if (generic.rawInput !== undefined && lines.length === 0) {
|
|
141
|
+
lines.push(typeof generic.rawInput === 'string' ? generic.rawInput : JSON.stringify(generic.rawInput));
|
|
142
|
+
}
|
|
143
|
+
const bounded = bound(lines);
|
|
144
|
+
return { kind: 'generic', title: title(generic, fallbackName), detail: bounded.detail, failed: false, totalLines: bounded.totalLines };
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
/** Map a tool's result intent to a card, falling back to the model-facing text. */
|
|
149
|
+
export function cardOfResult(view, input) {
|
|
150
|
+
const failed = input.failed;
|
|
151
|
+
if (view === undefined) {
|
|
152
|
+
const bounded = bound(input.contentLines);
|
|
153
|
+
return { kind: 'generic', title: input.fallbackTitle, detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
154
|
+
}
|
|
155
|
+
switch (view.card) {
|
|
156
|
+
case 'terminal': {
|
|
157
|
+
const terminal = view;
|
|
158
|
+
const lines = (terminal.output ?? '').split('\n');
|
|
159
|
+
const status = terminal.signal !== undefined && terminal.signal !== ''
|
|
160
|
+
? `signal ${terminal.signal}`
|
|
161
|
+
: terminal.exitCode === undefined ? undefined : `exit ${terminal.exitCode}`;
|
|
162
|
+
if (status !== undefined)
|
|
163
|
+
lines.push(status);
|
|
164
|
+
const bounded = bound(lines);
|
|
165
|
+
return { kind: 'terminal', title: title(terminal, input.fallbackTitle), detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
166
|
+
}
|
|
167
|
+
case 'diff': {
|
|
168
|
+
const diff = view;
|
|
169
|
+
const bounded = bound(diff.diffs.flatMap(renderFileDiff));
|
|
170
|
+
return { kind: 'diff', title: title(diff, input.fallbackTitle), detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
171
|
+
}
|
|
172
|
+
case 'search': {
|
|
173
|
+
const search = view;
|
|
174
|
+
const lines = search.shape === 'paths'
|
|
175
|
+
? [...search.paths]
|
|
176
|
+
: search.files.flatMap(file => file.matches.map(match => `${file.path}:${match.lineNumber}: ${match.line}`));
|
|
177
|
+
if (search.truncated)
|
|
178
|
+
lines.push(`… ${search.total} total`);
|
|
179
|
+
const bounded = bound(lines);
|
|
180
|
+
return { kind: 'search', title: title(search, input.fallbackTitle), detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
181
|
+
}
|
|
182
|
+
case 'read': {
|
|
183
|
+
const read = view;
|
|
184
|
+
const lines = read.lines.length > 0
|
|
185
|
+
? read.lines.map(line => `${line.number}: ${line.text}`)
|
|
186
|
+
: contentLines(read.content);
|
|
187
|
+
lines.unshift(`${read.path} (from line ${read.offset}, ${read.totalLines} total)`);
|
|
188
|
+
const bounded = bound(lines);
|
|
189
|
+
return { kind: 'read', title: title(read, input.fallbackTitle), detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
190
|
+
}
|
|
191
|
+
case 'web': {
|
|
192
|
+
const web = view;
|
|
193
|
+
const lines = [];
|
|
194
|
+
if (web.kind === 'search') {
|
|
195
|
+
if (web.answer !== undefined && web.answer !== '')
|
|
196
|
+
lines.push(...web.answer.split('\n'));
|
|
197
|
+
for (const source of web.sources)
|
|
198
|
+
lines.push(source.title === undefined ? source.url : `${source.title} — ${source.url}`);
|
|
199
|
+
if (web.truncated)
|
|
200
|
+
lines.push('… more sources');
|
|
201
|
+
}
|
|
202
|
+
else {
|
|
203
|
+
lines.push(`${web.url} → ${web.statusCode}`);
|
|
204
|
+
if (web.truncated)
|
|
205
|
+
lines.push('… body truncated');
|
|
206
|
+
}
|
|
207
|
+
const bounded = bound(lines);
|
|
208
|
+
return { kind: 'web', title: title(web, input.fallbackTitle), detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
209
|
+
}
|
|
210
|
+
default: {
|
|
211
|
+
const generic = view;
|
|
212
|
+
const lines = contentLines(generic.content);
|
|
213
|
+
const bounded = bound(lines.length > 0 ? lines : input.contentLines);
|
|
214
|
+
return { kind: 'generic', title: title(generic, input.fallbackTitle), detail: bounded.detail, failed, totalLines: bounded.totalLines };
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
//# sourceMappingURL=cards.js.map
|
package/lib/cards.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cards.js","sourceRoot":"","sources":["../src/cards.ts"],"names":[],"mappings":"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"}
|