dsh-code 1.0.7 → 1.2.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/README.en.md +70 -24
- package/README.md +71 -25
- package/bin/deepseek.mjs +202 -39
- package/cordis.patch.yml +13 -4
- package/lib/index.mjs +4063 -844
- package/lib/session-query.mjs +3 -2
- package/lib/startup.mjs +4 -4
- package/lib/{theme-DCT8Y2xf.mjs → theme-7u5Qo3dF.mjs} +657 -20
- package/lib/types/app.d.ts +100 -63
- package/lib/types/authorization-panel.d.ts +3 -3
- package/lib/types/git-workflow.d.ts +91 -2
- package/lib/types/i18n.d.ts +39 -0
- package/lib/types/index.d.ts +73 -1
- package/lib/types/input-split.d.ts +1 -1
- package/lib/types/kernel-panels.d.ts +86 -31
- package/lib/types/language-panel.d.ts +12 -0
- package/lib/types/locales/en.d.ts +450 -0
- package/lib/types/locales/zh.d.ts +9 -0
- package/lib/types/mentions.d.ts +7 -3
- package/lib/types/models.d.ts +14 -0
- package/lib/types/panel-accent.d.ts +28 -0
- package/lib/types/rainbow.d.ts +69 -0
- package/lib/types/render/animations.d.ts +42 -0
- package/lib/types/render/inspector.d.ts +26 -0
- package/lib/types/render/lines.d.ts +21 -1
- package/lib/types/render/markdown.d.ts +1 -1
- package/lib/types/render/projection.d.ts +95 -4
- package/lib/types/render/status.d.ts +8 -8
- package/lib/types/render/text.d.ts +6 -0
- package/lib/types/render/usage.d.ts +113 -0
- package/lib/types/session-directory.d.ts +17 -0
- package/lib/types/startup.d.ts +1 -1
- package/lib/types/terminal-title.d.ts +8 -0
- package/lib/types/theme-panel.d.ts +2 -2
- package/lib/types/theme.d.ts +271 -52
- package/lib/types/update-panel.d.ts +5 -5
- package/lib/types/update.d.ts +10 -1
- package/lib/types/version.d.ts +4 -3
- package/package.json +24 -7
- package/src/app.ts +1155 -478
- package/src/approval.ts +166 -166
- package/src/authorization-panel.ts +19 -16
- package/src/editor-keys.ts +371 -371
- package/src/git-workflow.ts +229 -3
- package/src/i18n.ts +68 -0
- package/src/index.ts +412 -76
- package/src/input-split.ts +3 -3
- package/src/kernel-panels.ts +471 -89
- package/src/keyboard.ts +5 -4
- package/src/language-panel.ts +53 -0
- package/src/locales/en.ts +489 -0
- package/src/locales/zh.ts +488 -0
- package/src/mentions.ts +8 -4
- package/src/models.ts +264 -212
- package/src/panel-accent.ts +41 -0
- package/src/presets.ts +1 -1
- package/src/provider-settings.ts +1 -1
- package/src/rainbow.ts +208 -0
- package/src/render/animations.ts +104 -6
- package/src/render/editor.ts +20 -20
- package/src/render/export.ts +116 -95
- package/src/render/inspector.ts +42 -0
- package/src/render/lines.ts +628 -415
- package/src/render/markdown.ts +15 -3
- package/src/render/projection.ts +429 -19
- package/src/render/status.ts +41 -35
- package/src/render/text.ts +14 -0
- package/src/render/tool-preview.ts +77 -77
- package/src/render/usage.ts +430 -0
- package/src/render/width.ts +2 -2
- package/src/session-directory.ts +8 -6
- package/src/session-query.ts +8 -4
- package/src/startup.ts +3 -3
- package/src/subagents.ts +229 -229
- package/src/terminal-title.ts +22 -5
- package/src/theme-panel.ts +17 -21
- package/src/theme.ts +281 -33
- package/src/update-panel.ts +37 -27
- package/src/update.ts +19 -3
- package/src/version.ts +58 -20
- package/src/whale-glyph.ts +23 -23
|
@@ -0,0 +1,488 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The Chinese message catalog: mirrors {@link en} key-for-key; the shared
|
|
3
|
+
* key union comes from the English catalog, so a missing key here fails
|
|
4
|
+
* typecheck.
|
|
5
|
+
*
|
|
6
|
+
* @module @deepseek-ai/dsh-tui/locales/zh
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
import type { MessageCatalog } from './en.ts'
|
|
10
|
+
|
|
11
|
+
export const zh: MessageCatalog = {
|
|
12
|
+
// Shared panel chrome
|
|
13
|
+
'panel.close': 'esc/q 关闭',
|
|
14
|
+
'panel.moveEnterSelect': '↑↓ 移动 · 回车 选择 · esc 关闭',
|
|
15
|
+
'panel.moveEnterSelectBack': '↑↓ 移动 · 回车 选择 · esc 返回 · q 关闭',
|
|
16
|
+
'panel.scrollEnds': '↑↓ 滚动 · pgup/pgdn 翻页 · g/G 首尾 · esc/q 关闭',
|
|
17
|
+
'panel.loading': '加载中…',
|
|
18
|
+
'panel.loadFailed': '加载失败',
|
|
19
|
+
'panel.noMatch': '没有匹配项',
|
|
20
|
+
'panel.emptyClose': 'esc 关闭',
|
|
21
|
+
'panel.searchIdle': '搜索:输入即过滤',
|
|
22
|
+
'panel.searchIdleStop': '搜索:输入即过滤 · esc 停止',
|
|
23
|
+
'panel.searchPrefix': '搜索:',
|
|
24
|
+
|
|
25
|
+
// /language panel
|
|
26
|
+
'language.title': '/language — 界面语言',
|
|
27
|
+
'language.hint': '↑↓ 移动 · 回车 应用 · esc/q 关闭',
|
|
28
|
+
|
|
29
|
+
// /theme panel
|
|
30
|
+
'theme.title': '/theme — 配色主题',
|
|
31
|
+
'theme.compact': '/theme · esc 关闭',
|
|
32
|
+
'theme.current': '当前',
|
|
33
|
+
'theme.dark.label': '暗色',
|
|
34
|
+
'theme.dark.description': 'DeepSeek 暗色配色(默认)',
|
|
35
|
+
'theme.light.label': '亮色',
|
|
36
|
+
'theme.light.description': '适合浅色终端的配色',
|
|
37
|
+
'theme.prismatic.label': '棱彩',
|
|
38
|
+
'theme.prismatic.description': '霓虹合成波配色(紫/品红/青)',
|
|
39
|
+
'theme.rainbow.label': '彩虹',
|
|
40
|
+
'theme.rainbow.description': '随机多彩配色(/rainbow 重掷)',
|
|
41
|
+
'theme.auto.label': '自动',
|
|
42
|
+
'theme.auto.description': '跟随终端;检测功能启用前使用暗色',
|
|
43
|
+
|
|
44
|
+
// /history panel
|
|
45
|
+
'history.title.prompts': '/history · {count} 条提示 · 输入即过滤',
|
|
46
|
+
'history.title.match': '/history · {count} 条中 {matches} 条匹配「{query}」',
|
|
47
|
+
'history.filterHint': '过滤{state},回车填入输入框',
|
|
48
|
+
'history.filterEmpty': '· 输入以搜索提示',
|
|
49
|
+
'history.filterQuery': '· {query}',
|
|
50
|
+
'history.empty': '没有匹配的提示',
|
|
51
|
+
'history.compact.none': '没有匹配的提示',
|
|
52
|
+
'history.footer': '↑↓ 移动 · g/G 首尾 · 回车 填入 · esc 关闭',
|
|
53
|
+
|
|
54
|
+
// /search panel
|
|
55
|
+
'search.title.type': '/search · 输入关键词后回车',
|
|
56
|
+
'search.title.hits': '/search · 「{query}」命中 {count} 条',
|
|
57
|
+
'search.title.hitsPlural': '/search · 「{query}」命中 {count} 条',
|
|
58
|
+
'search.hint': '{state} · 回车 搜索或恢复会话',
|
|
59
|
+
'search.hintEmpty': '输入以搜索历史会话',
|
|
60
|
+
'search.empty.idle': '对全部持久会话做全文检索',
|
|
61
|
+
'search.empty.noHits': '没有匹配的会话{loading}',
|
|
62
|
+
'search.compact.noResults': '暂无结果',
|
|
63
|
+
'search.compact.searching': '搜索中…',
|
|
64
|
+
'search.compact.error': '错误:{message}',
|
|
65
|
+
'search.footer': '↑↓ 移动 · 回车 搜索/恢复 · esc 关闭',
|
|
66
|
+
|
|
67
|
+
// /statusline panel
|
|
68
|
+
'statusline.title': '/statusline · 选项实时应用到下方状态栏',
|
|
69
|
+
|
|
70
|
+
// /schedule panel
|
|
71
|
+
'schedule.title': '/schedule · {count} 条活动提醒',
|
|
72
|
+
'schedule.titlePlural': '/schedule · {count} 条活动提醒',
|
|
73
|
+
'schedule.empty': '暂无活动提醒——模型通过 schedule_create 创建',
|
|
74
|
+
|
|
75
|
+
// Transcript document panel (/resume details)
|
|
76
|
+
'document.loading': '转录加载中…',
|
|
77
|
+
'document.compact': '转录 · esc 关闭',
|
|
78
|
+
'document.footer': '行 {from}-{to}/{total} · ↑↓/pg/g/G · t/esc 关闭',
|
|
79
|
+
|
|
80
|
+
// /review picker
|
|
81
|
+
'review.picker.title': '/review · 选择审查目标',
|
|
82
|
+
'review.picker.uncommitted': '审查未提交的改动(staged / unstaged / 新文件)',
|
|
83
|
+
'review.picker.branch': '选择基线分支对比(列出本地分支)',
|
|
84
|
+
'review.picker.commit': '审查当前分支的某个提交(列出近期提交)',
|
|
85
|
+
'review.picker.custom': '自定义审查关注点(输入文字)',
|
|
86
|
+
'review.picker.customHint': '输入关注点后回车开始审查',
|
|
87
|
+
'review.picker.branches': '{filtered}/{total} 个分支',
|
|
88
|
+
'review.picker.commits': '{filtered}/{total} 个提交',
|
|
89
|
+
'review.picker.loadingBranches': '分支加载中…',
|
|
90
|
+
'review.picker.loadingCommits': '提交加载中…',
|
|
91
|
+
'review.picker.empty': '没有候选',
|
|
92
|
+
'review.picker.noMatch': '没有匹配项',
|
|
93
|
+
'review.picker.loading': '加载中…',
|
|
94
|
+
'review.picker.loadFailed': '加载失败',
|
|
95
|
+
'review.picker.compact': '选择审查目标',
|
|
96
|
+
'review.picker.footer': '↑↓ 移动 · 回车 选择 · esc 返回 · q 关闭',
|
|
97
|
+
|
|
98
|
+
// Review result summary
|
|
99
|
+
'review.summary.untagged': '未分级×{n}',
|
|
100
|
+
'review.summary.incorrect': 'patch 不正确',
|
|
101
|
+
'review.summary.correctClean': '未发现问题',
|
|
102
|
+
'review.summary.correct': 'patch 正确',
|
|
103
|
+
'review.summary.noConclusion': '审查完成:没有结构化结论',
|
|
104
|
+
'review.summary.zero': '审查完成:0 项发现 · {verdict}',
|
|
105
|
+
'review.summary.count': '审查完成:{count} 项发现({parts})',
|
|
106
|
+
'review.summary.countVerdict': '审查完成:{count} 项发现({parts}) · {verdict}',
|
|
107
|
+
|
|
108
|
+
// Review runner notices
|
|
109
|
+
'review.notice.started': '审查已在只读权限下开始',
|
|
110
|
+
'review.notice.failed': '审查失败:{message}',
|
|
111
|
+
'review.notice.unavailable': '审查不可用:{message}',
|
|
112
|
+
|
|
113
|
+
// LOCAL_COMMAND descriptions
|
|
114
|
+
'cmd.help': '显示本帮助',
|
|
115
|
+
'cmd.model': '切换模型并管理供应商',
|
|
116
|
+
'cmd.effort': '调整当前模型的推理档位',
|
|
117
|
+
'cmd.mode': '查看或选择 Agent 预设(/mode [preset])',
|
|
118
|
+
'cmd.permission': '查看或选择权限预设(/permission [preset])',
|
|
119
|
+
'cmd.new': '新建并切换到新会话(/new [preset])',
|
|
120
|
+
'cmd.fork': '从最近的完成回合分叉(/fork [event-seq])',
|
|
121
|
+
'cmd.resume': '浏览或恢复历史会话(/resume [id|前缀])',
|
|
122
|
+
'cmd.search': '跨历史会话全文检索(/search [关键词])',
|
|
123
|
+
'cmd.plugin': '查看插件组成状态',
|
|
124
|
+
'cmd.update': '一键对齐升级 dsh-code、宿主与 profile 插件',
|
|
125
|
+
'cmd.jobs': '查看后台任务',
|
|
126
|
+
'cmd.schedule': '查看活动提醒(经 schedule 工具创建)',
|
|
127
|
+
'cmd.statusline': '自定义状态栏显示项',
|
|
128
|
+
'cmd.theme': '切换配色主题',
|
|
129
|
+
'cmd.language': '切换界面语言(/language [en|zh])',
|
|
130
|
+
'cmd.rainbow': '重掷或指定彩虹配色(/rainbow [seed])',
|
|
131
|
+
'cmd.animation': '开关计时动画(/animation [on|off])',
|
|
132
|
+
'cmd.history': '搜索并复用历史提示词',
|
|
133
|
+
'cmd.queue': '管理等待下一轮的消息',
|
|
134
|
+
'cmd.usage': '查看本会话的 token 用量',
|
|
135
|
+
'cmd.agents': '查看本会话的子代理',
|
|
136
|
+
'cmd.todos': '查看完整待办列表',
|
|
137
|
+
'cmd.subagent': '选择子代理使用的模型',
|
|
138
|
+
'cmd.vscode-keys': '放行 ctrl+r 进 VS Code 系终端',
|
|
139
|
+
'cmd.delete': '删除会话及其子代理线程',
|
|
140
|
+
'cmd.clear': '清屏',
|
|
141
|
+
'cmd.export': '导出转录为 Markdown(/export [path])',
|
|
142
|
+
'cmd.title': '重命名当前会话(/title <text>)',
|
|
143
|
+
'cmd.copy': '复制最近一条完整回复',
|
|
144
|
+
'cmd.diff': '查看 Git 改动(/diff [--staged|ref])',
|
|
145
|
+
'cmd.review': '在当前会话内审查 Git 改动(/review [说明])',
|
|
146
|
+
'cmd.quit': '退出',
|
|
147
|
+
|
|
148
|
+
// Help overlay
|
|
149
|
+
'help.keysTitle': ' 快捷键',
|
|
150
|
+
'help.key.submit': '回车 提交 · ctrl+j / alt+enter 换行 · ↑↓ 历史 · tab 补全',
|
|
151
|
+
'help.key.mentions': '@ 引用工作区文件或历史会话',
|
|
152
|
+
'help.key.inspector': 'ctrl+o 历史详情 · ctrl/alt+r 思考 · shift+tab 权限预设',
|
|
153
|
+
'help.key.cancel': 'esc 中断运行中的回合 · ctrl+c 取消/清空/退出 · ctrl+d 退出',
|
|
154
|
+
'help.key.queue': '空输入框 tab 选择排队或插队 · /queue 管理已排队消息 · Delete 取消最新一条',
|
|
155
|
+
'help.key.edit': 'ctrl+k 剪切到行尾 · ctrl+u 清空行 · ctrl+a / ctrl+e 行首尾',
|
|
156
|
+
'help.commandsTitle': ' 命令',
|
|
157
|
+
'help.skillsTitle': ' 技能',
|
|
158
|
+
'help.footer': '↑↓ 滚动 · pgup/pgdn 翻页 · g/G 首尾 · esc/q 关闭',
|
|
159
|
+
'help.compact': '/help · esc/q 关闭',
|
|
160
|
+
'panel.queue.title': '/queue — {count} 条排队消息 · 行 {from}-{to}',
|
|
161
|
+
'panel.queue.empty': ' 下一轮没有排队消息',
|
|
162
|
+
'panel.queue.attachments': '[含附件:只读]',
|
|
163
|
+
'panel.queue.footerBusy': '↑↓ 选择 · enter 插队 · e 编辑文本 · d 删除 · esc/q 关闭',
|
|
164
|
+
'panel.queue.footerIdle': '↑↓ 选择 · e 编辑文本 · d 删除 · esc/q 关闭',
|
|
165
|
+
'panel.queue.editFooter': '输入 · ←→ 移动 · enter 保存 · esc 取消',
|
|
166
|
+
'panel.queue.compact': '/queue · esc/q 关闭',
|
|
167
|
+
'panel.usage.title': '/usage — 本会话用量',
|
|
168
|
+
'panel.usage.compact': '/usage · esc/q 关闭',
|
|
169
|
+
'panel.usage.footer': '↑↓ 滚动 · pgup/pgdn 翻页 · g/G 首尾 · esc/q 关闭',
|
|
170
|
+
'panel.usage.totals': '总量(整个会话)',
|
|
171
|
+
'panel.usage.uncached': '未命中输入',
|
|
172
|
+
'panel.usage.cacheWrite': '缓存写入',
|
|
173
|
+
'panel.usage.cacheRead': '缓存读取',
|
|
174
|
+
'panel.usage.output': '输出',
|
|
175
|
+
'panel.usage.total': '合计',
|
|
176
|
+
'panel.usage.cacheHit': '缓存命中',
|
|
177
|
+
'panel.usage.turns': '按回合',
|
|
178
|
+
'panel.usage.byModel': '按模型',
|
|
179
|
+
'panel.usage.colTurns': '回合数',
|
|
180
|
+
'panel.usage.unknownModel': '未标注模型',
|
|
181
|
+
'panel.usage.colTurn': '回合',
|
|
182
|
+
'panel.usage.colTotal': '合计',
|
|
183
|
+
'panel.usage.colUncached': '未命中',
|
|
184
|
+
'panel.usage.colCacheRead': '缓存读',
|
|
185
|
+
'panel.usage.colCacheHit': '命中率',
|
|
186
|
+
'panel.usage.colCacheWrite': '缓存写',
|
|
187
|
+
'panel.usage.colOut': '输出',
|
|
188
|
+
'panel.usage.colThink': '思考',
|
|
189
|
+
'panel.usage.colModel': '模型',
|
|
190
|
+
'panel.usage.partialNote': '+ 表示这一组里有回合没有上报该项,数字只统计了已上报的部分',
|
|
191
|
+
'panel.usage.unavailable': '本部署没有挂载用量统计(缺少 dsh-token-meter)',
|
|
192
|
+
'panel.usage.noTurns': '还没有已完成的回合',
|
|
193
|
+
'status.cycleHint': '(shift+tab 切换)',
|
|
194
|
+
'approval.compact': '审批{queued} · 回车/y 允许 · esc/n 拒绝',
|
|
195
|
+
'approval.overflow': '… 还有 {count} 行 · ctrl+o 查看完整调用',
|
|
196
|
+
'question.compact.plan': '计划审查 · esc 取消',
|
|
197
|
+
'question.compact.normal': '问题 · esc 取消',
|
|
198
|
+
'approval.submitted': '已提交…',
|
|
199
|
+
'approval.footer': '↑↓ 移动 · 回车确认 · y/n/d 快速选择 · esc 拒绝',
|
|
200
|
+
'question.footer': '↑↓ 移动 · 1-9 选择 · 空格开关 · 回车提交 · esc 取消',
|
|
201
|
+
'question.custom': '输入自定义答案',
|
|
202
|
+
'question.submitted': '已提交…',
|
|
203
|
+
'question.customNoOptions': '↑↓/pgup/pgdn 滚动 · 输入答案 · 回车提交 · esc 中断',
|
|
204
|
+
'question.customOptions': '↑↓/pgup/pgdn 滚动 · 输入答案 · 回车提交 · tab/esc 或清空退格:返回选项',
|
|
205
|
+
'question.multiOptions': '↑↓ 移动 · pgup/pgdn 滚动 · 空格/1-9 开关 · 回车提交 · c 自定义 · esc 中断',
|
|
206
|
+
'question.singleOptions': '↑↓ 移动 · pgup/pgdn 滚动 · 1-9 选择 · c 自定义 · esc 中断',
|
|
207
|
+
'question.switch': ' · ←→/ctrl+p/n 切换问题',
|
|
208
|
+
'question.title.plan': '📋 计划审查',
|
|
209
|
+
'question.title.normal': '❓ 问题',
|
|
210
|
+
|
|
211
|
+
|
|
212
|
+
// Composer and status chrome
|
|
213
|
+
'composer.placeholder': '输入消息 · / 命令 · @ 引用 · tab 插队',
|
|
214
|
+
'composer.placeholderSteer': '插队进本轮 · tab 改为排队等下一轮',
|
|
215
|
+
'notice.submitMode.queue': '发送 → 排队等下一轮',
|
|
216
|
+
'notice.submitMode.steer': '发送 → 插队进本轮(仅回合运行中;空闲时直接发出)',
|
|
217
|
+
// 结算后的消息标记:不是空闲时直接发送的那种
|
|
218
|
+
'entry.delivery.queued': '排队',
|
|
219
|
+
'entry.delivery.steered': '插队',
|
|
220
|
+
'status.shiftTabHint': '(shift+tab 切换)',
|
|
221
|
+
'status.label.turns': '回合',
|
|
222
|
+
'status.label.steps': '步骤',
|
|
223
|
+
'status.label.modelTime': '模型',
|
|
224
|
+
'status.label.latency': '延迟',
|
|
225
|
+
'status.label.tokensPerSec': ' tokens/秒',
|
|
226
|
+
'status.label.tool': '工具',
|
|
227
|
+
'status.label.cache': '缓存',
|
|
228
|
+
'status.label.in': '入',
|
|
229
|
+
'status.label.out': '出',
|
|
230
|
+
'status.label.mode': '/mode',
|
|
231
|
+
'status.label.context': '上下文',
|
|
232
|
+
|
|
233
|
+
// Frozen band
|
|
234
|
+
'frozen.keysGoTo': '按键交给{owner} · esc {action}',
|
|
235
|
+
'frozen.action.rejects': '拒绝',
|
|
236
|
+
'frozen.action.cancels': '取消',
|
|
237
|
+
'frozen.action.closes': '关闭',
|
|
238
|
+
|
|
239
|
+
// Relative time (panel list timestamps)
|
|
240
|
+
'time.justNow': '刚刚',
|
|
241
|
+
'time.minutesAgo': '{n} 分钟前',
|
|
242
|
+
'time.hoursAgo': '{n} 小时前',
|
|
243
|
+
'time.daysAgo': '{n} 天前',
|
|
244
|
+
|
|
245
|
+
// Common notices
|
|
246
|
+
'notice.themeSaved': '主题 → {name}',
|
|
247
|
+
'notice.themeRainbow': '主题 → rainbow · 种子 {seed} · /rainbow 再随机',
|
|
248
|
+
'notice.rainbowRolled': '彩虹 · 种子 {seed} · /rainbow 再随机 · /rainbow {seed} 锁定',
|
|
249
|
+
'notice.languageSaved': '语言 → {name}',
|
|
250
|
+
'notice.themeSaveFailed': '主题保存失败:{message}',
|
|
251
|
+
'notice.languageSaveFailed': '语言保存失败:{message}',
|
|
252
|
+
'notice.alreadyActive': '该会话已是当前会话',
|
|
253
|
+
'notice.queueCancelled': '已取消排队消息',
|
|
254
|
+
'notice.queueActionFailed': '队列操作失败:{message}',
|
|
255
|
+
'notice.queueUnavailable': '该消息已不在队列中',
|
|
256
|
+
'notice.queueSteerUnavailable': '仅运行中的回合可以插队',
|
|
257
|
+
'notice.queueEditEmpty': '排队消息不能为空',
|
|
258
|
+
'notice.queueEdited': '已编辑排队消息',
|
|
259
|
+
'notice.queueSteered': '已将排队消息插入本轮',
|
|
260
|
+
'notice.historySaveFailed': '历史保存失败:{message}',
|
|
261
|
+
'notice.turnCancelled': '回合已取消 —— Ctrl+C 或 /quit 退出',
|
|
262
|
+
'notice.turnCancelledKeepQueue': '回合已取消 —— 所有待处理消息已保留 · Ctrl+C 或 /quit 退出',
|
|
263
|
+
'notice.noSessionYet': '还没有会话——先发一条消息开始',
|
|
264
|
+
'notice.usage.animation': '用法:/animation [on|off]',
|
|
265
|
+
'notice.usage.language': '用法:/language [en|zh]',
|
|
266
|
+
'notice.usage.rainbow': '用法:/rainbow [seed]',
|
|
267
|
+
'notice.imageCancelled': '图片提交已取消',
|
|
268
|
+
'notice.themeConfigUnreadable': '主题配置无法读取,使用暗色:{message}',
|
|
269
|
+
'notice.languageConfigUnreadable': '语言配置无法读取,使用英文:{message}',
|
|
270
|
+
'notice.animationsConfigUnreadable': '动画配置无法读取,保持开启:{message}',
|
|
271
|
+
'notice.statuslineConfigUnreadable': '状态栏配置无法读取,使用默认:{message}',
|
|
272
|
+
'notice.sessionSearchUnavailable': '此部署未启用会话检索',
|
|
273
|
+
'notice.subagentsReadOnly': '子代理会话为只读',
|
|
274
|
+
'notice.statuslineSaveFailed': '状态栏保存失败:{message}',
|
|
275
|
+
'notice.animationsSaveFailed': '动画保存失败:{message}',
|
|
276
|
+
'notice.commandRegistryMissing': '当前组合未加载命令注册表',
|
|
277
|
+
'notice.commandFallbackFailed': '命令回退失败:{message}',
|
|
278
|
+
'notice.commandFailed': '命令执行失败:{message}',
|
|
279
|
+
'notice.invalidReference': '会话引用无效:{message}',
|
|
280
|
+
'notice.messageFailed': '{kind}失败:{message}',
|
|
281
|
+
'notice.referenceFailed': '会话引用失败:{message}',
|
|
282
|
+
'notice.activationFailed': '会话激活失败:{message}',
|
|
283
|
+
'notice.creationFailed': '会话创建失败:{message}',
|
|
284
|
+
'notice.modeChanged': '模式 → {value}',
|
|
285
|
+
'notice.modeSwitchFailed': '模式切换失败:{message}',
|
|
286
|
+
'notice.permissionChanged': '权限 → {value}',
|
|
287
|
+
'notice.permissionChangeFailed': '权限切换失败:{message}',
|
|
288
|
+
'notice.cancelFailed': '取消失败:{message}',
|
|
289
|
+
'notice.modeChangeFailed': '模式变更失败:{message}',
|
|
290
|
+
'notice.modelNotDefault': '模型切换已应用于当前会话,但未保存为默认值:{message}',
|
|
291
|
+
'notice.modelSelectionRejected': '模型选择被拒绝:{message}——请重新打开 /model 选择',
|
|
292
|
+
'notice.exported': '已导出到 {path}',
|
|
293
|
+
'notice.exportFailed': '导出失败:{message}',
|
|
294
|
+
'notice.resumeFailed': '恢复失败:{message}',
|
|
295
|
+
'notice.forkFailed': '分叉失败:{message}',
|
|
296
|
+
'notice.sessionSwitchFailed': '会话切换失败:{message}',
|
|
297
|
+
'notice.switchQueued': '当前回合结束后将切换到 {label} · 可用 /resume cancel 取消',
|
|
298
|
+
'notice.reviewStarted': '审查已在只读权限下开始',
|
|
299
|
+
'notice.reviewFailed': '审查失败:{message}',
|
|
300
|
+
'notice.reviewUnavailable': '审查不可用:{message}',
|
|
301
|
+
'notice.startupImages': '正在处理 {count} 张启动图片…',
|
|
302
|
+
'notice.startupImagesAttached': '已附加 {count} 张启动图片',
|
|
303
|
+
'notice.initialPromptFailed': '初始提示失败:{message}',
|
|
304
|
+
'notice.rejected': '已拒绝——请在下方说明需要怎样调整(会影响下一步)',
|
|
305
|
+
'notice.attachmentAlready': '已附加 {name}',
|
|
306
|
+
'notice.attachmentsChecking': '正在检查 {count} 个附件…',
|
|
307
|
+
'notice.attachmentsAlready': '这些附件已经附加',
|
|
308
|
+
'notice.attachmentDraftChanged': '附件放置位置附近的草稿已变化,请重新放置文件',
|
|
309
|
+
'notice.attachmentsReady': '{count} 个附件已准备好,将随下一条消息发送',
|
|
310
|
+
'notice.attachmentFailed': '附件失败:{message}',
|
|
311
|
+
'notice.imageChecking': '正在检查图片 {name}…',
|
|
312
|
+
'notice.imageDraftChanged': '图片引用附近的草稿已变化,请重新选择',
|
|
313
|
+
'notice.imageReady': '{name} 已准备好,将随下一条消息发送',
|
|
314
|
+
'notice.imageFailed': '图片附件失败:{message}',
|
|
315
|
+
'notice.cancelBeforeExit': '退出前请先取消正在运行的回合(Esc 或 Ctrl+C)',
|
|
316
|
+
'notice.commandAttachments': '命令不能携带附件;该行将作为提示发送给模型',
|
|
317
|
+
'notice.copyFailed': '复制失败:{message}',
|
|
318
|
+
'notice.vscodeKeysFailed': 'vscode-keys 失败:{message}',
|
|
319
|
+
'notice.animationState': '动画{state}',
|
|
320
|
+
'notice.deleteFailed': '删除失败:{message}',
|
|
321
|
+
'notice.modelChangedPlaceholder': '模型 → {model} · 历史图片将以文本占位符发送',
|
|
322
|
+
'notice.modelNextStep': '模型 → 下一步使用 {model}',
|
|
323
|
+
'notice.modelSwitchFailed': '模型切换失败:{message}',
|
|
324
|
+
'notice.loggedIn': '已登录 {provider};请选择模型',
|
|
325
|
+
'notice.loggedOut': '已退出 {provider}',
|
|
326
|
+
'notice.providerSaved': '供应商配置已保存:{provider}{suffix}',
|
|
327
|
+
'notice.apiKeyRemoved': '已移除 {provider} 的 API 密钥',
|
|
328
|
+
'notice.providerRemoved': '已移除供应商:{provider}',
|
|
329
|
+
'notice.providerUnavailable': '当前 profile 不支持供应商配置',
|
|
330
|
+
'notice.apiKeyUnavailable': '当前 profile 不支持移除 API 密钥',
|
|
331
|
+
'notice.providerRemovalUnavailable': '当前 profile 不支持移除供应商',
|
|
332
|
+
'notice.loginIdleOnly': '只有 Agent 空闲时才能登录供应商',
|
|
333
|
+
'notice.loginUnavailable': '当前 profile 不支持供应商登录',
|
|
334
|
+
'notice.logoutUnavailable': '当前 profile 不支持供应商登出',
|
|
335
|
+
'notice.modeChangedSimple': '模式 → {value}',
|
|
336
|
+
'notice.permissionChangedSimple': '权限 → {value}',
|
|
337
|
+
'notice.subagentsChanged': '子代理 → {value}',
|
|
338
|
+
'notice.subagentsInherited': '子代理 → 跟随当前模型',
|
|
339
|
+
'notice.subagentChangeFailed': '子代理模型切换失败:{message}',
|
|
340
|
+
'notice.modelMissing': '当前模型不在目录中',
|
|
341
|
+
'notice.effortUnavailable': '推理档位暂不可用(能力查询失败)——请重试',
|
|
342
|
+
'notice.modelLookupFailed': '模型查询失败:{message}',
|
|
343
|
+
'notice.diffFailed': 'diff 失败:{message}',
|
|
344
|
+
|
|
345
|
+
// Additional panel chrome
|
|
346
|
+
'panel.footer.chooseSwitch': '↑↓ 移动 · 回车 切换 · r 刷新 · esc 关闭',
|
|
347
|
+
'panel.footer.chooseSelect': '↑↓ 移动 · 回车 选择 · r 刷新 · esc 关闭',
|
|
348
|
+
'panel.footer.inspectDetails': '↑↓ 查看 · 回车 详情 · r 刷新 · esc 关闭',
|
|
349
|
+
'panel.footer.inspectRefresh': '↑↓ 查看 · r 刷新 · esc 关闭',
|
|
350
|
+
'panel.footer.resume': 'tab/←→ 筛选 · ↑↓/pg 翻页 · ctrl+f 搜索 · e 详情 · t 转录 · d 删除 · 回车恢复',
|
|
351
|
+
'panel.footer.transcript': '行 {from}-{to}/{total} · ↑↓/pg/g/G · t/esc 关闭',
|
|
352
|
+
'panel.footer.history': '↑↓ 移动 · g/G 首尾 · 回车填入 · esc 关闭',
|
|
353
|
+
'panel.footer.review': '↑↓ 移动 · 回车选择 · esc 返回 · q 关闭',
|
|
354
|
+
'panel.footer.statusline': '↑↓ 移动 · 空格开关 · ←→ 调整顺序 · d 恢复默认 · esc 关闭',
|
|
355
|
+
'panel.footer.schedule': 'esc/q 关闭{more} · 模型通过 schedule_create 创建提醒',
|
|
356
|
+
'panel.mode.title': '/mode · 当前 {current}',
|
|
357
|
+
'panel.permission.title': '/permission · 当前 {current}',
|
|
358
|
+
'panel.plugin.title': '/plugin · 插件加载状态',
|
|
359
|
+
'panel.jobs.title': '/jobs · 后台任务 · {count}',
|
|
360
|
+
'panel.resume.deleteTitle': '永久删除 {target}?此操作无法撤销,子代理线程也会删除',
|
|
361
|
+
'panel.resume.title': '/resume{mode}{search} · {toolbar}',
|
|
362
|
+
'panel.noActiveReminders': '暂无活动提醒——模型通过 schedule_create 创建',
|
|
363
|
+
'panel.notMounted': '未加载',
|
|
364
|
+
'panel.broken': '异常:{message}',
|
|
365
|
+
'panel.live': '运行中',
|
|
366
|
+
'panel.parent': '父会话 {id}',
|
|
367
|
+
'panel.deleteMode': '删除模式',
|
|
368
|
+
'panel.searching': '搜索中',
|
|
369
|
+
'panel.noPresets': '暂无预设',
|
|
370
|
+
'panel.noPermissions': '暂无权限预设',
|
|
371
|
+
'panel.noJobs': '暂无后台任务',
|
|
372
|
+
'panel.diff.compact': '{title} · {files} 个文件 · esc/q 关闭',
|
|
373
|
+
'panel.diff.noFiles': '没有文件',
|
|
374
|
+
'panel.diff.footer': '↑/↓ 滚动 · g/G 首尾 · esc/q 关闭',
|
|
375
|
+
'panel.todos.compact': '待办 · esc/q 关闭',
|
|
376
|
+
'panel.todos.title': '待办 · 已完成 {done}/{total} · 进行中 {active} · 待处理 {pending} · 行 {from}-{to}/{rows}',
|
|
377
|
+
'panel.todos.empty': '暂无待办',
|
|
378
|
+
'panel.todos.footer': '↑↓ 滚动 · pgup/pgdn 翻页 · g/G 首尾 · esc/q 关闭',
|
|
379
|
+
'panel.verbose.compact': '历史详情 · ctrl+o / esc / q 关闭',
|
|
380
|
+
'panel.verbose.footer': '←→ 条目 · ↑↓ 滚动 · pgup/pgdn 翻页 · g/G 首尾 · ctrl+o/esc/q 关闭',
|
|
381
|
+
'panel.model.compact': '/model · {state}{providers} · {tail}',
|
|
382
|
+
'panel.model.noMatch': '没有匹配「{query}」的模型',
|
|
383
|
+
'panel.model.compactNoMatch': '没有匹配「{query}」',
|
|
384
|
+
'panel.model.loading': '加载中…',
|
|
385
|
+
'panel.model.error': '错误',
|
|
386
|
+
'panel.model.noModels': '暂无可用模型',
|
|
387
|
+
'panel.model.selectTitle': '/model — 选择模型',
|
|
388
|
+
'panel.model.matches': '{filtered}/{total} 个匹配「{query}」',
|
|
389
|
+
'panel.model.footer.filter': '输入过滤 · r 重试 · esc/q 关闭',
|
|
390
|
+
'panel.model.footer.filtered': '退格编辑 · esc 关闭',
|
|
391
|
+
'panel.model.title': '/model — 选择模型',
|
|
392
|
+
'panel.model.titleCount': '/model — 选择模型 · {index}/{total}',
|
|
393
|
+
'panel.model.titleMatches': '/model — 选择模型 · {filtered}/{total} 个匹配「{query}」',
|
|
394
|
+
'panel.model.footer.select': '输入过滤 · ↑↓ 移动 · pgup/pgdn 翻页 · 回车选择{providers} · r 重试 · esc/q 关闭',
|
|
395
|
+
'panel.model.footer.filteredSelect': '↑↓ 移动 · pgup/pgdn 翻页 · 回车选择 · 退格编辑 · esc 关闭',
|
|
396
|
+
'panel.model.providers': 'tab 供应商',
|
|
397
|
+
'panel.provider.failure': '不可用的供应商:{providers}',
|
|
398
|
+
'panel.provider.loading': '供应商加载中…',
|
|
399
|
+
'panel.provider.empty': '暂无可配置的供应商',
|
|
400
|
+
'panel.provider.notConfigured': '未配置',
|
|
401
|
+
'panel.provider.configured': '已配置',
|
|
402
|
+
'panel.provider.keyMissing': '缺少密钥',
|
|
403
|
+
'panel.provider.keyStatusUnavailable': '无法获取密钥状态',
|
|
404
|
+
'panel.provider.auth': '供应商认证',
|
|
405
|
+
'panel.provider.active': '活动',
|
|
406
|
+
'panel.provider.dormant': '未启用',
|
|
407
|
+
'panel.provider.readOnly': '只读',
|
|
408
|
+
'panel.provider.custom': '自定义',
|
|
409
|
+
'panel.provider.notConfiguredDivider': '── 未配置 ──',
|
|
410
|
+
'panel.provider.title': '/model — 供应商',
|
|
411
|
+
'panel.provider.titleCount': '/model — 供应商 · {index}/{total}',
|
|
412
|
+
'panel.provider.state': '{route} · {value}',
|
|
413
|
+
'panel.provider.key': '密钥 {value}',
|
|
414
|
+
'panel.provider.authConfigured': '供应商认证',
|
|
415
|
+
'panel.provider.noKey': '缺少密钥',
|
|
416
|
+
'panel.provider.noLogin': '未配置',
|
|
417
|
+
'panel.provider.loginStatusUnavailable': '登录状态不可用:{message}',
|
|
418
|
+
'panel.provider.noConfiguredKey': '该供应商没有已配置的 API 密钥可移除',
|
|
419
|
+
'panel.provider.readOnlyKey': '该 API 密钥由环境以只读方式提供',
|
|
420
|
+
'panel.provider.notRemovable': '该供应商配置不可移除',
|
|
421
|
+
'panel.provider.noLoginFlow': '该供应商不支持交互式登录',
|
|
422
|
+
'panel.provider.loginRunning': '该供应商已有登录尝试正在进行',
|
|
423
|
+
'panel.provider.noLoginRecord': '该供应商没有可移除的登录记录',
|
|
424
|
+
'panel.provider.readOnlyLogin': '该登录记录为只读',
|
|
425
|
+
'panel.provider.notManaged': '该供应商不受 Harness settings 管理',
|
|
426
|
+
'panel.providers.compact': '/model providers · 回车配置 · d 删除密钥 · esc 返回',
|
|
427
|
+
'panel.providers.footer': '↑↓ 移动 · 回车配置 · l 登录 · o 登出 · d 删除密钥 · x 删除供应商 · r 重试 · esc 返回',
|
|
428
|
+
'panel.update.compact': '/update · {summary}',
|
|
429
|
+
'panel.update.checking': '检查中…',
|
|
430
|
+
'panel.update.probeFailed': '检查失败',
|
|
431
|
+
'panel.update.updating': '更新中…',
|
|
432
|
+
'panel.update.installed': '已安装——重启后生效',
|
|
433
|
+
'panel.update.failed': '失败',
|
|
434
|
+
'panel.update.upToDate': '已是最新',
|
|
435
|
+
'panel.update.aheadOfNpm': '新于 npm',
|
|
436
|
+
'panel.update.enter': '回车更新',
|
|
437
|
+
'panel.update.blocked': '已阻止',
|
|
438
|
+
'panel.update.title': '/update · 对齐升级',
|
|
439
|
+
'panel.auth.methodsFooter': '↑↓ 选择 · 回车继续 · esc/q 返回',
|
|
440
|
+
'panel.auth.answerFooter': '回车回答 · c 复制 URL/代码 · esc 取消登录',
|
|
441
|
+
'panel.auth.title': '/model · 登录 {provider}',
|
|
442
|
+
'panel.auth.waiting': '等待供应商响应…',
|
|
443
|
+
'panel.auth.compact': '供应商登录 · esc 取消',
|
|
444
|
+
'panel.auth.logoutCompact': 'y 登出 · n/esc 返回',
|
|
445
|
+
'panel.auth.logoutTitle': '/model · 退出供应商登录',
|
|
446
|
+
'panel.auth.removeRecord': '移除 {provider} 的登录记录',
|
|
447
|
+
'panel.auth.unchanged': '供应商 endpoint 和模型配置保持不变',
|
|
448
|
+
'panel.auth.working': '处理中…',
|
|
449
|
+
'panel.auth.logoutFooter': 'y 确认 · n/esc 返回',
|
|
450
|
+
'panel.setup.compact': '供应商配置 · 终端过窄 · esc 返回',
|
|
451
|
+
'panel.setup.noDonors': '暂无声明推理档位的模型;请用 e 声明,或手动填写设置',
|
|
452
|
+
'panel.setup.copyInto': '原样复制到 {id}',
|
|
453
|
+
'panel.setup.copyTitle': '/model — 复制推理档位',
|
|
454
|
+
'panel.setup.copyFooter': '↑↓ 移动 · 回车复制 · esc 返回',
|
|
455
|
+
'panel.setup.title': '/model — 配置 {provider}',
|
|
456
|
+
'panel.setup.footer': '↑↓ 移动 · ←→ 输入/输出 · 空格移除 · e 推理档位 · c 复制推理档位 · tab 发现 · 回车保存 · esc 返回',
|
|
457
|
+
'panel.discovery.compact': '模型发现 · 终端过窄 · esc 返回',
|
|
458
|
+
'panel.discovery.loading': '正在发现模型…',
|
|
459
|
+
'panel.discovery.empty': '端点未提供模型;请在配置页手动添加 ID',
|
|
460
|
+
'panel.discovery.summary': '共 {advertised} 个 · 新增 {newCount} 个 · 已选 {checked} 个',
|
|
461
|
+
'panel.discovery.title': '/model — 发现 {provider}',
|
|
462
|
+
'panel.discovery.footer': '↑↓ 移动 · 空格勾选 · 回车采用 · f 重新获取 · esc 返回',
|
|
463
|
+
'panel.update.footer.probe': '检查中… · esc 关闭',
|
|
464
|
+
'panel.update.footer.error': 'r 重新检查 · esc 关闭',
|
|
465
|
+
'panel.update.footer.apply': '更新中… · ↑↓ 滚动 · esc 等待',
|
|
466
|
+
'panel.update.footer.current': '已是最新 · r 重新检查 · esc 关闭',
|
|
467
|
+
'panel.update.footer.ahead': '新于 npm,不降级 · r 重新检查 · esc 关闭',
|
|
468
|
+
'panel.update.footer.update': '回车更新 · r 重新检查 · esc 关闭',
|
|
469
|
+
'panel.update.footer.blocked': '已阻止 · r 重新检查 · esc 关闭',
|
|
470
|
+
'panel.footer.effortEmpty': 'esc 返回',
|
|
471
|
+
'panel.footer.effort': '↑↓ 移动 · 回车 应用 · esc/q 返回',
|
|
472
|
+
'panel.effort.title': '/model — {provider} · {model} 的推理档位',
|
|
473
|
+
'panel.effort.empty': '此模型未声明推理档位——使用供应商默认设置',
|
|
474
|
+
'panel.default': '默认',
|
|
475
|
+
'panel.footer.agents': '↑↓ 移动 · 回车/t 查看转录 · r 刷新 · esc 关闭',
|
|
476
|
+
'panel.agents.title': '/agents · {live} 个运行中 · 共 {total} 个',
|
|
477
|
+
'panel.document.title': '转录 · {id}',
|
|
478
|
+
'panel.subagent.transcriptTitle': '子代理 · {id}',
|
|
479
|
+
'panel.footer.subagent': '↑↓ 移动 · 回车 应用 · r 刷新 · esc 关闭',
|
|
480
|
+
'panel.subagent.title': '/subagent — 子代理使用的模型',
|
|
481
|
+
'panel.subagent.override': ' · 当前覆盖:{value}',
|
|
482
|
+
'panel.subagent.inherit': '跟随当前模型(/model 切换会同步)',
|
|
483
|
+
'panel.statusline.compact': '/statusline · esc 关闭',
|
|
484
|
+
'panel.schedule.compact': '/schedule · {summary}',
|
|
485
|
+
'panel.schedule.none': '暂无活动提醒',
|
|
486
|
+
'panel.schedule.more': ' · 另有 {count} 条',
|
|
487
|
+
'panel.schedule.footer': 'esc/q 关闭{more} · 模型通过 schedule_create 创建提醒',
|
|
488
|
+
}
|
package/src/mentions.ts
CHANGED
|
@@ -6,7 +6,10 @@
|
|
|
6
6
|
* canonical `@[label](dsh-session:…)` tokens; on submit the text is parsed
|
|
7
7
|
* back into readable `@label` text plus structured references, snapshots are
|
|
8
8
|
* injected via `agent.inject()` before the readable message wakes the driver
|
|
9
|
-
* (`followup
|
|
9
|
+
* (`followup`, which queues the next turn whether or not one is running) —
|
|
10
|
+
* exactly the upstream README's wiring. Steering the current turn is a
|
|
11
|
+
* deliberate user action through the `/queue` panel, never an implicit
|
|
12
|
+
* consequence of submitting while busy.
|
|
10
13
|
*
|
|
11
14
|
* File discovery lives entirely in the Harness service (per-agent bounded
|
|
12
15
|
* index, `@dir/` listing, symlink guards, tool/result invalidation); this
|
|
@@ -22,6 +25,7 @@
|
|
|
22
25
|
|
|
23
26
|
import type { Context } from '@deepseek-ai/cordis'
|
|
24
27
|
import type { Agent } from '@deepseek-ai/dsh-agent'
|
|
28
|
+
import type { UserMessage } from '@deepseek-ai/dsh-session'
|
|
25
29
|
import { isAbsolute, resolve } from 'node:path'
|
|
26
30
|
import {
|
|
27
31
|
DEFAULT_FILE_SEARCH_EXCLUDED_DIRECTORIES,
|
|
@@ -58,7 +62,7 @@ export interface PreparedMention {
|
|
|
58
62
|
/** Structured source sessions in appearance order (empty when none). */
|
|
59
63
|
references: SessionReferenceInput[]
|
|
60
64
|
/** Aggregated snapshot for `agent.inject()`, undefined without references. */
|
|
61
|
-
additionalContext?:
|
|
65
|
+
additionalContext?: UserMessage
|
|
62
66
|
}
|
|
63
67
|
|
|
64
68
|
/** One path candidate the `ctx.fileReferences` service returns. */
|
|
@@ -83,7 +87,7 @@ export function isPathLikeMentionQuery(query: string): boolean {
|
|
|
83
87
|
/** The mention API the input editor and the runner share. */
|
|
84
88
|
export interface MentionsApi {
|
|
85
89
|
/** Ranked menu candidates for the typed `@` query. */
|
|
86
|
-
candidates(query: string, signal?: AbortSignal)
|
|
90
|
+
candidates: (query: string, signal?: AbortSignal) => Promise<readonly MentionCandidate[]>
|
|
87
91
|
/** Parse submission text into readable text plus structured references. */
|
|
88
92
|
parse(text: string): ParsedSessionReferenceText
|
|
89
93
|
/**
|
|
@@ -164,7 +168,7 @@ export function createMentions(ctx: Context, agent: Agent | undefined, cwd: stri
|
|
|
164
168
|
})
|
|
165
169
|
: Promise.resolve([] as readonly ServiceFileCandidate[]),
|
|
166
170
|
sessionCapable && needle !== '' && !isPathLikeMentionQuery(needle) && agent !== undefined
|
|
167
|
-
? resolver
|
|
171
|
+
? resolver.listCandidates(agent, needle, 10, signal).catch((error: unknown) => {
|
|
168
172
|
sessionFailure = error
|
|
169
173
|
return [] as readonly SessionReferenceCandidate[]
|
|
170
174
|
})
|