@foxden-app/foxclaw 0.7.2 → 0.10.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/.env.example +14 -0
- package/CHANGELOG.md +129 -0
- package/README.md +22 -2
- package/README_EN.md +22 -2
- package/dist/antigravity/adapter.d.ts +17 -0
- package/dist/antigravity/adapter.js +256 -0
- package/dist/antigravity/auth.d.ts +121 -0
- package/dist/antigravity/auth.js +896 -0
- package/dist/antigravity/client.d.ts +32 -0
- package/dist/antigravity/client.js +238 -0
- package/dist/antigravity/controller.d.ts +96 -0
- package/dist/antigravity/controller.js +1922 -0
- package/dist/antigravity/conversations.d.ts +29 -0
- package/dist/antigravity/conversations.js +289 -0
- package/dist/antigravity/events.d.ts +101 -0
- package/dist/antigravity/events.js +114 -0
- package/dist/antigravity/runtime.d.ts +47 -0
- package/dist/antigravity/runtime.js +82 -0
- package/dist/auth/cross_node_sync.js +2 -2
- package/dist/channels/telegram/telegram_channel_adapter.d.ts +10 -3
- package/dist/channels/telegram/telegram_channel_adapter.js +2 -1
- package/dist/channels/weixin/weixin_channel_adapter.d.ts +5 -1
- package/dist/codex_app/adapter.d.ts +20 -0
- package/dist/codex_app/adapter.js +213 -0
- package/dist/codex_app/client.d.ts +2 -1
- package/dist/codex_app/client.js +47 -4
- package/dist/codex_app/force_takeover.d.ts +12 -0
- package/dist/codex_app/force_takeover.js +27 -0
- package/dist/config.d.ts +12 -0
- package/dist/config.js +42 -0
- package/dist/controller/controller.d.ts +15 -5
- package/dist/controller/controller.js +252 -20
- package/dist/core/attachments.d.ts +11 -0
- package/dist/core/attachments.js +56 -0
- package/dist/core/engine_spi.d.ts +76 -0
- package/dist/core/engine_spi.js +1 -0
- package/dist/core/orchestrator.d.ts +101 -0
- package/dist/core/orchestrator.js +1404 -0
- package/dist/core/stream_preview.d.ts +29 -0
- package/dist/core/stream_preview.js +146 -0
- package/dist/core/turn_queue.d.ts +19 -0
- package/dist/core/turn_queue.js +41 -0
- package/dist/i18n.d.ts +36 -6
- package/dist/i18n.js +81 -6
- package/dist/main.js +190 -20
- package/dist/opencode/adapter.d.ts +11 -0
- package/dist/opencode/adapter.js +168 -0
- package/dist/store/database.d.ts +41 -0
- package/dist/store/database.js +242 -43
- package/dist/store/token_usage.d.ts +23 -0
- package/dist/store/token_usage.js +61 -0
- package/dist/telegram/api.js +34 -1
- package/dist/telegram/bot_home.d.ts +3 -0
- package/dist/telegram/bot_home.js +107 -0
- package/dist/telegram/gateway.d.ts +5 -0
- package/dist/telegram/gateway.js +21 -0
- package/dist/types.d.ts +1 -0
- package/dist/update.d.ts +6 -0
- package/dist/update.js +78 -6
- package/dist/voice/target.js +2 -1
- package/dist/voice/tts.js +4 -2
- package/docs/devlogs//346/212/200/346/234/257/351/200/232/350/256/257/02./347/273/237/344/270/200/351/200/232/351/201/223/350/260/203/345/272/246/345/231/250/344/270/216/345/217/257/346/217/222/346/213/224/345/274/225/346/223/216SPI/357/274/232FoxClaw/344/273/216/345/215/225/344/275/223/350/265/260/345/220/221/345/244/232Agent/345/272/225/345/272/247.md +192 -0
- package/docs/devlogs//347/254/254/344/270/200/344/272/272/347/247/260/347/211/210/02./347/257/207/344/272/214_/345/275/223/344/270/200/344/270/252/346/241/245/346/216/245/345/231/250/345/274/200/345/247/213/345/255/246/344/274/232/345/220/254/346/207/202/346/211/200/346/234/211Agent.md +45 -0
- package/docs/user-manual.md +11 -1
- package/docs/zh/2026-09-05-bot-home-migration.md +26 -0
- package/docs/zh/2026-09-05-reliability-review.md +53 -0
- package/docs/zh/troubleshooting.md +12 -0
- package/docs/zh/user-manual.md +13 -1
- package/package.json +2 -2
- package/scripts/force-takeover.py +118 -0
- package/scripts/force-takeover.test.py +122 -0
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import type { AppLocale } from '../types.js';
|
|
2
|
+
export interface StreamPreviewState {
|
|
3
|
+
toolLines: string[];
|
|
4
|
+
accumulatedText: string;
|
|
5
|
+
isBoost?: boolean | undefined;
|
|
6
|
+
engineName?: string | undefined;
|
|
7
|
+
stepIndex?: number | undefined;
|
|
8
|
+
toolCount?: number | undefined;
|
|
9
|
+
currentTool?: string | null | undefined;
|
|
10
|
+
elapsedSeconds?: number | undefined;
|
|
11
|
+
}
|
|
12
|
+
export interface FoldedToolsSummaryOptions {
|
|
13
|
+
stepIndex?: number | undefined;
|
|
14
|
+
toolLines?: string[] | undefined;
|
|
15
|
+
toolCount?: number | undefined;
|
|
16
|
+
startTime?: number | undefined;
|
|
17
|
+
durationSeconds?: number | undefined;
|
|
18
|
+
usage?: {
|
|
19
|
+
inputTokens?: number | undefined;
|
|
20
|
+
outputTokens?: number | undefined;
|
|
21
|
+
cachedTokens?: number | undefined;
|
|
22
|
+
totalTokens?: number | undefined;
|
|
23
|
+
} | undefined;
|
|
24
|
+
locale?: AppLocale | undefined;
|
|
25
|
+
}
|
|
26
|
+
export declare function formatElapsedDuration(seconds: number, locale?: AppLocale): string;
|
|
27
|
+
export declare function buildFoldedToolsSummary(options: FoldedToolsSummaryOptions): string;
|
|
28
|
+
export declare function combineSummaryAndResponse(foldedSummary: string, responseText: string, limit?: number): string[];
|
|
29
|
+
export declare function renderStreamPreviewContent(state: StreamPreviewState): string;
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
import { formatMetricTokenCount } from '../store/token_usage.js';
|
|
2
|
+
import { chunkTelegramMessage } from '../telegram/text.js';
|
|
3
|
+
export function formatElapsedDuration(seconds, locale = 'zh') {
|
|
4
|
+
if (!Number.isFinite(seconds) || seconds <= 0)
|
|
5
|
+
return '0s';
|
|
6
|
+
if (seconds < 60)
|
|
7
|
+
return locale === 'zh' ? `${seconds}秒` : `${seconds}s`;
|
|
8
|
+
const mins = Math.floor(seconds / 60);
|
|
9
|
+
const secs = seconds % 60;
|
|
10
|
+
if (mins < 60) {
|
|
11
|
+
return locale === 'zh'
|
|
12
|
+
? `${mins}分${secs > 0 ? `${secs}秒` : ''}`
|
|
13
|
+
: `${mins}m${secs > 0 ? ` ${secs}s` : ''}`;
|
|
14
|
+
}
|
|
15
|
+
const hours = Math.floor(mins / 60);
|
|
16
|
+
const remMins = mins % 60;
|
|
17
|
+
return locale === 'zh'
|
|
18
|
+
? `${hours}小时${remMins > 0 ? `${remMins}分` : ''}`
|
|
19
|
+
: `${hours}h${remMins > 0 ? ` ${remMins}m` : ''}`;
|
|
20
|
+
}
|
|
21
|
+
export function buildFoldedToolsSummary(options) {
|
|
22
|
+
const { stepIndex, toolLines = [], toolCount = toolLines.length, startTime, durationSeconds, usage, locale = 'zh', } = options;
|
|
23
|
+
if (toolCount === 0 && (!stepIndex || stepIndex <= 1) && !usage) {
|
|
24
|
+
return '';
|
|
25
|
+
}
|
|
26
|
+
const roundText = stepIndex && stepIndex > 1
|
|
27
|
+
? (locale === 'zh' ? ` · 共 ${stepIndex} 轮` : ` · ${stepIndex} turns`)
|
|
28
|
+
: '';
|
|
29
|
+
const toolText = toolCount > 0
|
|
30
|
+
? (locale === 'zh' ? ` · 累计执行 ${toolCount} 次工具` : ` · ${toolCount} tools`)
|
|
31
|
+
: '';
|
|
32
|
+
let durationText = '';
|
|
33
|
+
const elapsedSec = typeof durationSeconds === 'number' && durationSeconds > 0
|
|
34
|
+
? durationSeconds
|
|
35
|
+
: startTime
|
|
36
|
+
? Math.max(1, Math.round((Date.now() - startTime) / 1000))
|
|
37
|
+
: 0;
|
|
38
|
+
if (elapsedSec > 0) {
|
|
39
|
+
durationText = locale === 'zh'
|
|
40
|
+
? ` · 耗时 ${formatElapsedDuration(elapsedSec, 'zh')}`
|
|
41
|
+
: ` · in ${formatElapsedDuration(elapsedSec, 'en')}`;
|
|
42
|
+
}
|
|
43
|
+
// Header line
|
|
44
|
+
const header = `🛠️ <b>${locale === 'zh' ? '执行小结' : 'Execution Summary'}${roundText}${toolText}${durationText}</b>`;
|
|
45
|
+
// Token line
|
|
46
|
+
let usageLine = '';
|
|
47
|
+
if (usage && (usage.totalTokens || usage.inputTokens || usage.outputTokens || usage.cachedTokens)) {
|
|
48
|
+
const totalVal = usage.totalTokens || ((usage.inputTokens || 0) + (usage.outputTokens || 0));
|
|
49
|
+
const total = formatMetricTokenCount(totalVal);
|
|
50
|
+
const input = formatMetricTokenCount(usage.inputTokens || 0);
|
|
51
|
+
const output = formatMetricTokenCount(usage.outputTokens || 0);
|
|
52
|
+
const cached = formatMetricTokenCount(usage.cachedTokens || 0);
|
|
53
|
+
if (locale === 'zh') {
|
|
54
|
+
usageLine = `\n🪙 <b>Token 消耗</b>: 总计 ${total} (输入 ${input} · 输出 ${output} · 缓存 ${cached})`;
|
|
55
|
+
}
|
|
56
|
+
else {
|
|
57
|
+
usageLine = `\n🪙 <b>Token Usage</b>: Total ${total} (Input ${input} · Output ${output} · Cached ${cached})`;
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
// Tool detail section:
|
|
61
|
+
// If toolLines <= 25 (e.g. 10-20 step summaries in Codex/AGY): preserve ALL of them!
|
|
62
|
+
// If toolLines > 25 (e.g. 100+ raw tool calls): keep first 3 + omitted notice + last 15.
|
|
63
|
+
let toolDetailSection = '';
|
|
64
|
+
if (toolLines.length > 0) {
|
|
65
|
+
let previewLines = [];
|
|
66
|
+
if (toolLines.length <= 25) {
|
|
67
|
+
previewLines = toolLines;
|
|
68
|
+
}
|
|
69
|
+
else {
|
|
70
|
+
const head = toolLines.slice(0, 3);
|
|
71
|
+
const tail = toolLines.slice(-15);
|
|
72
|
+
const omitted = toolCount - (head.length + tail.length);
|
|
73
|
+
const omittedNote = omitted > 0
|
|
74
|
+
? `<i>${locale === 'zh' ? `(中间 ${omitted} 项历史工具调用已折叠收起)` : `(${omitted} intermediate tools collapsed)`}</i>`
|
|
75
|
+
: '';
|
|
76
|
+
previewLines = [...head, omittedNote, ...tail].filter(Boolean);
|
|
77
|
+
}
|
|
78
|
+
toolDetailSection = `\n\n<i>${locale === 'zh' ? '工具调用记录:' : 'Tool calls:'}</i>\n${previewLines.join('\n')}`;
|
|
79
|
+
}
|
|
80
|
+
return `<blockquote expandable>${header}${usageLine}${toolDetailSection}</blockquote>\n\n`;
|
|
81
|
+
}
|
|
82
|
+
export function combineSummaryAndResponse(foldedSummary, responseText, limit = 4000) {
|
|
83
|
+
const content = (responseText || '(无输出 / No output)').trim();
|
|
84
|
+
if (!foldedSummary) {
|
|
85
|
+
return chunkTelegramMessage(content, limit);
|
|
86
|
+
}
|
|
87
|
+
const combined = `${foldedSummary}${content}`;
|
|
88
|
+
if (combined.length <= limit) {
|
|
89
|
+
return [combined];
|
|
90
|
+
}
|
|
91
|
+
// Combined exceeds limit: chunk responseText cleanly without tearing foldedSummary apart!
|
|
92
|
+
const remainingInFirstChunk = limit - foldedSummary.length;
|
|
93
|
+
if (remainingInFirstChunk >= 300) {
|
|
94
|
+
const window = content.slice(0, remainingInFirstChunk);
|
|
95
|
+
const splitAt = Math.max(window.lastIndexOf('\n\n'), window.lastIndexOf('\n'));
|
|
96
|
+
if (splitAt >= Math.floor(remainingInFirstChunk / 3)) {
|
|
97
|
+
const firstChunkText = content.slice(0, splitAt + 1).trim();
|
|
98
|
+
const rest = content.slice(splitAt + 1).trim();
|
|
99
|
+
const restChunks = chunkTelegramMessage(rest, limit);
|
|
100
|
+
return [`${foldedSummary}${firstChunkText}`, ...restChunks];
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
// If foldedSummary takes up most of the message or no clean paragraph break was found,
|
|
104
|
+
// foldedSummary gets its own clean message, and responseText is chunked independently.
|
|
105
|
+
const responseChunks = chunkTelegramMessage(content, limit);
|
|
106
|
+
return [foldedSummary.trim(), ...responseChunks];
|
|
107
|
+
}
|
|
108
|
+
export function renderStreamPreviewContent(state) {
|
|
109
|
+
const parts = [];
|
|
110
|
+
const name = state.engineName || 'AI';
|
|
111
|
+
const roundText = state.stepIndex && state.stepIndex > 0 ? `第 ${state.stepIndex} 轮` : '';
|
|
112
|
+
const toolText = typeof state.toolCount === 'number' && state.toolCount > 0 ? `累计执行 ${state.toolCount} 次工具` : '';
|
|
113
|
+
const timeText = typeof state.elapsedSeconds === 'number' && state.elapsedSeconds > 0 ? `已耗时 ${state.elapsedSeconds}s` : '';
|
|
114
|
+
const meta = [roundText, toolText, timeText].filter(Boolean).join(' · ');
|
|
115
|
+
if (meta || state.currentTool || state.toolLines.length > 0) {
|
|
116
|
+
if (state.isBoost) {
|
|
117
|
+
parts.push(`🚀 <b>${name} (Boost 模式) 正在执行中</b>${meta ? ` (${meta})` : ''}`);
|
|
118
|
+
}
|
|
119
|
+
else {
|
|
120
|
+
parts.push(`🔄 <b>${name} 正在执行中</b>${meta ? ` (${meta})` : ''}`);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
if (state.currentTool) {
|
|
124
|
+
parts.push(`⚙️ <b>当前正在运行</b>: <code>${escapeTelegramHtml(state.currentTool)}</code>`);
|
|
125
|
+
parts.push('');
|
|
126
|
+
}
|
|
127
|
+
if (state.toolLines.length > 0) {
|
|
128
|
+
const recent = state.toolLines.slice(-6);
|
|
129
|
+
parts.push(`<blockquote expandable>🛠️ <b>正在调用工具 (${state.toolLines.length} 项)</b>\n${recent.join('\n')}</blockquote>`);
|
|
130
|
+
parts.push('');
|
|
131
|
+
}
|
|
132
|
+
if (state.accumulatedText) {
|
|
133
|
+
const preview = state.accumulatedText.slice(-3000);
|
|
134
|
+
parts.push(preview);
|
|
135
|
+
}
|
|
136
|
+
else {
|
|
137
|
+
parts.push(state.isBoost ? `🚀 ${name} (Boost 模式) 正在深度思考中…` : `⏳ ${name} 正在思考中…`);
|
|
138
|
+
}
|
|
139
|
+
return parts.join('\n');
|
|
140
|
+
}
|
|
141
|
+
function escapeTelegramHtml(value) {
|
|
142
|
+
return value
|
|
143
|
+
.replace(/&/g, '&')
|
|
144
|
+
.replace(/</g, '<')
|
|
145
|
+
.replace(/>/g, '>');
|
|
146
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export type TurnMessageMode = 'steer' | 'queue';
|
|
2
|
+
export interface QueuedTurnItem<T = unknown> {
|
|
3
|
+
id: string;
|
|
4
|
+
scopeId: string;
|
|
5
|
+
prompt: string;
|
|
6
|
+
payload: T;
|
|
7
|
+
enqueuedAt: number;
|
|
8
|
+
}
|
|
9
|
+
export declare class TurnQueueManager<T = unknown> {
|
|
10
|
+
private readonly queues;
|
|
11
|
+
private readonly activeModes;
|
|
12
|
+
getMode(scopeId: string, defaultMode?: TurnMessageMode): TurnMessageMode;
|
|
13
|
+
setMode(scopeId: string, mode: TurnMessageMode): void;
|
|
14
|
+
enqueue(scopeId: string, item: Omit<QueuedTurnItem<T>, 'id' | 'enqueuedAt'>): QueuedTurnItem<T>;
|
|
15
|
+
dequeue(scopeId: string): QueuedTurnItem<T> | undefined;
|
|
16
|
+
peek(scopeId: string): QueuedTurnItem<T> | undefined;
|
|
17
|
+
getQueueLength(scopeId: string): number;
|
|
18
|
+
clearQueue(scopeId: string): number;
|
|
19
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
export class TurnQueueManager {
|
|
2
|
+
queues = new Map();
|
|
3
|
+
activeModes = new Map();
|
|
4
|
+
getMode(scopeId, defaultMode = 'queue') {
|
|
5
|
+
return this.activeModes.get(scopeId) ?? defaultMode;
|
|
6
|
+
}
|
|
7
|
+
setMode(scopeId, mode) {
|
|
8
|
+
this.activeModes.set(scopeId, mode);
|
|
9
|
+
}
|
|
10
|
+
enqueue(scopeId, item) {
|
|
11
|
+
const fullItem = {
|
|
12
|
+
...item,
|
|
13
|
+
id: `q_${Date.now()}_${Math.random().toString(36).slice(2, 7)}`,
|
|
14
|
+
enqueuedAt: Date.now(),
|
|
15
|
+
};
|
|
16
|
+
const list = this.queues.get(scopeId) || [];
|
|
17
|
+
list.push(fullItem);
|
|
18
|
+
this.queues.set(scopeId, list);
|
|
19
|
+
return fullItem;
|
|
20
|
+
}
|
|
21
|
+
dequeue(scopeId) {
|
|
22
|
+
const list = this.queues.get(scopeId);
|
|
23
|
+
if (!list || list.length === 0)
|
|
24
|
+
return undefined;
|
|
25
|
+
const item = list.shift();
|
|
26
|
+
if (list.length === 0)
|
|
27
|
+
this.queues.delete(scopeId);
|
|
28
|
+
return item;
|
|
29
|
+
}
|
|
30
|
+
peek(scopeId) {
|
|
31
|
+
return this.queues.get(scopeId)?.[0];
|
|
32
|
+
}
|
|
33
|
+
getQueueLength(scopeId) {
|
|
34
|
+
return this.queues.get(scopeId)?.length ?? 0;
|
|
35
|
+
}
|
|
36
|
+
clearQueue(scopeId) {
|
|
37
|
+
const count = this.getQueueLength(scopeId);
|
|
38
|
+
this.queues.delete(scopeId);
|
|
39
|
+
return count;
|
|
40
|
+
}
|
|
41
|
+
}
|
package/dist/i18n.d.ts
CHANGED
|
@@ -43,6 +43,7 @@ declare const MESSAGES: {
|
|
|
43
43
|
readonly usage_files: "Usage: /files <query>";
|
|
44
44
|
readonly cmd_desc_help: "Show commands";
|
|
45
45
|
readonly cmd_desc_setup: "Unified preference panel";
|
|
46
|
+
readonly cmd_desc_backend: "Switch backend engine and account";
|
|
46
47
|
readonly cmd_desc_fast: "Toggle Fast mode";
|
|
47
48
|
readonly cmd_desc_active: "Active-turn message behavior";
|
|
48
49
|
readonly cmd_desc_rich: "Telegram RichMessage demo";
|
|
@@ -52,6 +53,8 @@ declare const MESSAGES: {
|
|
|
52
53
|
readonly cmd_desc_account: "Codex account";
|
|
53
54
|
readonly cmd_desc_quota: "Codex quota";
|
|
54
55
|
readonly cmd_desc_login_device: "ChatGPT device login";
|
|
56
|
+
readonly cmd_desc_login_cancel: "Cancel the pending login";
|
|
57
|
+
readonly cmd_desc_cli: "Continue this session in the local CLI";
|
|
55
58
|
readonly cmd_desc_threads: "Recent threads";
|
|
56
59
|
readonly cmd_desc_open: "Open a cached thread";
|
|
57
60
|
readonly cmd_desc_goal: "Thread goal";
|
|
@@ -246,13 +249,13 @@ declare const MESSAGES: {
|
|
|
246
249
|
readonly auth_sync_test_sent: "Auth sync test complete: sent {sent}, replies {replied}.";
|
|
247
250
|
readonly auth_sync_test_missing: "Missing replies: {value}";
|
|
248
251
|
readonly auth_sync_push_blocked_active: "Cannot push auth sync while any runtime, approval, input, login, or auth mirror write is active.";
|
|
249
|
-
readonly auth_sync_safe_starting: "Auditing every node
|
|
252
|
+
readonly auth_sync_safe_starting: "Auditing every node and distributing valid auth. An unreachable peer can add up to 5 minutes per audit phase. Use /auth sync status to check progress.";
|
|
250
253
|
readonly auth_sync_safe_done: "Safe auth sync complete: local synced {localSynced}, local skipped {localSkipped}; cross-node sent {sent}, skipped {skipped}.";
|
|
251
254
|
readonly auth_cluster_audit_starting: "Asking all auth-sync peers to validate accounts, reconcile the newest usable credentials, and refresh credentials at least 8 days old...";
|
|
252
255
|
readonly auth_cluster_audit_blocked_active: "Cluster auth check requires every local runtime, approval, input, login, and auth mirror write to be idle.";
|
|
253
256
|
readonly auth_cluster_audit_failed: "Cluster auth check failed: {error}";
|
|
254
257
|
readonly auth_cluster_audit_summary: "Cluster auth check: nodes {responded}/{expected}; accounts checked {checked}, usable {valid}, unusable {invalid}.";
|
|
255
|
-
readonly auth_cluster_audit_synced: "
|
|
258
|
+
readonly auth_cluster_audit_synced: "Valid auth selected and sent (remote import not confirmed): {value}";
|
|
256
259
|
readonly auth_cluster_audit_repair: "Marked for manual repair after multi-node consensus: {value}";
|
|
257
260
|
readonly auth_cluster_audit_missing: "No response: {value}";
|
|
258
261
|
readonly auth_cluster_audit_busy: "Busy nodes: {value}";
|
|
@@ -301,7 +304,17 @@ declare const MESSAGES: {
|
|
|
301
304
|
readonly working: "Working...";
|
|
302
305
|
readonly usage_open: "Usage: /open <n>";
|
|
303
306
|
readonly usage_watch: "Usage: /watch [n]";
|
|
304
|
-
readonly usage_takeover: "Usage: /takeover <message>";
|
|
307
|
+
readonly usage_takeover: "Usage: /takeover <message> or /takeover --force <message> (confirm stopping a local CLI)";
|
|
308
|
+
readonly force_takeover_trusted_telegram_only: "Force takeover is only available to the configured trusted Telegram user.";
|
|
309
|
+
readonly force_takeover_confirm: "Force takeover of thread {threadId}?\nLocal Codex CLI PID: {pid}\nWorking directory: {cwd}\nNext prompt: {prompt}\nThis will terminate that CLI (SIGTERM, then SIGKILL after 5 seconds if needed). Unfinished work may be interrupted; child commands may continue running. No edits are rolled back. Confirmation expires in 60 seconds.";
|
|
310
|
+
readonly button_force_takeover: "Confirm force takeover";
|
|
311
|
+
readonly force_takeover_busy: "Force takeover is in progress. Please wait before switching threads.";
|
|
312
|
+
readonly force_takeover_hint: "Use /watch then /queue <message> to queue for that CLI. To stop a local CLI and hand the thread to this bridge, use /takeover --force <message> and confirm.";
|
|
313
|
+
readonly force_takeover_expired: "Confirmation expired or thread changed. Send /takeover --force <message> again.";
|
|
314
|
+
readonly force_takeover_cancelled: "Force takeover cancelled. Nothing was stopped or submitted.";
|
|
315
|
+
readonly force_takeover_stopping: "Stopping the confirmed CLI PID {pid} and checking its writer lock...";
|
|
316
|
+
readonly force_takeover_failed: "Force takeover not completed; no new prompt was sent. If stopping already began, the CLI may have exited. Check /status before retrying. Reason: {error}";
|
|
317
|
+
readonly force_takeover_acquired: "Bridge acquired thread {threadId}. Preparing the requested prompt; this is not task completion.";
|
|
305
318
|
readonly usage_queue: "Usage: /queue <message>";
|
|
306
319
|
readonly unknown_cached_thread: "Unknown cached thread. Run /threads first.";
|
|
307
320
|
readonly cached_thread_unavailable: "That cached thread is no longer available. Run /threads again.";
|
|
@@ -771,6 +784,7 @@ declare const MESSAGES: {
|
|
|
771
784
|
readonly usage_files: "用法:/files <关键词>";
|
|
772
785
|
readonly cmd_desc_help: "查看命令";
|
|
773
786
|
readonly cmd_desc_setup: "统一偏好面板";
|
|
787
|
+
readonly cmd_desc_backend: "切换后端运行环境与账号";
|
|
774
788
|
readonly cmd_desc_fast: "切换 Fast 模式";
|
|
775
789
|
readonly cmd_desc_active: "运行中新消息处理方式";
|
|
776
790
|
readonly cmd_desc_rich: "Telegram RichMessage 演示";
|
|
@@ -780,6 +794,8 @@ declare const MESSAGES: {
|
|
|
780
794
|
readonly cmd_desc_account: "Codex 账号";
|
|
781
795
|
readonly cmd_desc_quota: "Codex 用量";
|
|
782
796
|
readonly cmd_desc_login_device: "ChatGPT 设备登录";
|
|
797
|
+
readonly cmd_desc_login_cancel: "取消当前登录流程";
|
|
798
|
+
readonly cmd_desc_cli: "从本机 CLI 继续当前会话";
|
|
783
799
|
readonly cmd_desc_threads: "最近线程";
|
|
784
800
|
readonly cmd_desc_open: "打开缓存线程";
|
|
785
801
|
readonly cmd_desc_goal: "线程目标";
|
|
@@ -974,13 +990,13 @@ declare const MESSAGES: {
|
|
|
974
990
|
readonly auth_sync_test_sent: "auth sync 测试完成:已发送 {sent},收到回应 {replied}。";
|
|
975
991
|
readonly auth_sync_test_missing: "未回应:{value}";
|
|
976
992
|
readonly auth_sync_push_blocked_active: "当前有任一 runtime、审批、待输入、登录或 auth 镜像写入在进行中,不能推送 auth 同步。";
|
|
977
|
-
readonly auth_sync_safe_starting: "
|
|
993
|
+
readonly auth_sync_safe_starting: "正在自检各节点并分发有效授权。节点未回应时,每轮自检最多等待 5 分钟;可用 /auth sync status 查看进展。";
|
|
978
994
|
readonly auth_sync_safe_done: "安全 auth 同步完成:本机同步 {localSynced},本机跳过 {localSkipped};跨节点发送 {sent},跳过 {skipped}。";
|
|
979
995
|
readonly auth_cluster_audit_starting: "正在通知所有 auth sync 节点逐账号自检,协商最新有效凭据,并由本节点刷新已满 8 天的 auth...";
|
|
980
996
|
readonly auth_cluster_audit_blocked_active: "集群 auth 自检要求本机所有 runtime、审批、待输入、登录和 auth 镜像写入均为空闲。";
|
|
981
997
|
readonly auth_cluster_audit_failed: "集群 auth 自检失败:{error}";
|
|
982
998
|
readonly auth_cluster_audit_summary: "集群 auth 自检:节点 {responded}/{expected};检查账号 {checked},有效 {valid},无有效副本 {invalid}。";
|
|
983
|
-
readonly auth_cluster_audit_synced: "
|
|
999
|
+
readonly auth_cluster_audit_synced: "已选出并发送有效授权(远端导入尚未确认):{value}";
|
|
984
1000
|
readonly auth_cluster_audit_repair: "多节点确认无效,已标记问号等待人工处理:{value}";
|
|
985
1001
|
readonly auth_cluster_audit_missing: "未回应节点:{value}";
|
|
986
1002
|
readonly auth_cluster_audit_busy: "忙碌节点:{value}";
|
|
@@ -1029,7 +1045,17 @@ declare const MESSAGES: {
|
|
|
1029
1045
|
readonly working: "处理中...";
|
|
1030
1046
|
readonly usage_open: "用法:/open <编号>";
|
|
1031
1047
|
readonly usage_watch: "用法:/watch [编号]";
|
|
1032
|
-
readonly usage_takeover: "用法:/takeover
|
|
1048
|
+
readonly usage_takeover: "用法:/takeover <消息>;或 /takeover --force <消息>(确认后停止本机 CLI)";
|
|
1049
|
+
readonly force_takeover_trusted_telegram_only: "强制接管仅对配置中的可信 Telegram 用户开放。";
|
|
1050
|
+
readonly force_takeover_confirm: "强制接管 thread {threadId}?\n本机 Codex CLI PID:{pid}\n工作目录:{cwd}\n接管后消息:{prompt}\n将终止这个 CLI(先 SIGTERM,5 秒后仍未退出则 SIGKILL)。未完成任务可能被中断,已启动的子命令可能继续运行;不会回滚文件修改。确认 60 秒内有效。";
|
|
1051
|
+
readonly button_force_takeover: "确认强制接管";
|
|
1052
|
+
readonly force_takeover_busy: "正在强制接管,请等待结果后再切换会话。";
|
|
1053
|
+
readonly force_takeover_hint: "可先 /watch 再 /queue <消息> 排队给原 CLI;如需停止本机 CLI、让桥接管,请发送 /takeover --force <消息> 并确认。";
|
|
1054
|
+
readonly force_takeover_expired: "确认已过期或 thread 已切换,请重新发送 /takeover --force <消息>。";
|
|
1055
|
+
readonly force_takeover_cancelled: "已取消强制接管,没有停止进程或发送新任务。";
|
|
1056
|
+
readonly force_takeover_stopping: "正在停止已确认的 CLI PID {pid},并检查写入锁是否释放…";
|
|
1057
|
+
readonly force_takeover_failed: "强制接管未完成,没有发送新任务。如果已开始停止,CLI 可能已经退出。请先 /status 检查再重试。原因:{error}";
|
|
1058
|
+
readonly force_takeover_acquired: "桥已取得 thread {threadId} 的写入权,准备发送指定消息;这不代表任务已完成。";
|
|
1033
1059
|
readonly usage_queue: "用法:/queue <消息>";
|
|
1034
1060
|
readonly unknown_cached_thread: "找不到这个缓存线程,请先运行 /threads。";
|
|
1035
1061
|
readonly cached_thread_unavailable: "这个缓存线程已经不可用,请重新运行 /threads。";
|
|
@@ -1469,4 +1495,8 @@ export declare function getOpencodeTelegramCommands(locale: AppLocale): Array<{
|
|
|
1469
1495
|
command: string;
|
|
1470
1496
|
description: string;
|
|
1471
1497
|
}>;
|
|
1498
|
+
export declare function getAntigravityTelegramCommands(locale: AppLocale): Array<{
|
|
1499
|
+
command: string;
|
|
1500
|
+
description: string;
|
|
1501
|
+
}>;
|
|
1472
1502
|
export {};
|
package/dist/i18n.js
CHANGED
|
@@ -41,6 +41,7 @@ const MESSAGES = {
|
|
|
41
41
|
usage_files: 'Usage: /files <query>',
|
|
42
42
|
cmd_desc_help: 'Show commands',
|
|
43
43
|
cmd_desc_setup: 'Unified preference panel',
|
|
44
|
+
cmd_desc_backend: 'Switch backend engine and account',
|
|
44
45
|
cmd_desc_fast: 'Toggle Fast mode',
|
|
45
46
|
cmd_desc_active: 'Active-turn message behavior',
|
|
46
47
|
cmd_desc_rich: 'Telegram RichMessage demo',
|
|
@@ -50,6 +51,8 @@ const MESSAGES = {
|
|
|
50
51
|
cmd_desc_account: 'Codex account',
|
|
51
52
|
cmd_desc_quota: 'Codex quota',
|
|
52
53
|
cmd_desc_login_device: 'ChatGPT device login',
|
|
54
|
+
cmd_desc_login_cancel: 'Cancel the pending login',
|
|
55
|
+
cmd_desc_cli: 'Continue this session in the local CLI',
|
|
53
56
|
cmd_desc_threads: 'Recent threads',
|
|
54
57
|
cmd_desc_open: 'Open a cached thread',
|
|
55
58
|
cmd_desc_goal: 'Thread goal',
|
|
@@ -244,13 +247,13 @@ const MESSAGES = {
|
|
|
244
247
|
auth_sync_test_sent: 'Auth sync test complete: sent {sent}, replies {replied}.',
|
|
245
248
|
auth_sync_test_missing: 'Missing replies: {value}',
|
|
246
249
|
auth_sync_push_blocked_active: 'Cannot push auth sync while any runtime, approval, input, login, or auth mirror write is active.',
|
|
247
|
-
auth_sync_safe_starting: 'Auditing every node
|
|
250
|
+
auth_sync_safe_starting: 'Auditing every node and distributing valid auth. An unreachable peer can add up to 5 minutes per audit phase. Use /auth sync status to check progress.',
|
|
248
251
|
auth_sync_safe_done: 'Safe auth sync complete: local synced {localSynced}, local skipped {localSkipped}; cross-node sent {sent}, skipped {skipped}.',
|
|
249
252
|
auth_cluster_audit_starting: 'Asking all auth-sync peers to validate accounts, reconcile the newest usable credentials, and refresh credentials at least 8 days old...',
|
|
250
253
|
auth_cluster_audit_blocked_active: 'Cluster auth check requires every local runtime, approval, input, login, and auth mirror write to be idle.',
|
|
251
254
|
auth_cluster_audit_failed: 'Cluster auth check failed: {error}',
|
|
252
255
|
auth_cluster_audit_summary: 'Cluster auth check: nodes {responded}/{expected}; accounts checked {checked}, usable {valid}, unusable {invalid}.',
|
|
253
|
-
auth_cluster_audit_synced: '
|
|
256
|
+
auth_cluster_audit_synced: 'Valid auth selected and sent (remote import not confirmed): {value}',
|
|
254
257
|
auth_cluster_audit_repair: 'Marked for manual repair after multi-node consensus: {value}',
|
|
255
258
|
auth_cluster_audit_missing: 'No response: {value}',
|
|
256
259
|
auth_cluster_audit_busy: 'Busy nodes: {value}',
|
|
@@ -299,7 +302,17 @@ const MESSAGES = {
|
|
|
299
302
|
working: 'Working...',
|
|
300
303
|
usage_open: 'Usage: /open <n>',
|
|
301
304
|
usage_watch: 'Usage: /watch [n]',
|
|
302
|
-
usage_takeover: 'Usage: /takeover <message>',
|
|
305
|
+
usage_takeover: 'Usage: /takeover <message> or /takeover --force <message> (confirm stopping a local CLI)',
|
|
306
|
+
force_takeover_trusted_telegram_only: 'Force takeover is only available to the configured trusted Telegram user.',
|
|
307
|
+
force_takeover_confirm: 'Force takeover of thread {threadId}?\nLocal Codex CLI PID: {pid}\nWorking directory: {cwd}\nNext prompt: {prompt}\nThis will terminate that CLI (SIGTERM, then SIGKILL after 5 seconds if needed). Unfinished work may be interrupted; child commands may continue running. No edits are rolled back. Confirmation expires in 60 seconds.',
|
|
308
|
+
button_force_takeover: 'Confirm force takeover',
|
|
309
|
+
force_takeover_busy: 'Force takeover is in progress. Please wait before switching threads.',
|
|
310
|
+
force_takeover_hint: 'Use /watch then /queue <message> to queue for that CLI. To stop a local CLI and hand the thread to this bridge, use /takeover --force <message> and confirm.',
|
|
311
|
+
force_takeover_expired: 'Confirmation expired or thread changed. Send /takeover --force <message> again.',
|
|
312
|
+
force_takeover_cancelled: 'Force takeover cancelled. Nothing was stopped or submitted.',
|
|
313
|
+
force_takeover_stopping: 'Stopping the confirmed CLI PID {pid} and checking its writer lock...',
|
|
314
|
+
force_takeover_failed: 'Force takeover not completed; no new prompt was sent. If stopping already began, the CLI may have exited. Check /status before retrying. Reason: {error}',
|
|
315
|
+
force_takeover_acquired: 'Bridge acquired thread {threadId}. Preparing the requested prompt; this is not task completion.',
|
|
303
316
|
usage_queue: 'Usage: /queue <message>',
|
|
304
317
|
unknown_cached_thread: 'Unknown cached thread. Run /threads first.',
|
|
305
318
|
cached_thread_unavailable: 'That cached thread is no longer available. Run /threads again.',
|
|
@@ -769,6 +782,7 @@ const MESSAGES = {
|
|
|
769
782
|
usage_files: '用法:/files <关键词>',
|
|
770
783
|
cmd_desc_help: '查看命令',
|
|
771
784
|
cmd_desc_setup: '统一偏好面板',
|
|
785
|
+
cmd_desc_backend: '切换后端运行环境与账号',
|
|
772
786
|
cmd_desc_fast: '切换 Fast 模式',
|
|
773
787
|
cmd_desc_active: '运行中新消息处理方式',
|
|
774
788
|
cmd_desc_rich: 'Telegram RichMessage 演示',
|
|
@@ -778,6 +792,8 @@ const MESSAGES = {
|
|
|
778
792
|
cmd_desc_account: 'Codex 账号',
|
|
779
793
|
cmd_desc_quota: 'Codex 用量',
|
|
780
794
|
cmd_desc_login_device: 'ChatGPT 设备登录',
|
|
795
|
+
cmd_desc_login_cancel: '取消当前登录流程',
|
|
796
|
+
cmd_desc_cli: '从本机 CLI 继续当前会话',
|
|
781
797
|
cmd_desc_threads: '最近线程',
|
|
782
798
|
cmd_desc_open: '打开缓存线程',
|
|
783
799
|
cmd_desc_goal: '线程目标',
|
|
@@ -972,13 +988,13 @@ const MESSAGES = {
|
|
|
972
988
|
auth_sync_test_sent: 'auth sync 测试完成:已发送 {sent},收到回应 {replied}。',
|
|
973
989
|
auth_sync_test_missing: '未回应:{value}',
|
|
974
990
|
auth_sync_push_blocked_active: '当前有任一 runtime、审批、待输入、登录或 auth 镜像写入在进行中,不能推送 auth 同步。',
|
|
975
|
-
auth_sync_safe_starting: '
|
|
991
|
+
auth_sync_safe_starting: '正在自检各节点并分发有效授权。节点未回应时,每轮自检最多等待 5 分钟;可用 /auth sync status 查看进展。',
|
|
976
992
|
auth_sync_safe_done: '安全 auth 同步完成:本机同步 {localSynced},本机跳过 {localSkipped};跨节点发送 {sent},跳过 {skipped}。',
|
|
977
993
|
auth_cluster_audit_starting: '正在通知所有 auth sync 节点逐账号自检,协商最新有效凭据,并由本节点刷新已满 8 天的 auth...',
|
|
978
994
|
auth_cluster_audit_blocked_active: '集群 auth 自检要求本机所有 runtime、审批、待输入、登录和 auth 镜像写入均为空闲。',
|
|
979
995
|
auth_cluster_audit_failed: '集群 auth 自检失败:{error}',
|
|
980
996
|
auth_cluster_audit_summary: '集群 auth 自检:节点 {responded}/{expected};检查账号 {checked},有效 {valid},无有效副本 {invalid}。',
|
|
981
|
-
auth_cluster_audit_synced: '
|
|
997
|
+
auth_cluster_audit_synced: '已选出并发送有效授权(远端导入尚未确认):{value}',
|
|
982
998
|
auth_cluster_audit_repair: '多节点确认无效,已标记问号等待人工处理:{value}',
|
|
983
999
|
auth_cluster_audit_missing: '未回应节点:{value}',
|
|
984
1000
|
auth_cluster_audit_busy: '忙碌节点:{value}',
|
|
@@ -1027,7 +1043,17 @@ const MESSAGES = {
|
|
|
1027
1043
|
working: '处理中...',
|
|
1028
1044
|
usage_open: '用法:/open <编号>',
|
|
1029
1045
|
usage_watch: '用法:/watch [编号]',
|
|
1030
|
-
usage_takeover: '用法:/takeover
|
|
1046
|
+
usage_takeover: '用法:/takeover <消息>;或 /takeover --force <消息>(确认后停止本机 CLI)',
|
|
1047
|
+
force_takeover_trusted_telegram_only: '强制接管仅对配置中的可信 Telegram 用户开放。',
|
|
1048
|
+
force_takeover_confirm: '强制接管 thread {threadId}?\n本机 Codex CLI PID:{pid}\n工作目录:{cwd}\n接管后消息:{prompt}\n将终止这个 CLI(先 SIGTERM,5 秒后仍未退出则 SIGKILL)。未完成任务可能被中断,已启动的子命令可能继续运行;不会回滚文件修改。确认 60 秒内有效。',
|
|
1049
|
+
button_force_takeover: '确认强制接管',
|
|
1050
|
+
force_takeover_busy: '正在强制接管,请等待结果后再切换会话。',
|
|
1051
|
+
force_takeover_hint: '可先 /watch 再 /queue <消息> 排队给原 CLI;如需停止本机 CLI、让桥接管,请发送 /takeover --force <消息> 并确认。',
|
|
1052
|
+
force_takeover_expired: '确认已过期或 thread 已切换,请重新发送 /takeover --force <消息>。',
|
|
1053
|
+
force_takeover_cancelled: '已取消强制接管,没有停止进程或发送新任务。',
|
|
1054
|
+
force_takeover_stopping: '正在停止已确认的 CLI PID {pid},并检查写入锁是否释放…',
|
|
1055
|
+
force_takeover_failed: '强制接管未完成,没有发送新任务。如果已开始停止,CLI 可能已经退出。请先 /status 检查再重试。原因:{error}',
|
|
1056
|
+
force_takeover_acquired: '桥已取得 thread {threadId} 的写入权,准备发送指定消息;这不代表任务已完成。',
|
|
1031
1057
|
usage_queue: '用法:/queue <消息>',
|
|
1032
1058
|
unknown_cached_thread: '找不到这个缓存线程,请先运行 /threads。',
|
|
1033
1059
|
cached_thread_unavailable: '这个缓存线程已经不可用,请重新运行 /threads。',
|
|
@@ -1468,10 +1494,12 @@ export function getTelegramCommands(locale) {
|
|
|
1468
1494
|
return [
|
|
1469
1495
|
{ command: 'help', description: t(locale, 'cmd_desc_help') },
|
|
1470
1496
|
{ command: 'setup', description: t(locale, 'cmd_desc_setup') },
|
|
1497
|
+
{ command: 'backend', description: t(locale, 'cmd_desc_backend') },
|
|
1471
1498
|
{ command: 'status', description: t(locale, 'cmd_desc_status') },
|
|
1472
1499
|
{ command: 'update', description: t(locale, 'cmd_desc_update') },
|
|
1473
1500
|
{ command: 'threads', description: t(locale, 'cmd_desc_threads') },
|
|
1474
1501
|
{ command: 'auth', description: t(locale, 'cmd_desc_auth') },
|
|
1502
|
+
{ command: 'boost', description: locale === 'zh' ? '切换 Boost 深度推理模式' : 'Toggle Boost reasoning mode' },
|
|
1475
1503
|
{ command: 'fast', description: t(locale, 'cmd_desc_fast') },
|
|
1476
1504
|
{ command: 'active', description: t(locale, 'cmd_desc_active') },
|
|
1477
1505
|
{ command: 'rich', description: t(locale, 'cmd_desc_rich') },
|
|
@@ -1479,6 +1507,8 @@ export function getTelegramCommands(locale) {
|
|
|
1479
1507
|
{ command: 'account', description: t(locale, 'cmd_desc_account') },
|
|
1480
1508
|
{ command: 'quota', description: t(locale, 'cmd_desc_quota') },
|
|
1481
1509
|
{ command: 'login_device', description: t(locale, 'cmd_desc_login_device') },
|
|
1510
|
+
{ command: 'login_cancel', description: t(locale, 'cmd_desc_login_cancel') },
|
|
1511
|
+
{ command: 'cli', description: t(locale, 'cmd_desc_cli') },
|
|
1482
1512
|
{ command: 'open', description: t(locale, 'cmd_desc_open') },
|
|
1483
1513
|
{ command: 'goal', description: t(locale, 'cmd_desc_goal') },
|
|
1484
1514
|
{ command: 'history', description: t(locale, 'cmd_desc_history') },
|
|
@@ -1552,3 +1582,48 @@ export function getOpencodeTelegramCommands(locale) {
|
|
|
1552
1582
|
.map(([command, description]) => ({ command, description })),
|
|
1553
1583
|
];
|
|
1554
1584
|
}
|
|
1585
|
+
export function getAntigravityTelegramCommands(locale) {
|
|
1586
|
+
return locale === 'zh'
|
|
1587
|
+
? [
|
|
1588
|
+
{ command: 'help', description: '查看帮助' },
|
|
1589
|
+
{ command: 'setup', description: '控制面板与设置' },
|
|
1590
|
+
{ command: 'backend', description: '切换后端运行环境与账号' },
|
|
1591
|
+
{ command: 'threads', description: '查看会话列表' },
|
|
1592
|
+
{ command: 'open', description: '打开指定会话' },
|
|
1593
|
+
{ command: 'watch', description: '只读观察会话' },
|
|
1594
|
+
{ command: 'unwatch', description: '停止观察' },
|
|
1595
|
+
{ command: 'new', description: '新建会话' },
|
|
1596
|
+
{ command: 'boost', description: '切换 Boost 深度推理模式' },
|
|
1597
|
+
{ command: 'models', description: '切换模型' },
|
|
1598
|
+
{ command: 'auth', description: '账号管理与切换' },
|
|
1599
|
+
{ command: 'login', description: '网页授权登录新账号' },
|
|
1600
|
+
{ command: 'active', description: '设置运行中消息模式 (插话/排队)' },
|
|
1601
|
+
{ command: 'queue', description: '排队下一轮回复' },
|
|
1602
|
+
{ command: 'steer', description: '插话并中断当前回复' },
|
|
1603
|
+
{ command: 'effort', description: '设置思考深度' },
|
|
1604
|
+
{ command: 'status', description: '运行状态' },
|
|
1605
|
+
{ command: 'update', description: '自升级服务及后端 (Codex/AGY)' },
|
|
1606
|
+
{ command: 'interrupt', description: '打断当前任务' },
|
|
1607
|
+
]
|
|
1608
|
+
: [
|
|
1609
|
+
{ command: 'help', description: 'Show commands' },
|
|
1610
|
+
{ command: 'setup', description: 'Control panel & settings' },
|
|
1611
|
+
{ command: 'backend', description: 'Switch backend and account' },
|
|
1612
|
+
{ command: 'threads', description: 'List conversations' },
|
|
1613
|
+
{ command: 'open', description: 'Open conversation' },
|
|
1614
|
+
{ command: 'watch', description: 'Watch conversation' },
|
|
1615
|
+
{ command: 'unwatch', description: 'Stop watching' },
|
|
1616
|
+
{ command: 'new', description: 'New session' },
|
|
1617
|
+
{ command: 'boost', description: 'Toggle Boost reasoning mode' },
|
|
1618
|
+
{ command: 'models', description: 'Select model' },
|
|
1619
|
+
{ command: 'auth', description: 'Manage accounts' },
|
|
1620
|
+
{ command: 'login', description: 'Sign in new Google account' },
|
|
1621
|
+
{ command: 'active', description: 'Active-turn message mode' },
|
|
1622
|
+
{ command: 'queue', description: 'Queue next prompt' },
|
|
1623
|
+
{ command: 'steer', description: 'Interrupt and steer turn' },
|
|
1624
|
+
{ command: 'effort', description: 'Reasoning effort' },
|
|
1625
|
+
{ command: 'status', description: 'Bridge status' },
|
|
1626
|
+
{ command: 'update', description: 'Self-update service & backends' },
|
|
1627
|
+
{ command: 'interrupt', description: 'Stop active turn' },
|
|
1628
|
+
];
|
|
1629
|
+
}
|