@itookit/dsht 0.3.0 → 0.3.3

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 (134) hide show
  1. package/README.i18n.yaml +2 -2
  2. package/README.md +39 -23
  3. package/README.zh.md +40 -24
  4. package/dist/catalog/controller.d.ts +32 -0
  5. package/dist/catalog/controller.js +88 -0
  6. package/dist/catalog/index.d.ts +2 -0
  7. package/dist/catalog/index.js +2 -0
  8. package/dist/{cli.js → cli/index.js} +42 -29
  9. package/dist/controller/connection.d.ts +80 -0
  10. package/dist/controller/connection.js +190 -0
  11. package/dist/controller/controller.d.ts +269 -0
  12. package/dist/controller/controller.js +372 -0
  13. package/dist/controller/index.d.ts +5 -0
  14. package/dist/controller/index.js +3 -0
  15. package/dist/controller/memory-log.d.ts +35 -0
  16. package/dist/controller/memory-log.js +95 -0
  17. package/dist/cost/config.d.ts +17 -0
  18. package/dist/cost/config.js +68 -0
  19. package/dist/cost/controller.d.ts +41 -0
  20. package/dist/cost/controller.js +115 -0
  21. package/dist/cost/index.d.ts +10 -0
  22. package/dist/cost/index.js +8 -0
  23. package/dist/cost/ledger-files.d.ts +16 -0
  24. package/dist/cost/ledger-files.js +103 -0
  25. package/dist/cost/ledger.d.ts +78 -0
  26. package/dist/cost/ledger.js +146 -0
  27. package/dist/cost/pricing.d.ts +86 -0
  28. package/dist/cost/pricing.js +223 -0
  29. package/dist/cost/records.d.ts +17 -0
  30. package/dist/cost/records.js +79 -0
  31. package/dist/cost/scanner.d.ts +22 -0
  32. package/dist/cost/scanner.js +95 -0
  33. package/dist/cost/types.d.ts +85 -0
  34. package/dist/cost/types.js +7 -0
  35. package/dist/index.d.ts +3 -0
  36. package/dist/index.js +2 -0
  37. package/dist/session/connection-view.d.ts +18 -0
  38. package/dist/session/connection-view.js +1 -0
  39. package/dist/{controller.d.ts → session/controller.d.ts} +102 -136
  40. package/dist/session/controller.js +616 -0
  41. package/dist/session/export-html.d.ts +9 -0
  42. package/dist/session/export-html.js +39 -0
  43. package/dist/{export.d.ts → session/export.d.ts} +1 -1
  44. package/dist/{export.js → session/export.js} +6 -20
  45. package/dist/{history.d.ts → session/history.d.ts} +17 -0
  46. package/dist/{history.js → session/history.js} +163 -2
  47. package/dist/session/index.d.ts +17 -0
  48. package/dist/session/index.js +10 -0
  49. package/dist/session/markdown.d.ts +39 -0
  50. package/dist/session/markdown.js +255 -0
  51. package/dist/session/math.d.ts +11 -0
  52. package/dist/session/math.js +82 -0
  53. package/dist/session/navigation.d.ts +37 -0
  54. package/dist/session/navigation.js +84 -0
  55. package/dist/{references.js → session/references.js} +1 -1
  56. package/dist/{telemetry.d.ts → session/telemetry.d.ts} +1 -1
  57. package/dist/{telemetry.js → session/telemetry.js} +1 -1
  58. package/dist/{transcript.d.ts → session/transcript.d.ts} +65 -1
  59. package/dist/{transcript.js → session/transcript.js} +141 -20
  60. package/dist/session/types.d.ts +18 -0
  61. package/dist/session/types.js +2 -0
  62. package/dist/state.d.ts +41 -0
  63. package/dist/state.js +9 -0
  64. package/dist/storage/directories.d.ts +14 -0
  65. package/dist/storage/directories.js +24 -0
  66. package/dist/storage/files.d.ts +51 -0
  67. package/dist/storage/files.js +152 -0
  68. package/dist/storage/heap-snapshot.d.ts +19 -0
  69. package/dist/storage/heap-snapshot.js +29 -0
  70. package/dist/storage/index.d.ts +4 -0
  71. package/dist/storage/index.js +4 -0
  72. package/dist/transport/auth.js +65 -0
  73. package/dist/transport/host.d.ts +13 -0
  74. package/dist/transport/host.js +1 -0
  75. package/dist/ui/app.d.ts +11 -0
  76. package/dist/ui/app.js +790 -0
  77. package/dist/ui/chat/header.d.ts +11 -0
  78. package/dist/ui/chat/header.js +14 -0
  79. package/dist/ui/chat/history-view.d.ts +12 -0
  80. package/dist/ui/chat/history-view.js +17 -0
  81. package/dist/ui/chat/status.d.ts +91 -0
  82. package/dist/ui/chat/status.js +386 -0
  83. package/dist/ui/chat/viewport.d.ts +17 -0
  84. package/dist/ui/chat/viewport.js +14 -0
  85. package/dist/ui/commands/parse.d.ts +99 -0
  86. package/dist/ui/commands/parse.js +126 -0
  87. package/dist/ui/commands/registry.d.ts +33 -0
  88. package/dist/ui/commands/registry.js +73 -0
  89. package/dist/ui/copy-mode.d.ts +4 -0
  90. package/dist/ui/copy-mode.js +6 -0
  91. package/dist/{cost-view.d.ts → ui/dialogs/cost.d.ts} +1 -1
  92. package/dist/{cost-view.js → ui/dialogs/cost.js} +6 -6
  93. package/dist/ui/dialogs/index.d.ts +120 -0
  94. package/dist/ui/dialogs/index.js +113 -0
  95. package/dist/ui/dialogs/picker.d.ts +18 -0
  96. package/dist/ui/dialogs/picker.js +38 -0
  97. package/dist/ui/frozen.d.ts +8 -0
  98. package/dist/ui/frozen.js +7 -0
  99. package/dist/ui/input/references.d.ts +12 -0
  100. package/dist/ui/input/references.js +15 -0
  101. package/dist/ui/mount.d.ts +6 -0
  102. package/dist/ui/mount.js +11 -0
  103. package/dist/{theme.d.ts → ui/theme/index.d.ts} +1 -1
  104. package/package.json +19 -13
  105. package/dist/app.d.ts +0 -21
  106. package/dist/app.js +0 -805
  107. package/dist/auth.js +0 -108
  108. package/dist/controller.js +0 -961
  109. package/dist/cost.d.ts +0 -119
  110. package/dist/cost.js +0 -313
  111. package/dist/history-view.d.ts +0 -8
  112. package/dist/history-view.js +0 -12
  113. package/dist/navigation.d.ts +0 -11
  114. package/dist/navigation.js +0 -36
  115. package/dist/status.d.ts +0 -28
  116. package/dist/status.js +0 -157
  117. /package/dist/{cli.d.ts → cli/index.d.ts} +0 -0
  118. /package/dist/{memory.d.ts → session/memory.d.ts} +0 -0
  119. /package/dist/{memory.js → session/memory.js} +0 -0
  120. /package/dist/{references.d.ts → session/references.d.ts} +0 -0
  121. /package/dist/{auth.d.ts → transport/auth.d.ts} +0 -0
  122. /package/dist/{client.d.ts → transport/client.d.ts} +0 -0
  123. /package/dist/{client.js → transport/client.js} +0 -0
  124. /package/dist/{endpoint.d.ts → transport/endpoint.d.ts} +0 -0
  125. /package/dist/{endpoint.js → transport/endpoint.js} +0 -0
  126. /package/dist/{wire.d.ts → transport/wire.d.ts} +0 -0
  127. /package/dist/{wire.js → transport/wire.js} +0 -0
  128. /package/dist/{input-history.d.ts → ui/input/history.d.ts} +0 -0
  129. /package/dist/{input-history.js → ui/input/history.js} +0 -0
  130. /package/dist/{input.d.ts → ui/input/input.d.ts} +0 -0
  131. /package/dist/{input.js → ui/input/input.js} +0 -0
  132. /package/dist/{mouse.d.ts → ui/input/mouse.d.ts} +0 -0
  133. /package/dist/{mouse.js → ui/input/mouse.js} +0 -0
  134. /package/dist/{theme.js → ui/theme/index.js} +0 -0
package/dist/status.js DELETED
@@ -1,157 +0,0 @@
1
- import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
- /** Terminal status from host projections; cumulative usage and estimated context stay distinct. */
3
- import { useTheme } from "./theme.js";
4
- import { memo, useEffect, useState } from 'react';
5
- import { Box, Text, useStdout } from 'ink';
6
- import wrapAnsi from 'wrap-ansi';
7
- import { costText } from "./cost.js";
8
- import { toolLine } from "./transcript.js";
9
- import { safeText } from "./wire.js";
10
- /** Format elapsed wall time, clamping clock skew instead of displaying negative durations.
11
- * @param milliseconds - Elapsed duration.
12
- * @returns Minute/second display, with hours when needed.
13
- */
14
- export function elapsedTime(milliseconds) {
15
- const seconds = Math.max(0, Math.floor(milliseconds / 1000));
16
- const minutes = Math.floor(seconds / 60);
17
- if (minutes === 0)
18
- return `${seconds}s`;
19
- return `${minutes >= 60 ? `${Math.floor(minutes / 60)}h ` : ''}${minutes % 60}m ${seconds % 60}s`;
20
- }
21
- /** Produce compact metadata lines without inferring missing provider measurements.
22
- * @param values - Current host projection values.
23
- * @param defaultModel - Host catalog default used before a session selects a route.
24
- * @param running - Whether the current route or next route is primary.
25
- * @returns Model, approximate context occupancy, and cumulative token buckets.
26
- */
27
- export function metricLines(values, defaultModel, running) {
28
- const selection = record(values.modelSelection);
29
- const current = running ? selection.lastUsed ?? selection.next ?? defaultModel : selection.next ?? selection.lastUsed ?? defaultModel;
30
- const model = modelName(current);
31
- const next = modelName(selection.next);
32
- const pressure = record(values.contextPressure);
33
- const used = numeric(pressure.projectedTokens) ?? numeric(pressure.pressureTokens);
34
- const capacity = numeric(pressure.contextWindow);
35
- const context = used !== undefined && capacity !== undefined && capacity > 0
36
- ? `~${Math.min(100, Math.round(used / capacity * 100))}% (${count(used)} / ${count(capacity)})`
37
- : 'unknown';
38
- const usage = record(values.tokenUsage);
39
- const buckets = [usage.uncachedInputTokens, usage.outputTokens, usage.cacheReadTokens, usage.cacheWriteTokens].map(numeric);
40
- const total = buckets.every(value => value !== undefined) ? buckets.reduce((a, b) => a + b, 0) : undefined;
41
- return [
42
- `Model: ${model}${running && next !== 'unknown' && next !== model ? ` · Next: ${next}` : ''}`,
43
- `Context: ${context} · Tokens: ${count(total)} total`,
44
- `In (uncached): ${count(buckets[0])} · Out: ${count(buckets[1])} · Cache read/write: ${count(buckets[2])}/${count(buckets[3])}`,
45
- ];
46
- }
47
- /** Fit the status summary to one terminal row; details remain available through /status.
48
- * @param fields - Activity, model, cost, context, and cumulative usage groups in display order.
49
- * @param width - Available terminal columns.
50
- * @returns A terminal-safe single line, shortened by display width.
51
- */
52
- export function compactStatus(fields, width) {
53
- return compactStatusFields(fields, width).filter(Boolean).join(' ');
54
- }
55
- /** Keep group identities while fitting plain text; ANSI styling is applied only after layout. */
56
- function compactStatusFields(fields, width) {
57
- if (width <= 0)
58
- return [];
59
- const clean = fields.map(value => safeText(value).replace(/[\r\n\t]/g, ' '));
60
- const join = () => clean.filter(Boolean).join(' ');
61
- const fits = () => !wrapAnsi(join(), width, { hard: true, wordWrap: false, trim: false }).includes('\n');
62
- if (fits())
63
- return clean;
64
- // Keep the stable activity column while it fits; reclaim it on narrow terminals.
65
- clean[0] = clean[0]?.trimEnd() ?? '';
66
- if (fits())
67
- return clean;
68
- clean[3] = (clean[3] ?? '').replace(/[█░]+ /u, '');
69
- if (fits())
70
- return clean;
71
- clean[1] = toolLine(clean[1] ?? '', Math.max(8, Math.min(24, Math.floor(width / 4))));
72
- if (fits())
73
- return clean;
74
- for (const index of [4, 2, 1, 3]) {
75
- clean[index] = '';
76
- if (fits())
77
- return clean;
78
- }
79
- return [toolLine(join(), width)];
80
- }
81
- /** Compact token counts; one formatter is reused because construction dominates the format cost. */
82
- const compactNumber = new Intl.NumberFormat('en', { notation: 'compact', maximumFractionDigits: 1 });
83
- /** Render a live clock and selected-session metadata; the timer belongs to this mounted bar. */
84
- export const StatusBar = memo(function StatusBar({ controller, expanded = false, width, paused = false }) {
85
- const theme = useTheme();
86
- const { stdout } = useStdout();
87
- const [now, setNow] = useState(Date.now);
88
- const running = controller.running;
89
- const since = controller.workingSince;
90
- useEffect(() => {
91
- setNow(Date.now());
92
- if (!running || paused)
93
- return;
94
- const timer = setInterval(() => setNow(Date.now()), 1000);
95
- return () => clearInterval(timer);
96
- }, [running, since, paused]);
97
- const state = controller.state;
98
- const workspace = state.workspaces.find(item => item.workspaceId === state.workspaceId);
99
- const view = controller.telemetry.view(state.sessionId);
100
- const costs = controller.costs;
101
- const sessionCost = costs?.hasSession(state.sessionId) ? costText(costs.total(state.sessionId)) : '?';
102
- const todayCost = costs ? costText(costs.total(undefined, 1, Date.now())) : '?';
103
- // `*` belongs to costText alone; incomplete coverage is a separate degradation, reported by `!`.
104
- const coverage = costs?.coverage ?? 'complete';
105
- const label = workspace ? `${workspace.title} · ${workspace.path}` : 'none selected';
106
- if (!expanded) {
107
- const selection = record(view.values.modelSelection);
108
- const route = record(running ? selection.lastUsed ?? selection.next ?? state.defaultModel : selection.next ?? selection.lastUsed ?? state.defaultModel);
109
- const model = typeof route.model === 'string' ? `${route.model.replace(/^deepseek-/, '')}${typeof route.reasoningEffort === 'string' ? ` · ${route.reasoningEffort}` : ''}` : 'model ?';
110
- const pressure = record(view.values.contextPressure);
111
- const used = numeric(pressure.projectedTokens) ?? numeric(pressure.pressureTokens);
112
- const capacity = numeric(pressure.contextWindow);
113
- const percent = used !== undefined && capacity !== undefined && capacity > 0 ? Math.min(100, Math.round(used / capacity * 100)) : undefined;
114
- const filled = percent === undefined ? 0 : Math.round(percent / 10);
115
- const context = percent === undefined ? 'ctx ?' : `${'█'.repeat(filled)}${'░'.repeat(10 - filled)} ~${percent}%`;
116
- const usage = record(view.values.tokenUsage);
117
- const buckets = [usage.uncachedInputTokens, usage.outputTokens, usage.cacheReadTokens, usage.cacheWriteTokens].map(numeric);
118
- const total = buckets.every(value => value !== undefined) ? buckets.reduce((a, b) => a + b, 0) : undefined;
119
- const compactCount = (value) => value === undefined ? '?' : compactNumber.format(value);
120
- const activity = running ? `◐ Working · ${since === undefined ? '?' : elapsedTime(now - since)}${state.transcript.activeTurnStartedAt === undefined ? '~' : ''} · Ctrl+C Stop` : '● Ready';
121
- const warning = state.controlError || state.modelError || coverage === 'partial' ? '! ' : '';
122
- const fields = [
123
- `${warning}${!state.online ? 'Offline · ' : ''}${activity}`.padEnd(31),
124
- model,
125
- costs ? `${costs.hasSession(state.sessionId) ? compactCost(costs.total(state.sessionId)) : '?'}/${compactCost(costs.total(undefined, 1, Date.now()))}` : '?/?',
126
- context,
127
- `${count(numeric(record(view.values.sessionStats).turns))} turns · ${compactCount(total)} tok`,
128
- ];
129
- const fitted = compactStatusFields(fields, width ?? Math.max(1, (stdout.columns ?? 80) - 2));
130
- const colors = [
131
- !state.online ? theme.status.offline : warning ? theme.status.warning : running ? theme.status.working : theme.status.ready,
132
- theme.status.model, costs ? theme.status.cost : theme.status.usage,
133
- percent === undefined ? theme.status.usage : percent >= 95 ? theme.status.critical : percent >= 80 ? theme.status.warning : theme.status.context,
134
- theme.status.usage,
135
- ];
136
- return _jsx(Text, { wrap: "truncate-end", children: fitted.map((text, index) => text ? _jsxs(Text, { children: [fitted.slice(0, index).some(Boolean) && _jsx(Text, { color: theme.colors.muted, children: ' ' }), _jsx(Text, { color: colors[index], bold: index === 0, children: text })] }, index) : null) });
137
- }
138
- return _jsxs(Box, { flexDirection: "column", borderStyle: "single", borderColor: theme.border, paddingX: 1, children: [_jsxs(Text, { color: running ? theme.colors.context : theme.colors.muted, children: [running
139
- ? `◐ Working · ${since === undefined ? 'unknown duration' : elapsedTime(now - since)}${state.transcript.activeTurnStartedAt === undefined ? ' (observed)' : ''} · Ctrl+C Stop`
140
- : '● Ready · Ctrl+C exit', !state.online ? ' · disconnected, last known status' : ''] }), _jsxs(Text, { wrap: "truncate-end", children: ["Host: ", safeText(controller.base), " \u00B7 ", safeText(state.status)] }), state.sessionId && _jsxs(Text, { children: ["Session ID: ", safeText(state.sessionId)] }), controller.sessionMode && _jsxs(Text, { children: ["Mode: ", safeText(controller.sessionMode)] }), _jsxs(Text, { wrap: "truncate-end", children: ["Workspace: ", safeText(label)] }), metricLines(view.values, state.defaultModel, running).map((line, index) => _jsx(Text, { dimColor: true, children: safeText(line) }, index)), costs && _jsxs(Text, { dimColor: true, children: ["Cost (CNY estimate): Session ", sessionCost, " \u00B7 Today ", todayCost] }), costs && coverage === 'partial' && _jsxs(Text, { color: theme.colors.context, children: ["Cost coverage incomplete: ", costs.error ? safeText(costs.error) : 'no complete scan yet'] }), _jsxs(Text, { dimColor: true, children: ["Turns: ", count(numeric(record(view.values.sessionStats).turns))] }), _jsxs(Text, { dimColor: true, children: ["Queued: ", count(view.queued), " \u00B7 Active jobs: ", count(view.jobs)] }), state.controlError && _jsx(Text, { color: theme.colors.context, children: safeText(state.controlError) }), state.presetError && _jsxs(Text, { color: theme.colors.context, children: ["Preset names unavailable: ", safeText(state.presetError)] }), state.modelError && _jsxs(Text, { color: theme.colors.context, children: ["Model catalog unavailable: ", safeText(state.modelError)] })] });
141
- });
142
- function record(value) {
143
- return value !== null && typeof value === 'object' && !Array.isArray(value) ? value : {};
144
- }
145
- function numeric(value) {
146
- return typeof value === 'number' && Number.isFinite(value) && value >= 0 ? value : undefined;
147
- }
148
- function count(value) { return value === undefined ? '?' : value.toLocaleString('en-US'); }
149
- function modelName(value) {
150
- const model = record(value);
151
- if (typeof model.model !== 'string' || typeof model.provider !== 'string')
152
- return 'unknown';
153
- return safeText(`${model.provider}/${model.model}${typeof model.reasoningEffort === 'string' ? ` (${model.reasoningEffort})` : ''}`);
154
- }
155
- function compactCost(total) {
156
- return `~¥${total.amount.toFixed(2)}${total.unknown || total.estimated ? '*' : ''}`;
157
- }
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes