fix(control-ui): repair zh-CN localization coverage

Route remaining Control UI agent, debug, channel refresh, and exec approval copy through the locale source of truth.

Preserve the English Cron Jobs tab label, keep the security audit command monospace, and regenerate locale metadata against current main.

Verified locally:
- pnpm test ui/src/ui/views/agents.test.ts ui/src/ui/views/debug.test.ts ui/src/ui/views/exec-approval.test.ts
- pnpm ui:i18n:check
- pnpm exec oxfmt --check --threads=1 ui/src/i18n/locales/en.ts ui/src/i18n/locales/zh-CN.ts ui/src/ui/views/agents-panels-status-files.ts ui/src/ui/views/agents.ts ui/src/ui/views/agents.test.ts ui/src/ui/views/debug.ts ui/src/ui/views/debug.test.ts ui/src/ui/views/exec-approval.ts ui/src/ui/views/exec-approval.test.ts
- git diff --check origin/main...HEAD
This commit is contained in:
openclaw-clownfish[bot]
2026-04-29 14:22:36 -05:00
committed by GitHub
parent 3059702687
commit 648ed69f82
45 changed files with 3502 additions and 200 deletions

View File

@@ -26,6 +26,7 @@ Docs: https://docs.openclaw.ai
- Anthropic/Meridian: preserve text and thinking content seeded on `content_block_start` in anthropic-messages streams, so `[thinking, text]` replies no longer persist as empty turns or trigger empty-response fallbacks. Fixes #74410. Thanks @vyctorbrzezowski.
- Media: include redacted per-attempt resize failures and resolved model input capabilities in vision-pipeline errors so ARM64 image failures are diagnosable without closing the remaining routing investigation. Refs #74552. Thanks @1yihui.
- Control UI/i18n: route zh-CN agent, debug, channel-refresh, and exec-approval copy through the locale source while preserving the English `Cron Jobs` agent tab label and the security-audit command styling. Carries forward #39692 repair context. Thanks @hepeng154833488 and @vincentkoc.
- Auto-reply: honor explicit `silentReply.direct: "allow"` for clean empty or reasoning-only direct chat turns while keeping the default direct-chat empty-response guard conservative. Fixes #74409. Thanks @jesuskannolis.
- OpenAI Codex: send a non-empty Responses input item when a Codex turn only has systemPrompt-backed instructions, avoiding ChatGPT backend 400s from `input: []`. Fixes #73820. Thanks @woodhouse-bot.
- Ollama: normalize provider-prefixed tool-call names at the native stream boundary so Kimi/Ollama calls such as `functions.exec` dispatch as `exec` instead of missing configured tools. Fixes #74487. Thanks @afurm and @carreipeia.

View File

@@ -1,11 +1,125 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:40:46.712Z",
"fallbackKeys": [
"agents.alreadyDefaultTitle",
"agents.channels.configuredCount",
"agents.channels.connectedCount",
"agents.channels.empty",
"agents.channels.enabledCount",
"agents.channels.lastRefresh",
"agents.channels.loadHint",
"agents.channels.noAccounts",
"agents.channels.notConfigured",
"agents.channels.setupGuide",
"agents.channels.subtitle",
"agents.channels.title",
"agents.context.configurationSubtitle",
"agents.context.default",
"agents.context.identityAvatar",
"agents.context.identityName",
"agents.context.openFilesTab",
"agents.context.primaryModel",
"agents.context.runtime",
"agents.context.schedulingSubtitle",
"agents.context.skillsFilter",
"agents.context.title",
"agents.context.workspace",
"agents.copyId",
"agents.copyIdTitle",
"agents.cronPanel.agentJobsSubtitle",
"agents.cronPanel.agentJobsTitle",
"agents.cronPanel.jobs",
"agents.cronPanel.nextWake",
"agents.cronPanel.noJobs",
"agents.cronPanel.runNow",
"agents.cronPanel.schedulerSubtitle",
"agents.cronPanel.schedulerTitle",
"agents.default",
"agents.files.closePreview",
"agents.files.collapsePreview",
"agents.files.content",
"agents.files.coreFilesSubtitle",
"agents.files.coreFilesTitle",
"agents.files.editFile",
"agents.files.empty",
"agents.files.emptyDraft",
"agents.files.expandPreview",
"agents.files.extensionPreview",
"agents.files.lines",
"agents.files.liveDraftPreview",
"agents.files.loadHint",
"agents.files.markdownPreview",
"agents.files.minRead",
"agents.files.missing",
"agents.files.missingHint",
"agents.files.notCreatedYet",
"agents.files.preview",
"agents.files.previewMarkdownTitle",
"agents.files.savedPreview",
"agents.files.selectFile",
"agents.files.updated",
"agents.files.updatedUnknown",
"agents.files.willCreateOnSave",
"agents.files.words",
"agents.files.workspace",
"agents.noAgents",
"agents.selectSubtitle",
"agents.selectTitle",
"agents.setDefault",
"agents.setDefaultTitle",
"agents.tabs.channels",
"agents.tabs.cronJobs",
"agents.tabs.files",
"agents.tabs.overview",
"agents.tabs.skills",
"agents.tabs.tools",
"common.never",
"common.reset",
"debug.eventLogSubtitle",
"debug.eventLogTitle",
"debug.health",
"debug.lastHeartbeat",
"debug.manualRpcSubtitle",
"debug.manualRpcTitle",
"debug.method",
"debug.modelsSubtitle",
"debug.modelsTitle",
"debug.noEvents",
"debug.paramsJson",
"debug.security.audit",
"debug.security.critical",
"debug.security.info",
"debug.security.noCriticalIssues",
"debug.security.runPrefix",
"debug.security.runSuffix",
"debug.security.warnings",
"debug.selectMethod",
"debug.snapshotsSubtitle",
"debug.snapshotsTitle",
"debug.status",
"execApproval.allowOnce",
"execApproval.alwaysAllow",
"execApproval.deny",
"execApproval.execApprovalNeeded",
"execApproval.expired",
"execApproval.expiresIn",
"execApproval.labels.agent",
"execApproval.labels.ask",
"execApproval.labels.cwd",
"execApproval.labels.host",
"execApproval.labels.plugin",
"execApproval.labels.resolved",
"execApproval.labels.security",
"execApproval.labels.session",
"execApproval.labels.severity",
"execApproval.pending",
"execApproval.pluginApprovalNeeded"
],
"generatedAt": "2026-04-29T19:08:30.710Z",
"locale": "ar",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 768,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:35:03.767Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:29.139Z",
"locale": "de",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:36:10.668Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:29.459Z",
"locale": "es",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,125 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:45:53.092Z",
"fallbackKeys": [
"agents.alreadyDefaultTitle",
"agents.channels.configuredCount",
"agents.channels.connectedCount",
"agents.channels.empty",
"agents.channels.enabledCount",
"agents.channels.lastRefresh",
"agents.channels.loadHint",
"agents.channels.noAccounts",
"agents.channels.notConfigured",
"agents.channels.setupGuide",
"agents.channels.subtitle",
"agents.channels.title",
"agents.context.configurationSubtitle",
"agents.context.default",
"agents.context.identityAvatar",
"agents.context.identityName",
"agents.context.openFilesTab",
"agents.context.primaryModel",
"agents.context.runtime",
"agents.context.schedulingSubtitle",
"agents.context.skillsFilter",
"agents.context.title",
"agents.context.workspace",
"agents.copyId",
"agents.copyIdTitle",
"agents.cronPanel.agentJobsSubtitle",
"agents.cronPanel.agentJobsTitle",
"agents.cronPanel.jobs",
"agents.cronPanel.nextWake",
"agents.cronPanel.noJobs",
"agents.cronPanel.runNow",
"agents.cronPanel.schedulerSubtitle",
"agents.cronPanel.schedulerTitle",
"agents.default",
"agents.files.closePreview",
"agents.files.collapsePreview",
"agents.files.content",
"agents.files.coreFilesSubtitle",
"agents.files.coreFilesTitle",
"agents.files.editFile",
"agents.files.empty",
"agents.files.emptyDraft",
"agents.files.expandPreview",
"agents.files.extensionPreview",
"agents.files.lines",
"agents.files.liveDraftPreview",
"agents.files.loadHint",
"agents.files.markdownPreview",
"agents.files.minRead",
"agents.files.missing",
"agents.files.missingHint",
"agents.files.notCreatedYet",
"agents.files.preview",
"agents.files.previewMarkdownTitle",
"agents.files.savedPreview",
"agents.files.selectFile",
"agents.files.updated",
"agents.files.updatedUnknown",
"agents.files.willCreateOnSave",
"agents.files.words",
"agents.files.workspace",
"agents.noAgents",
"agents.selectSubtitle",
"agents.selectTitle",
"agents.setDefault",
"agents.setDefaultTitle",
"agents.tabs.channels",
"agents.tabs.cronJobs",
"agents.tabs.files",
"agents.tabs.overview",
"agents.tabs.skills",
"agents.tabs.tools",
"common.never",
"common.reset",
"debug.eventLogSubtitle",
"debug.eventLogTitle",
"debug.health",
"debug.lastHeartbeat",
"debug.manualRpcSubtitle",
"debug.manualRpcTitle",
"debug.method",
"debug.modelsSubtitle",
"debug.modelsTitle",
"debug.noEvents",
"debug.paramsJson",
"debug.security.audit",
"debug.security.critical",
"debug.security.info",
"debug.security.noCriticalIssues",
"debug.security.runPrefix",
"debug.security.runSuffix",
"debug.security.warnings",
"debug.selectMethod",
"debug.snapshotsSubtitle",
"debug.snapshotsTitle",
"debug.status",
"execApproval.allowOnce",
"execApproval.alwaysAllow",
"execApproval.deny",
"execApproval.execApprovalNeeded",
"execApproval.expired",
"execApproval.expiresIn",
"execApproval.labels.agent",
"execApproval.labels.ask",
"execApproval.labels.cwd",
"execApproval.labels.host",
"execApproval.labels.plugin",
"execApproval.labels.resolved",
"execApproval.labels.security",
"execApproval.labels.session",
"execApproval.labels.severity",
"execApproval.pending",
"execApproval.pluginApprovalNeeded"
],
"generatedAt": "2026-04-29T19:08:33.526Z",
"locale": "fa",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 768,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:36:08.909Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:30.398Z",
"locale": "fr",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:37:59.703Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:31.956Z",
"locale": "id",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,125 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:39:53.120Z",
"fallbackKeys": [
"agents.alreadyDefaultTitle",
"agents.channels.configuredCount",
"agents.channels.connectedCount",
"agents.channels.empty",
"agents.channels.enabledCount",
"agents.channels.lastRefresh",
"agents.channels.loadHint",
"agents.channels.noAccounts",
"agents.channels.notConfigured",
"agents.channels.setupGuide",
"agents.channels.subtitle",
"agents.channels.title",
"agents.context.configurationSubtitle",
"agents.context.default",
"agents.context.identityAvatar",
"agents.context.identityName",
"agents.context.openFilesTab",
"agents.context.primaryModel",
"agents.context.runtime",
"agents.context.schedulingSubtitle",
"agents.context.skillsFilter",
"agents.context.title",
"agents.context.workspace",
"agents.copyId",
"agents.copyIdTitle",
"agents.cronPanel.agentJobsSubtitle",
"agents.cronPanel.agentJobsTitle",
"agents.cronPanel.jobs",
"agents.cronPanel.nextWake",
"agents.cronPanel.noJobs",
"agents.cronPanel.runNow",
"agents.cronPanel.schedulerSubtitle",
"agents.cronPanel.schedulerTitle",
"agents.default",
"agents.files.closePreview",
"agents.files.collapsePreview",
"agents.files.content",
"agents.files.coreFilesSubtitle",
"agents.files.coreFilesTitle",
"agents.files.editFile",
"agents.files.empty",
"agents.files.emptyDraft",
"agents.files.expandPreview",
"agents.files.extensionPreview",
"agents.files.lines",
"agents.files.liveDraftPreview",
"agents.files.loadHint",
"agents.files.markdownPreview",
"agents.files.minRead",
"agents.files.missing",
"agents.files.missingHint",
"agents.files.notCreatedYet",
"agents.files.preview",
"agents.files.previewMarkdownTitle",
"agents.files.savedPreview",
"agents.files.selectFile",
"agents.files.updated",
"agents.files.updatedUnknown",
"agents.files.willCreateOnSave",
"agents.files.words",
"agents.files.workspace",
"agents.noAgents",
"agents.selectSubtitle",
"agents.selectTitle",
"agents.setDefault",
"agents.setDefaultTitle",
"agents.tabs.channels",
"agents.tabs.cronJobs",
"agents.tabs.files",
"agents.tabs.overview",
"agents.tabs.skills",
"agents.tabs.tools",
"common.never",
"common.reset",
"debug.eventLogSubtitle",
"debug.eventLogTitle",
"debug.health",
"debug.lastHeartbeat",
"debug.manualRpcSubtitle",
"debug.manualRpcTitle",
"debug.method",
"debug.modelsSubtitle",
"debug.modelsTitle",
"debug.noEvents",
"debug.paramsJson",
"debug.security.audit",
"debug.security.critical",
"debug.security.info",
"debug.security.noCriticalIssues",
"debug.security.runPrefix",
"debug.security.runSuffix",
"debug.security.warnings",
"debug.selectMethod",
"debug.snapshotsSubtitle",
"debug.snapshotsTitle",
"debug.status",
"execApproval.allowOnce",
"execApproval.alwaysAllow",
"execApproval.deny",
"execApproval.execApprovalNeeded",
"execApproval.expired",
"execApproval.expiresIn",
"execApproval.labels.agent",
"execApproval.labels.ask",
"execApproval.labels.cwd",
"execApproval.labels.host",
"execApproval.labels.plugin",
"execApproval.labels.resolved",
"execApproval.labels.security",
"execApproval.labels.session",
"execApproval.labels.severity",
"execApproval.pending",
"execApproval.pluginApprovalNeeded"
],
"generatedAt": "2026-04-29T19:08:31.026Z",
"locale": "it",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 768,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:36:05.788Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:29.768Z",
"locale": "ja-JP",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:36:02.577Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:30.082Z",
"locale": "ko",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,125 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:42:07.899Z",
"fallbackKeys": [
"agents.alreadyDefaultTitle",
"agents.channels.configuredCount",
"agents.channels.connectedCount",
"agents.channels.empty",
"agents.channels.enabledCount",
"agents.channels.lastRefresh",
"agents.channels.loadHint",
"agents.channels.noAccounts",
"agents.channels.notConfigured",
"agents.channels.setupGuide",
"agents.channels.subtitle",
"agents.channels.title",
"agents.context.configurationSubtitle",
"agents.context.default",
"agents.context.identityAvatar",
"agents.context.identityName",
"agents.context.openFilesTab",
"agents.context.primaryModel",
"agents.context.runtime",
"agents.context.schedulingSubtitle",
"agents.context.skillsFilter",
"agents.context.title",
"agents.context.workspace",
"agents.copyId",
"agents.copyIdTitle",
"agents.cronPanel.agentJobsSubtitle",
"agents.cronPanel.agentJobsTitle",
"agents.cronPanel.jobs",
"agents.cronPanel.nextWake",
"agents.cronPanel.noJobs",
"agents.cronPanel.runNow",
"agents.cronPanel.schedulerSubtitle",
"agents.cronPanel.schedulerTitle",
"agents.default",
"agents.files.closePreview",
"agents.files.collapsePreview",
"agents.files.content",
"agents.files.coreFilesSubtitle",
"agents.files.coreFilesTitle",
"agents.files.editFile",
"agents.files.empty",
"agents.files.emptyDraft",
"agents.files.expandPreview",
"agents.files.extensionPreview",
"agents.files.lines",
"agents.files.liveDraftPreview",
"agents.files.loadHint",
"agents.files.markdownPreview",
"agents.files.minRead",
"agents.files.missing",
"agents.files.missingHint",
"agents.files.notCreatedYet",
"agents.files.preview",
"agents.files.previewMarkdownTitle",
"agents.files.savedPreview",
"agents.files.selectFile",
"agents.files.updated",
"agents.files.updatedUnknown",
"agents.files.willCreateOnSave",
"agents.files.words",
"agents.files.workspace",
"agents.noAgents",
"agents.selectSubtitle",
"agents.selectTitle",
"agents.setDefault",
"agents.setDefaultTitle",
"agents.tabs.channels",
"agents.tabs.cronJobs",
"agents.tabs.files",
"agents.tabs.overview",
"agents.tabs.skills",
"agents.tabs.tools",
"common.never",
"common.reset",
"debug.eventLogSubtitle",
"debug.eventLogTitle",
"debug.health",
"debug.lastHeartbeat",
"debug.manualRpcSubtitle",
"debug.manualRpcTitle",
"debug.method",
"debug.modelsSubtitle",
"debug.modelsTitle",
"debug.noEvents",
"debug.paramsJson",
"debug.security.audit",
"debug.security.critical",
"debug.security.info",
"debug.security.noCriticalIssues",
"debug.security.runPrefix",
"debug.security.runSuffix",
"debug.security.warnings",
"debug.selectMethod",
"debug.snapshotsSubtitle",
"debug.snapshotsTitle",
"debug.status",
"execApproval.allowOnce",
"execApproval.alwaysAllow",
"execApproval.deny",
"execApproval.execApprovalNeeded",
"execApproval.expired",
"execApproval.expiresIn",
"execApproval.labels.agent",
"execApproval.labels.ask",
"execApproval.labels.cwd",
"execApproval.labels.host",
"execApproval.labels.plugin",
"execApproval.labels.resolved",
"execApproval.labels.security",
"execApproval.labels.session",
"execApproval.labels.severity",
"execApproval.pending",
"execApproval.pluginApprovalNeeded"
],
"generatedAt": "2026-04-29T19:08:33.205Z",
"locale": "nl",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 768,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:38:29.591Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:32.268Z",
"locale": "pl",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:35:02.393Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:28.821Z",
"locale": "pt-BR",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:38:48.503Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:32.585Z",
"locale": "th",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:36:58.183Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:31.341Z",
"locale": "tr",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:37:08.260Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:31.648Z",
"locale": "uk",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -1,11 +1,125 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:42:15.736Z",
"fallbackKeys": [
"agents.alreadyDefaultTitle",
"agents.channels.configuredCount",
"agents.channels.connectedCount",
"agents.channels.empty",
"agents.channels.enabledCount",
"agents.channels.lastRefresh",
"agents.channels.loadHint",
"agents.channels.noAccounts",
"agents.channels.notConfigured",
"agents.channels.setupGuide",
"agents.channels.subtitle",
"agents.channels.title",
"agents.context.configurationSubtitle",
"agents.context.default",
"agents.context.identityAvatar",
"agents.context.identityName",
"agents.context.openFilesTab",
"agents.context.primaryModel",
"agents.context.runtime",
"agents.context.schedulingSubtitle",
"agents.context.skillsFilter",
"agents.context.title",
"agents.context.workspace",
"agents.copyId",
"agents.copyIdTitle",
"agents.cronPanel.agentJobsSubtitle",
"agents.cronPanel.agentJobsTitle",
"agents.cronPanel.jobs",
"agents.cronPanel.nextWake",
"agents.cronPanel.noJobs",
"agents.cronPanel.runNow",
"agents.cronPanel.schedulerSubtitle",
"agents.cronPanel.schedulerTitle",
"agents.default",
"agents.files.closePreview",
"agents.files.collapsePreview",
"agents.files.content",
"agents.files.coreFilesSubtitle",
"agents.files.coreFilesTitle",
"agents.files.editFile",
"agents.files.empty",
"agents.files.emptyDraft",
"agents.files.expandPreview",
"agents.files.extensionPreview",
"agents.files.lines",
"agents.files.liveDraftPreview",
"agents.files.loadHint",
"agents.files.markdownPreview",
"agents.files.minRead",
"agents.files.missing",
"agents.files.missingHint",
"agents.files.notCreatedYet",
"agents.files.preview",
"agents.files.previewMarkdownTitle",
"agents.files.savedPreview",
"agents.files.selectFile",
"agents.files.updated",
"agents.files.updatedUnknown",
"agents.files.willCreateOnSave",
"agents.files.words",
"agents.files.workspace",
"agents.noAgents",
"agents.selectSubtitle",
"agents.selectTitle",
"agents.setDefault",
"agents.setDefaultTitle",
"agents.tabs.channels",
"agents.tabs.cronJobs",
"agents.tabs.files",
"agents.tabs.overview",
"agents.tabs.skills",
"agents.tabs.tools",
"common.never",
"common.reset",
"debug.eventLogSubtitle",
"debug.eventLogTitle",
"debug.health",
"debug.lastHeartbeat",
"debug.manualRpcSubtitle",
"debug.manualRpcTitle",
"debug.method",
"debug.modelsSubtitle",
"debug.modelsTitle",
"debug.noEvents",
"debug.paramsJson",
"debug.security.audit",
"debug.security.critical",
"debug.security.info",
"debug.security.noCriticalIssues",
"debug.security.runPrefix",
"debug.security.runSuffix",
"debug.security.warnings",
"debug.selectMethod",
"debug.snapshotsSubtitle",
"debug.snapshotsTitle",
"debug.status",
"execApproval.allowOnce",
"execApproval.alwaysAllow",
"execApproval.deny",
"execApproval.execApprovalNeeded",
"execApproval.expired",
"execApproval.expiresIn",
"execApproval.labels.agent",
"execApproval.labels.ask",
"execApproval.labels.cwd",
"execApproval.labels.host",
"execApproval.labels.plugin",
"execApproval.labels.resolved",
"execApproval.labels.security",
"execApproval.labels.session",
"execApproval.labels.severity",
"execApproval.pending",
"execApproval.pluginApprovalNeeded"
],
"generatedAt": "2026-04-29T19:08:32.902Z",
"locale": "vi",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 768,
"workflow": 1
}

View File

@@ -1,11 +1,11 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:35:12.940Z",
"generatedAt": "2026-04-29T19:08:28.139Z",
"locale": "zh-CN",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 881,
"workflow": 1
}

View File

@@ -1,11 +1,13 @@
{
"fallbackKeys": [],
"generatedAt": "2026-04-29T17:35:07.758Z",
"fallbackKeys": [
"agents.context.runtime"
],
"generatedAt": "2026-04-29T19:08:28.498Z",
"locale": "zh-TW",
"model": "gpt-5.5",
"provider": "openai",
"sourceHash": "e2d2b3df6a5e614401e887d4c49d24c633ac3435956040c48672ec8b289abdd4",
"totalKeys": 768,
"translatedKeys": 768,
"sourceHash": "a6a1060fe4eda88e0261e78c7c635df6e579a56cc539595a331da79dc7ca832b",
"totalKeys": 881,
"translatedKeys": 880,
"workflow": 1
}

View File

@@ -16,6 +16,7 @@ export const ar: TranslationMap = {
connected: "متصل",
refresh: "تحديث",
reload: "إعادة التحميل",
reset: "Reset",
probe: "فحص",
call: "اتصال",
confirm: "تأكيد",
@@ -24,6 +25,7 @@ export const ar: TranslationMap = {
enabled: "مفعّل",
disabled: "معطّل",
na: "غير متوفر",
never: "never",
configured: "مهيأ",
running: "قيد التشغيل",
linked: "مرتبط",
@@ -137,6 +139,137 @@ export const ar: TranslationMap = {
lastInput: "آخر إدخال {time}",
reason: "السبب {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "متصل: {id}",
connected: "متصل",

View File

@@ -16,6 +16,7 @@ export const de: TranslationMap = {
connected: "Verbunden",
refresh: "Aktualisieren",
reload: "Neu laden",
reset: "Reset",
probe: "Prüfen",
call: "Anrufen",
confirm: "Bestätigen",
@@ -24,6 +25,7 @@ export const de: TranslationMap = {
enabled: "Aktiviert",
disabled: "Deaktiviert",
na: "k. A.",
never: "never",
configured: "Konfiguriert",
running: "Wird ausgeführt",
linked: "Verknüpft",
@@ -141,6 +143,137 @@ export const de: TranslationMap = {
lastInput: "Letzte Eingabe {time}",
reason: "Grund {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Verbunden: {id}",
connected: "Verbunden",

View File

@@ -15,6 +15,7 @@ export const en: TranslationMap = {
connected: "Connected",
refresh: "Refresh",
reload: "Reload",
reset: "Reset",
probe: "Probe",
call: "Call",
confirm: "Confirm",
@@ -23,6 +24,7 @@ export const en: TranslationMap = {
enabled: "Enabled",
disabled: "Disabled",
na: "n/a",
never: "never",
configured: "Configured",
running: "Running",
linked: "Linked",
@@ -136,6 +138,137 @@ export const en: TranslationMap = {
lastInput: "Last input {time}",
reason: "Reason {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Connected: {id}",
connected: "Connected",

View File

@@ -16,6 +16,7 @@ export const es: TranslationMap = {
connected: "Conectado",
refresh: "Actualizar",
reload: "Recargar",
reset: "Reset",
probe: "Probar",
call: "Llamada",
confirm: "Confirmar",
@@ -24,6 +25,7 @@ export const es: TranslationMap = {
enabled: "Habilitado",
disabled: "Deshabilitado",
na: "n/d",
never: "never",
configured: "Configurado",
running: "En ejecución",
linked: "Vinculado",
@@ -138,6 +140,137 @@ export const es: TranslationMap = {
lastInput: "Última entrada {time}",
reason: "Motivo {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Conectado: {id}",
connected: "Conectado",

View File

@@ -16,6 +16,7 @@ export const fa: TranslationMap = {
connected: "متصل",
refresh: "تازه‌سازی",
reload: "بارگذاری مجدد",
reset: "Reset",
probe: "بررسی",
call: "فراخوانی",
confirm: "تأیید",
@@ -24,6 +25,7 @@ export const fa: TranslationMap = {
enabled: "فعال",
disabled: "غیرفعال",
na: "n/a",
never: "never",
configured: "پیکربندی‌شده",
running: "در حال اجرا",
linked: "پیوندشده",
@@ -139,6 +141,137 @@ export const fa: TranslationMap = {
lastInput: "آخرین ورودی {time}",
reason: "دلیل {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "متصل: {id}",
connected: "متصل",

View File

@@ -16,6 +16,7 @@ export const fr: TranslationMap = {
connected: "Connecté",
refresh: "Actualiser",
reload: "Recharger",
reset: "Reset",
probe: "Sonder",
call: "Appeler",
confirm: "Confirmer",
@@ -24,6 +25,7 @@ export const fr: TranslationMap = {
enabled: "Activé",
disabled: "Désactivé",
na: "n/d",
never: "never",
configured: "Configuré",
running: "En cours dexécution",
linked: "Lié",
@@ -140,6 +142,137 @@ export const fr: TranslationMap = {
lastInput: "Dernière entrée {time}",
reason: "Raison {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Connecté : {id}",
connected: "Connecté",

View File

@@ -16,6 +16,7 @@ export const id: TranslationMap = {
connected: "Terhubung",
refresh: "Muat ulang",
reload: "Muat ulang",
reset: "Reset",
probe: "Probe",
call: "Panggil",
confirm: "Konfirmasi",
@@ -24,6 +25,7 @@ export const id: TranslationMap = {
enabled: "Diaktifkan",
disabled: "Dinonaktifkan",
na: "t/a",
never: "never",
configured: "Dikonfigurasi",
running: "Berjalan",
linked: "Ditautkan",
@@ -138,6 +140,137 @@ export const id: TranslationMap = {
lastInput: "Input terakhir {time}",
reason: "Alasan {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Terhubung: {id}",
connected: "Terhubung",

View File

@@ -16,6 +16,7 @@ export const it: TranslationMap = {
connected: "Connesso",
refresh: "Aggiorna",
reload: "Ricarica",
reset: "Reset",
probe: "Sonda",
call: "Chiama",
confirm: "Conferma",
@@ -24,6 +25,7 @@ export const it: TranslationMap = {
enabled: "Abilitato",
disabled: "Disabilitato",
na: "n/d",
never: "never",
configured: "Configurato",
running: "In esecuzione",
linked: "Collegato",
@@ -138,6 +140,137 @@ export const it: TranslationMap = {
lastInput: "Ultimo input {time}",
reason: "Motivo {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Connesso: {id}",
connected: "Connesso",

View File

@@ -16,6 +16,7 @@ export const ja_JP: TranslationMap = {
connected: "接続済み",
refresh: "更新",
reload: "再読み込み",
reset: "Reset",
probe: "プローブ",
call: "通話",
confirm: "確認",
@@ -24,6 +25,7 @@ export const ja_JP: TranslationMap = {
enabled: "有効",
disabled: "無効",
na: "n/a",
never: "never",
configured: "設定済み",
running: "実行中",
linked: "リンク済み",
@@ -141,6 +143,137 @@ export const ja_JP: TranslationMap = {
lastInput: "最後の入力 {time}",
reason: "理由 {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "接続済み: {id}",
connected: "接続済み",

View File

@@ -16,6 +16,7 @@ export const ko: TranslationMap = {
connected: "연결됨",
refresh: "새로고침",
reload: "다시 로드",
reset: "Reset",
probe: "프로브",
call: "호출",
confirm: "확인",
@@ -24,6 +25,7 @@ export const ko: TranslationMap = {
enabled: "사용",
disabled: "사용 안 함",
na: "해당 없음",
never: "never",
configured: "구성됨",
running: "실행 중",
linked: "연결됨",
@@ -137,6 +139,137 @@ export const ko: TranslationMap = {
lastInput: "마지막 입력 {time}",
reason: "사유 {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "연결됨: {id}",
connected: "연결됨",

View File

@@ -16,6 +16,7 @@ export const nl: TranslationMap = {
connected: "Verbonden",
refresh: "Vernieuwen",
reload: "Opnieuw laden",
reset: "Reset",
probe: "Testen",
call: "Aanroepen",
confirm: "Bevestigen",
@@ -24,6 +25,7 @@ export const nl: TranslationMap = {
enabled: "Ingeschakeld",
disabled: "Uitgeschakeld",
na: "n.v.t.",
never: "never",
configured: "Geconfigureerd",
running: "Actief",
linked: "Gekoppeld",
@@ -140,6 +142,137 @@ export const nl: TranslationMap = {
lastInput: "Laatste invoer {time}",
reason: "Reden {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Verbonden: {id}",
connected: "Verbonden",

View File

@@ -16,6 +16,7 @@ export const pl: TranslationMap = {
connected: "Połączono",
refresh: "Odśwież",
reload: "Przeładuj",
reset: "Reset",
probe: "Sprawdź",
call: "Połączenie",
confirm: "Potwierdź",
@@ -24,6 +25,7 @@ export const pl: TranslationMap = {
enabled: "Włączone",
disabled: "Wyłączone",
na: "n/d",
never: "never",
configured: "Skonfigurowano",
running: "Uruchomiono",
linked: "Połączono",
@@ -139,6 +141,137 @@ export const pl: TranslationMap = {
lastInput: "Ostatnie wejście {time}",
reason: "Powód {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Połączono: {id}",
connected: "Połączono",

View File

@@ -16,6 +16,7 @@ export const pt_BR: TranslationMap = {
connected: "Conectado",
refresh: "Atualizar",
reload: "Recarregar",
reset: "Reset",
probe: "Sondar",
call: "Ligar",
confirm: "Confirmar",
@@ -24,6 +25,7 @@ export const pt_BR: TranslationMap = {
enabled: "Ativado",
disabled: "Desativado",
na: "n/d",
never: "never",
configured: "Configurado",
running: "Em execução",
linked: "Vinculado",
@@ -138,6 +140,137 @@ export const pt_BR: TranslationMap = {
lastInput: "Última entrada {time}",
reason: "Motivo {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Conectado: {id}",
connected: "Conectado",

View File

@@ -16,6 +16,7 @@ export const th: TranslationMap = {
connected: "เชื่อมต่อแล้ว",
refresh: "รีเฟรช",
reload: "โหลดใหม่",
reset: "Reset",
probe: "ตรวจสอบ",
call: "โทร",
confirm: "ยืนยัน",
@@ -24,6 +25,7 @@ export const th: TranslationMap = {
enabled: "เปิดใช้งาน",
disabled: "ปิดใช้งาน",
na: "n/a",
never: "never",
configured: "กำหนดค่าแล้ว",
running: "กำลังทำงาน",
linked: "เชื่อมโยงแล้ว",
@@ -136,6 +138,137 @@ export const th: TranslationMap = {
lastInput: "อินพุตล่าสุด {time}",
reason: "เหตุผล {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "เชื่อมต่อแล้ว: {id}",
connected: "เชื่อมต่อแล้ว",

View File

@@ -16,6 +16,7 @@ export const tr: TranslationMap = {
connected: "Bağlandı",
refresh: "Yenile",
reload: "Yeniden yükle",
reset: "Reset",
probe: "Sına",
call: "Ara",
confirm: "Onayla",
@@ -24,6 +25,7 @@ export const tr: TranslationMap = {
enabled: "Etkin",
disabled: "Devre dışı",
na: "yok",
never: "never",
configured: "Yapılandırıldı",
running: "Çalışıyor",
linked: "Bağlandı",
@@ -140,6 +142,137 @@ export const tr: TranslationMap = {
lastInput: "Son giriş {time}",
reason: "Neden {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Bağlı: {id}",
connected: "Bağlı",

View File

@@ -16,6 +16,7 @@ export const uk: TranslationMap = {
connected: "Підключено",
refresh: "Оновити",
reload: "Перезавантажити",
reset: "Reset",
probe: "Перевірити",
call: "Виклик",
confirm: "Підтвердити",
@@ -24,6 +25,7 @@ export const uk: TranslationMap = {
enabled: "Увімкнено",
disabled: "Вимкнено",
na: "н/д",
never: "never",
configured: "Налаштовано",
running: "Запущено",
linked: "Пов’язано",
@@ -139,6 +141,137 @@ export const uk: TranslationMap = {
lastInput: "Останнє введення {time}",
reason: "Причина {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Підключено: {id}",
connected: "Підключено",

View File

@@ -16,6 +16,7 @@ export const vi: TranslationMap = {
connected: "Đã kết nối",
refresh: "Làm mới",
reload: "Tải lại",
reset: "Reset",
probe: "Thăm dò",
call: "Gọi",
confirm: "Xác nhận",
@@ -24,6 +25,7 @@ export const vi: TranslationMap = {
enabled: "Đã bật",
disabled: "Đã tắt",
na: "n/a",
never: "never",
configured: "Đã cấu hình",
running: "Đang chạy",
linked: "Đã liên kết",
@@ -138,6 +140,137 @@ export const vi: TranslationMap = {
lastInput: "Đầu vào gần nhất {time}",
reason: "Lý do {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "Đã kết nối: {id}",
connected: "Đã kết nối",

View File

@@ -16,6 +16,7 @@ export const zh_CN: TranslationMap = {
connected: "已连接",
refresh: "刷新",
reload: "重新加载",
reset: "重置",
probe: "探测",
call: "调用",
confirm: "确认",
@@ -24,6 +25,7 @@ export const zh_CN: TranslationMap = {
enabled: "已启用",
disabled: "已禁用",
na: "不适用",
never: "从未",
configured: "已配置",
running: "运行中",
linked: "已关联",
@@ -136,6 +138,137 @@ export const zh_CN: TranslationMap = {
lastInput: "上次输入 {time}",
reason: "原因 {reason}",
},
agents: {
noAgents: "无代理",
copyId: "复制 ID",
copyIdTitle: "将代理 ID 复制到剪贴板",
default: "默认",
setDefault: "设为默认",
alreadyDefaultTitle: "已是默认代理",
setDefaultTitle: "设为默认代理",
selectTitle: "选择代理",
selectSubtitle: "选择代理以查看其工作区和工具。",
tabs: {
overview: "概览",
files: "文件",
tools: "工具",
skills: "技能",
channels: "频道",
cronJobs: "Cron Jobs",
},
context: {
title: "代理上下文",
workspace: "工作区",
openFilesTab: "打开文件标签",
primaryModel: "主模型",
runtime: "运行时",
identityName: "身份名称",
identityAvatar: "身份头像",
skillsFilter: "技能筛选器",
default: "默认",
configurationSubtitle: "工作区、身份和模型配置。",
schedulingSubtitle: "工作区和调度目标。",
},
channels: {
title: "频道",
subtitle: "Gateway 全局频道状态快照。",
lastRefresh: "上次刷新:{time}",
loadHint: "加载频道以查看实时状态。",
empty: "未找到频道。",
connectedCount: "{connected}/{total} 已连接",
noAccounts: "无账户",
configuredCount: "已配置 {count} 个",
notConfigured: "未配置",
enabledCount: "已启用 {count} 个",
setupGuide: "设置指南",
},
cronPanel: {
schedulerTitle: "调度器",
schedulerSubtitle: "Gateway 定时任务状态。",
jobs: "任务",
nextWake: "下次唤醒",
agentJobsTitle: "代理定时任务",
agentJobsSubtitle: "面向此代理的计划任务。",
noJobs: "未分配任务。",
runNow: "立即运行",
},
files: {
emptyDraft: "空草稿",
minRead: "{count} 分钟阅读",
markdownPreview: "Markdown 预览",
extensionPreview: "{ext} 预览",
preview: "预览",
expandPreview: "展开预览",
collapsePreview: "收起预览",
editFile: "编辑文件",
closePreview: "关闭预览",
coreFilesTitle: "核心文件",
coreFilesSubtitle: "引导人格、身份和工具指引。",
workspace: "工作区",
loadHint: "加载代理工作区文件以编辑核心指令。",
empty: "未找到文件。",
missing: "缺失",
selectFile: "选择要编辑的文件。",
previewMarkdownTitle: "预览渲染后的 Markdown",
willCreateOnSave: "保存时将创建",
liveDraftPreview: "实时草稿预览",
savedPreview: "已保存预览",
updated: "更新于 {time}",
notCreatedYet: "尚未创建",
updatedUnknown: "更新时间未知",
missingHint: "此文件缺失。保存后将在代理工作区中创建它。",
content: "内容",
words: "{count} 个词",
lines: "行",
},
},
debug: {
snapshotsTitle: "快照",
snapshotsSubtitle: "状态、健康状况和心跳数据。",
status: "状态",
health: "健康状况",
lastHeartbeat: "上次心跳",
security: {
audit: "安全审计",
critical: "{count} 个严重问题",
warnings: "{count} 个警告",
noCriticalIssues: "无严重问题",
info: "{count} 条信息",
runPrefix: "运行",
runSuffix: "查看详情。",
},
manualRpcTitle: "手动 RPC",
manualRpcSubtitle: "发送带 JSON 参数的原始 Gateway 方法。",
method: "方法",
selectMethod: "选择方法…",
paramsJson: "参数 (JSON)",
modelsTitle: "模型",
modelsSubtitle: "来自 models.list 的目录。",
eventLogTitle: "事件日志",
eventLogSubtitle: "最新 Gateway 事件。",
noEvents: "暂无事件。",
},
execApproval: {
expiresIn: "{time} 后过期",
expired: "已过期",
execApprovalNeeded: "需要 Exec 审批",
pluginApprovalNeeded: "需要插件审批",
pending: "{count} 个待处理",
allowOnce: "允许一次",
alwaysAllow: "始终允许",
deny: "拒绝",
labels: {
host: "主机",
agent: "代理",
session: "会话",
cwd: "CWD",
resolved: "已解析",
security: "安全",
ask: "询问策略",
severity: "严重性",
plugin: "插件",
},
},
agentTools: {
connectedSource: "已连接:{id}",
connected: "已连接",

View File

@@ -16,6 +16,7 @@ export const zh_TW: TranslationMap = {
connected: "已連線",
refresh: "刷新",
reload: "重新載入",
reset: "Reset",
probe: "探測",
call: "呼叫",
confirm: "確認",
@@ -24,6 +25,7 @@ export const zh_TW: TranslationMap = {
enabled: "已啟用",
disabled: "已禁用",
na: "不適用",
never: "never",
configured: "已設定",
running: "執行中",
linked: "已連結",
@@ -136,6 +138,137 @@ export const zh_TW: TranslationMap = {
lastInput: "上次輸入 {time}",
reason: "原因 {reason}",
},
agents: {
noAgents: "No agents",
copyId: "Copy ID",
copyIdTitle: "Copy agent ID to clipboard",
default: "Default",
setDefault: "Set Default",
alreadyDefaultTitle: "Already the default agent",
setDefaultTitle: "Set as the default agent",
selectTitle: "Select an agent",
selectSubtitle: "Pick an agent to inspect its workspace and tools.",
tabs: {
overview: "Overview",
files: "Files",
tools: "Tools",
skills: "Skills",
channels: "Channels",
cronJobs: "Cron Jobs",
},
context: {
title: "Agent Context",
workspace: "Workspace",
openFilesTab: "Open Files tab",
primaryModel: "Primary Model",
runtime: "Runtime",
identityName: "Identity Name",
identityAvatar: "Identity Avatar",
skillsFilter: "Skills Filter",
default: "Default",
configurationSubtitle: "Workspace, identity, and model configuration.",
schedulingSubtitle: "Workspace and scheduling targets.",
},
channels: {
title: "Channels",
subtitle: "Gateway-wide channel status snapshot.",
lastRefresh: "Last refresh: {time}",
loadHint: "Load channels to see live status.",
empty: "No channels found.",
connectedCount: "{connected}/{total} connected",
noAccounts: "no accounts",
configuredCount: "{count} configured",
notConfigured: "not configured",
enabledCount: "{count} enabled",
setupGuide: "Setup guide",
},
cronPanel: {
schedulerTitle: "Scheduler",
schedulerSubtitle: "Gateway cron status.",
jobs: "Jobs",
nextWake: "Next wake",
agentJobsTitle: "Agent Cron Jobs",
agentJobsSubtitle: "Scheduled jobs targeting this agent.",
noJobs: "No jobs assigned.",
runNow: "Run Now",
},
files: {
emptyDraft: "Empty draft",
minRead: "{count} min read",
markdownPreview: "Markdown Preview",
extensionPreview: "{ext} Preview",
preview: "Preview",
expandPreview: "Expand preview",
collapsePreview: "Collapse preview",
editFile: "Edit file",
closePreview: "Close preview",
coreFilesTitle: "Core Files",
coreFilesSubtitle: "Bootstrap persona, identity, and tool guidance.",
workspace: "Workspace",
loadHint: "Load the agent workspace files to edit core instructions.",
empty: "No files found.",
missing: "missing",
selectFile: "Select a file to edit.",
previewMarkdownTitle: "Preview rendered markdown",
willCreateOnSave: "Will Create on Save",
liveDraftPreview: "Live Draft Preview",
savedPreview: "Saved Preview",
updated: "Updated {time}",
notCreatedYet: "Not Created Yet",
updatedUnknown: "Updated Unknown",
missingHint: "This file is missing. Saving will create it in the agent workspace.",
content: "Content",
words: "{count} words",
lines: "lines",
},
},
debug: {
snapshotsTitle: "Snapshots",
snapshotsSubtitle: "Status, health, and heartbeat data.",
status: "Status",
health: "Health",
lastHeartbeat: "Last heartbeat",
security: {
audit: "Security audit",
critical: "{count} critical",
warnings: "{count} warnings",
noCriticalIssues: "No critical issues",
info: "{count} info",
runPrefix: "Run",
runSuffix: "for details.",
},
manualRpcTitle: "Manual RPC",
manualRpcSubtitle: "Send a raw gateway method with JSON params.",
method: "Method",
selectMethod: "Select a method…",
paramsJson: "Params (JSON)",
modelsTitle: "Models",
modelsSubtitle: "Catalog from models.list.",
eventLogTitle: "Event Log",
eventLogSubtitle: "Latest gateway events.",
noEvents: "No events yet.",
},
execApproval: {
expiresIn: "expires in {time}",
expired: "expired",
execApprovalNeeded: "Exec approval needed",
pluginApprovalNeeded: "Plugin approval needed",
pending: "{count} pending",
allowOnce: "Allow once",
alwaysAllow: "Always allow",
deny: "Deny",
labels: {
host: "Host",
agent: "Agent",
session: "Session",
cwd: "CWD",
resolved: "Resolved",
security: "Security",
ask: "Ask",
severity: "Severity",
plugin: "Plugin",
},
},
agentTools: {
connectedSource: "已連線:{id}",
connected: "已連線",

View File

@@ -34,17 +34,19 @@ function countLines(text: string) {
function estimateReadingTimeLabel(wordCount: number) {
if (wordCount <= 0) {
return "Empty draft";
return t("agents.files.emptyDraft");
}
return `${Math.max(1, Math.round(wordCount / 220))} min read`;
return t("agents.files.minRead", { count: String(Math.max(1, Math.round(wordCount / 220))) });
}
function getExtensionLabel(fileName: string) {
const ext = fileName.split(".").pop()?.trim().toLowerCase();
if (ext === "md" || ext === "markdown") {
return "Markdown Preview";
return t("agents.files.markdownPreview");
}
return ext ? `${ext.toUpperCase()} Preview` : "Preview";
return ext
? t("agents.files.extensionPreview", { ext: ext.toUpperCase() })
: t("agents.files.preview");
}
function formatWorkspaceRelativePath(filePath: string, workspace: string | null | undefined) {
@@ -78,7 +80,7 @@ function setPreviewExpandButtonState(button: Element | null | undefined, isFulls
if (!(button instanceof HTMLElement)) {
return;
}
const label = isFullscreen ? "Collapse preview" : "Expand preview";
const label = isFullscreen ? t("agents.files.collapsePreview") : t("agents.files.expandPreview");
button.classList.toggle("is-fullscreen", isFullscreen);
button.setAttribute("aria-pressed", String(isFullscreen));
button.setAttribute("aria-label", label);
@@ -92,45 +94,45 @@ function renderAgentContextCard(
) {
return html`
<section class="card">
<div class="card-title">Agent Context</div>
<div class="card-title">${t("agents.context.title")}</div>
<div class="card-sub">${subtitle}</div>
<div class="agents-overview-grid" style="margin-top: 16px;">
<div class="agent-kv">
<div class="label">Workspace</div>
<div class="label">${t("agents.context.workspace")}</div>
<div>
<button
type="button"
class="workspace-link mono"
@click=${() => onSelectPanel("files")}
title="Open Files tab"
title=${t("agents.context.openFilesTab")}
>
${context.workspace}
</button>
</div>
</div>
<div class="agent-kv">
<div class="label">Primary Model</div>
<div class="label">${t("agents.context.primaryModel")}</div>
<div class="mono">${context.model}</div>
</div>
<div class="agent-kv">
<div class="label">Runtime</div>
<div class="label">${t("agents.context.runtime")}</div>
<div class="mono">${context.runtime}</div>
</div>
<div class="agent-kv">
<div class="label">Identity Name</div>
<div class="label">${t("agents.context.identityName")}</div>
<div>${context.identityName}</div>
</div>
<div class="agent-kv">
<div class="label">Identity Avatar</div>
<div class="label">${t("agents.context.identityAvatar")}</div>
<div>${context.identityAvatar}</div>
</div>
<div class="agent-kv">
<div class="label">Skills Filter</div>
<div class="label">${t("agents.context.skillsFilter")}</div>
<div>${context.skillsLabel}</div>
</div>
<div class="agent-kv">
<div class="label">Default</div>
<div>${context.isDefault ? "yes" : "no"}</div>
<div class="label">${t("agents.context.default")}</div>
<div>${context.isDefault ? t("common.yes") : t("common.no")}</div>
</div>
</div>
</section>
@@ -227,48 +229,55 @@ export function renderAgentChannels(params: {
const entries = resolveChannelEntries(params.snapshot);
const lastSuccessLabel = params.lastSuccess
? formatRelativeTimestamp(params.lastSuccess)
: "never";
: t("common.never");
return html`
<section class="grid grid-cols-2">
${renderAgentContextCard(
params.context,
"Workspace, identity, and model configuration.",
t("agents.context.configurationSubtitle"),
params.onSelectPanel,
)}
<section class="card">
<div class="row" style="justify-content: space-between;">
<div>
<div class="card-title">Channels</div>
<div class="card-sub">Gateway-wide channel status snapshot.</div>
<div class="card-title">${t("agents.channels.title")}</div>
<div class="card-sub">${t("agents.channels.subtitle")}</div>
</div>
<button class="btn btn--sm" ?disabled=${params.loading} @click=${params.onRefresh}>
${params.loading ? t("common.refreshing") : t("common.refresh")}
</button>
</div>
<div class="muted" style="margin-top: 8px;">Last refresh: ${lastSuccessLabel}</div>
<div class="muted" style="margin-top: 8px;">
${t("agents.channels.lastRefresh", { time: lastSuccessLabel })}
</div>
${params.error
? html`<div class="callout danger" style="margin-top: 12px;">${params.error}</div>`
: nothing}
${!params.snapshot
? html`
<div class="callout info" style="margin-top: 12px">
Load channels to see live status.
${t("agents.channels.loadHint")}
</div>
`
: nothing}
${entries.length === 0
? html` <div class="muted" style="margin-top: 16px">No channels found.</div> `
? html` <div class="muted" style="margin-top: 16px">${t("agents.channels.empty")}</div>`
: html`
<div class="list" style="margin-top: 16px;">
${entries.map((entry) => {
const summary = summarizeChannelAccounts(entry.accounts);
const status = summary.total
? `${summary.connected}/${summary.total} connected`
: "no accounts";
? t("agents.channels.connectedCount", {
connected: String(summary.connected),
total: String(summary.total),
})
: t("agents.channels.noAccounts");
const configLabel = summary.configured
? `${summary.configured} configured`
: "not configured";
const enabled = summary.total ? `${summary.enabled} enabled` : "disabled";
? t("agents.channels.configuredCount", { count: String(summary.configured) })
: t("agents.channels.notConfigured");
const enabled = summary.total
? t("agents.channels.enabledCount", { count: String(summary.enabled) })
: t("common.disabled");
const extras = resolveChannelExtrasFromConfig({
configForm: params.configForm,
channelId: entry.id,
@@ -292,7 +301,7 @@ export function renderAgentChannels(params: {
target="_blank"
rel="noopener"
style="color: var(--accent); font-size: 12px"
>Setup guide</a
>${t("agents.channels.setupGuide")}</a
>
</div>
`
@@ -327,14 +336,14 @@ export function renderAgentCron(params: {
<section class="grid grid-cols-2">
${renderAgentContextCard(
params.context,
"Workspace and scheduling targets.",
t("agents.context.schedulingSubtitle"),
params.onSelectPanel,
)}
<section class="card">
<div class="row" style="justify-content: space-between;">
<div>
<div class="card-title">Scheduler</div>
<div class="card-sub">Gateway cron status.</div>
<div class="card-title">${t("agents.cronPanel.schedulerTitle")}</div>
<div class="card-sub">${t("agents.cronPanel.schedulerSubtitle")}</div>
</div>
<button class="btn btn--sm" ?disabled=${params.loading} @click=${params.onRefresh}>
${params.loading ? t("common.refreshing") : t("common.refresh")}
@@ -352,11 +361,11 @@ export function renderAgentCron(params: {
</div>
</div>
<div class="stat">
<div class="stat-label">Jobs</div>
<div class="stat-label">${t("agents.cronPanel.jobs")}</div>
<div class="stat-value">${params.status?.jobs ?? t("common.na")}</div>
</div>
<div class="stat">
<div class="stat-label">Next wake</div>
<div class="stat-label">${t("agents.cronPanel.nextWake")}</div>
<div class="stat-value">${formatNextRun(params.status?.nextWakeAtMs ?? null)}</div>
</div>
</div>
@@ -366,10 +375,10 @@ export function renderAgentCron(params: {
</section>
</section>
<section class="card">
<div class="card-title">Agent Cron Jobs</div>
<div class="card-sub">Scheduled jobs targeting this agent.</div>
<div class="card-title">${t("agents.cronPanel.agentJobsTitle")}</div>
<div class="card-sub">${t("agents.cronPanel.agentJobsSubtitle")}</div>
${jobs.length === 0
? html` <div class="muted" style="margin-top: 16px">No jobs assigned.</div> `
? html` <div class="muted" style="margin-top: 16px">${t("agents.cronPanel.noJobs")}</div>`
: html`
<div class="list" style="margin-top: 16px;">
${jobs.map(
@@ -383,7 +392,7 @@ export function renderAgentCron(params: {
<div class="chip-row" style="margin-top: 6px;">
<span class="chip">${formatCronSchedule(job)}</span>
<span class="chip ${job.enabled ? "chip-ok" : "chip-warn"}">
${job.enabled ? "enabled" : "disabled"}
${job.enabled ? t("common.enabled") : t("common.disabled")}
</span>
<span class="chip">${job.sessionTarget}</span>
</div>
@@ -397,7 +406,7 @@ export function renderAgentCron(params: {
?disabled=${!job.enabled}
@click=${() => params.onRunNow(job.id)}
>
Run Now
${t("agents.cronPanel.runNow")}
</button>
</div>
</div>
@@ -444,27 +453,27 @@ export function renderAgentFiles(params: {
: "";
const previewTitleId = activeEntry ? `agent-file-preview-title-${toDomId(activeEntry.name)}` : "";
const previewStatusLabel = activeEntry?.missing
? "Will Create on Save"
? t("agents.files.willCreateOnSave")
: isDirty
? "Live Draft Preview"
: "Saved Preview";
? t("agents.files.liveDraftPreview")
: t("agents.files.savedPreview");
const previewStatusClass = activeEntry?.missing
? "is-missing"
: isDirty
? "is-dirty"
: "is-synced";
const previewUpdatedLabel = activeEntry?.updatedAtMs
? `Updated ${formatRelativeTimestamp(activeEntry.updatedAtMs)}`
? t("agents.files.updated", { time: formatRelativeTimestamp(activeEntry.updatedAtMs) })
: activeEntry?.missing
? "Not Created Yet"
: "Updated Unknown";
? t("agents.files.notCreatedYet")
: t("agents.files.updatedUnknown");
return html`
<section class="card">
<div class="row" style="justify-content: space-between;">
<div>
<div class="card-title">Core Files</div>
<div class="card-sub">Bootstrap persona, identity, and tool guidance.</div>
<div class="card-title">${t("agents.files.coreFilesTitle")}</div>
<div class="card-sub">${t("agents.files.coreFilesSubtitle")}</div>
</div>
<button
class="btn btn--sm"
@@ -476,7 +485,7 @@ export function renderAgentFiles(params: {
</div>
${list
? html`<div class="muted mono" style="margin-top: 8px;">
Workspace: <span>${list.workspace}</span>
${t("agents.files.workspace")}: <span>${list.workspace}</span>
</div>`
: nothing}
${params.agentFilesError
@@ -486,12 +495,10 @@ export function renderAgentFiles(params: {
: nothing}
${!list
? html`
<div class="callout info" style="margin-top: 12px">
Load the agent workspace files to edit core instructions.
</div>
<div class="callout info" style="margin-top: 12px">${t("agents.files.loadHint")}</div>
`
: files.length === 0
? html` <div class="muted" style="margin-top: 16px">No files found.</div> `
? html` <div class="muted" style="margin-top: 16px">${t("agents.files.empty")}</div> `
: html`
<div class="agent-tabs" style="margin-top: 14px;">
${files.map((file) => {
@@ -505,14 +512,16 @@ export function renderAgentFiles(params: {
@click=${() => params.onSelectFile(file.name)}
>
${label}${file.missing
? html` <span class="agent-tab-badge">missing</span> `
? html` <span class="agent-tab-badge">${t("agents.files.missing")}</span> `
: nothing}
</button>
`;
})}
</div>
${!activeEntry
? html` <div class="muted" style="margin-top: 16px">Select a file to edit.</div> `
? html` <div class="muted" style="margin-top: 16px">
${t("agents.files.selectFile")}
</div>`
: html`
<div class="agent-file-header" style="margin-top: 14px;">
<div>
@@ -521,7 +530,7 @@ export function renderAgentFiles(params: {
<div class="agent-file-actions">
<button
class="btn btn--sm"
title="Preview rendered markdown"
title=${t("agents.files.previewMarkdownTitle")}
@click=${(e: Event) => {
const btn = e.currentTarget as HTMLElement;
const dialog = btn.closest(".card")?.querySelector("dialog");
@@ -530,33 +539,33 @@ export function renderAgentFiles(params: {
}
}}
>
${icons.eye} Preview
${icons.eye} ${t("agents.files.preview")}
</button>
<button
class="btn btn--sm"
?disabled=${!isDirty}
@click=${() => params.onFileReset(activeEntry.name)}
>
Reset
${t("common.reset")}
</button>
<button
class="btn btn--sm primary"
?disabled=${params.agentFileSaving || !isDirty}
@click=${() => params.onFileSave(activeEntry.name)}
>
${params.agentFileSaving ? "Saving" : "Save"}
${params.agentFileSaving ? t("common.saving") : t("common.save")}
</button>
</div>
</div>
${activeEntry.missing
? html`
<div class="callout info" style="margin-top: 10px">
This file is missing. Saving will create it in the agent workspace.
${t("agents.files.missingHint")}
</div>
`
: nothing}
<label class="field agent-file-field" style="margin-top: 12px;">
<span>Content</span>
<span>${t("agents.files.content")}</span>
<textarea
class="agent-file-textarea"
.value=${draft}
@@ -611,8 +620,8 @@ export function renderAgentFiles(params: {
<button
type="button"
class="btn btn--sm md-preview-icon-btn md-preview-expand-btn"
title="Expand preview"
aria-label="Expand preview"
title=${t("agents.files.expandPreview")}
aria-label=${t("agents.files.expandPreview")}
aria-pressed="false"
@click=${(e: Event) => {
const btn = e.currentTarget as HTMLElement;
@@ -632,8 +641,8 @@ export function renderAgentFiles(params: {
<button
type="button"
class="btn btn--sm md-preview-icon-btn"
title="Edit file"
aria-label="Edit file"
title=${t("agents.files.editFile")}
aria-label=${t("agents.files.editFile")}
@click=${(e: Event) => {
(e.currentTarget as HTMLElement).closest("dialog")?.close();
const textarea =
@@ -646,8 +655,8 @@ export function renderAgentFiles(params: {
<button
type="button"
class="btn btn--sm md-preview-icon-btn"
title="Close preview"
aria-label="Close preview"
title=${t("agents.files.closePreview")}
aria-label=${t("agents.files.closePreview")}
@click=${(e: Event) => {
(e.currentTarget as HTMLElement).closest("dialog")?.close();
}}
@@ -662,11 +671,13 @@ export function renderAgentFiles(params: {
</div>
<div class="md-preview-dialog__chip">
<strong>${estimateReadingTimeLabel(draftWordCount)}</strong>
<span>${draftWordCount} words</span>
<span
>${t("agents.files.words", { count: String(draftWordCount) })}</span
>
</div>
<div class="md-preview-dialog__chip">
<strong>${draftLineCount}</strong>
<span>lines</span>
<span>${t("agents.files.lines")}</span>
</div>
<div class="md-preview-dialog__chip">
<strong>${draftByteSize}</strong>

View File

@@ -1,5 +1,7 @@
import { render } from "lit";
import { describe, expect, it, vi } from "vitest";
import { i18n } from "../../i18n/index.ts";
import { createStorageMock } from "../../test-helpers/storage.ts";
import { renderAgentFiles } from "./agents-panels-status-files.ts";
import { renderAgents, type AgentsProps } from "./agents.ts";
@@ -306,6 +308,40 @@ describe("renderAgents", () => {
expect(skillsTab?.textContent?.trim()).toContain("1");
});
it("keeps the Cron Jobs tab label while localizing channel refresh never state", async () => {
vi.stubGlobal("localStorage", createStorageMock());
await i18n.setLocale("zh-CN");
const container = document.createElement("div");
try {
render(
renderAgents(
createProps({
activePanel: "channels",
channels: {
snapshot: null,
loading: false,
error: null,
lastSuccess: null,
},
}),
),
container,
);
await Promise.resolve();
const tabLabels = Array.from(container.querySelectorAll<HTMLButtonElement>(".agent-tab")).map(
(button) => button.textContent?.trim(),
);
expect(tabLabels).toContain("Cron Jobs");
expect(container.textContent).toContain("上次刷新:从未");
} finally {
await i18n.setLocale("en");
vi.unstubAllGlobals();
}
});
});
describe("renderAgentFiles", () => {

View File

@@ -157,7 +157,7 @@ export function renderAgents(props: AgentsProps) {
@change=${(e: Event) => props.onSelectAgent((e.target as HTMLSelectElement).value)}
>
${agents.length === 0
? html` <option value="">No agents</option> `
? html` <option value="">${t("agents.noAgents")}</option> `
: agents.map(
(agent) => html`
<option value=${agent.id} ?selected=${agent.id === selectedId}>
@@ -176,9 +176,9 @@ export function renderAgents(props: AgentsProps) {
type="button"
class="btn btn--sm btn--ghost"
@click=${() => void navigator.clipboard.writeText(selectedAgent.id)}
title="Copy agent ID to clipboard"
title=${t("agents.copyIdTitle")}
>
Copy ID
${t("agents.copyId")}
</button>
<button
type="button"
@@ -186,10 +186,12 @@ export function renderAgents(props: AgentsProps) {
?disabled=${Boolean(defaultId && selectedAgent.id === defaultId)}
@click=${() => props.onSetDefault(selectedAgent.id)}
title=${defaultId && selectedAgent.id === defaultId
? "Already the default agent"
: "Set as the default agent"}
? t("agents.alreadyDefaultTitle")
: t("agents.setDefaultTitle")}
>
${defaultId && selectedAgent.id === defaultId ? "Default" : "Set Default"}
${defaultId && selectedAgent.id === defaultId
? t("agents.default")
: t("agents.setDefault")}
</button>
`
: nothing}
@@ -210,8 +212,8 @@ export function renderAgents(props: AgentsProps) {
${!selectedAgent
? html`
<div class="card">
<div class="card-title">Select an agent</div>
<div class="card-sub">Pick an agent to inspect its workspace and tools.</div>
<div class="card-title">${t("agents.selectTitle")}</div>
<div class="card-sub">${t("agents.selectSubtitle")}</div>
</div>
`
: html`
@@ -352,12 +354,12 @@ function renderAgentTabs(
counts: Record<string, number | null>,
) {
const tabs: Array<{ id: AgentsPanel; label: string }> = [
{ id: "overview", label: "Overview" },
{ id: "files", label: "Files" },
{ id: "tools", label: "Tools" },
{ id: "skills", label: "Skills" },
{ id: "channels", label: "Channels" },
{ id: "cron", label: "Cron Jobs" },
{ id: "overview", label: t("agents.tabs.overview") },
{ id: "files", label: t("agents.tabs.files") },
{ id: "tools", label: t("agents.tabs.tools") },
{ id: "skills", label: t("agents.tabs.skills") },
{ id: "channels", label: t("agents.tabs.channels") },
{ id: "cron", label: t("agents.tabs.cronJobs") },
];
return html`
<div class="agent-tabs">

View File

@@ -0,0 +1,64 @@
import { render } from "lit";
import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
import { i18n } from "../../i18n/index.ts";
import { createStorageMock } from "../../test-helpers/storage.ts";
import { renderDebug, type DebugProps } from "./debug.ts";
function createProps(overrides: Partial<DebugProps> = {}): DebugProps {
return {
loading: false,
status: null,
health: null,
models: [],
heartbeat: null,
eventLog: [],
methods: [],
callMethod: "",
callParams: "{}",
callResult: null,
callError: null,
onCallMethodChange: () => undefined,
onCallParamsChange: () => undefined,
onRefresh: () => undefined,
onCall: () => undefined,
...overrides,
};
}
describe("renderDebug", () => {
beforeEach(async () => {
vi.stubGlobal("localStorage", createStorageMock());
await i18n.setLocale("en");
});
afterEach(async () => {
await i18n.setLocale("en");
vi.unstubAllGlobals();
});
it("keeps the security audit command styled as monospace", async () => {
await i18n.setLocale("zh-CN");
const container = document.createElement("div");
render(
renderDebug(
createProps({
status: {
securityAudit: {
summary: {
critical: 0,
warn: 1,
info: 2,
},
},
},
}),
),
container,
);
const command = container.querySelector<HTMLElement>(".callout .mono");
expect(command?.textContent).toBe("openclaw security audit --deep");
expect(container.textContent).toContain("安全审计");
});
});

View File

@@ -32,15 +32,19 @@ export function renderDebug(props: DebugProps) {
const info = securitySummary?.info ?? 0;
const securityTone = critical > 0 ? "danger" : warn > 0 ? "warn" : "success";
const securityLabel =
critical > 0 ? `${critical} critical` : warn > 0 ? `${warn} warnings` : "No critical issues";
critical > 0
? t("debug.security.critical", { count: String(critical) })
: warn > 0
? t("debug.security.warnings", { count: String(warn) })
: t("debug.security.noCriticalIssues");
return html`
<section class="grid">
<div class="card">
<div class="row" style="justify-content: space-between;">
<div>
<div class="card-title">Snapshots</div>
<div class="card-sub">Status, health, and heartbeat data.</div>
<div class="card-title">${t("debug.snapshotsTitle")}</div>
<div class="card-sub">${t("debug.snapshotsSubtitle")}</div>
</div>
<button class="btn" ?disabled=${props.loading} @click=${props.onRefresh}>
${props.loading ? t("common.refreshing") : t("common.refresh")}
@@ -48,45 +52,50 @@ export function renderDebug(props: DebugProps) {
</div>
<div class="stack" style="margin-top: 12px;">
<div>
<div class="muted">Status</div>
<div class="muted">${t("debug.status")}</div>
${securitySummary
? html`<div class="callout ${securityTone}" style="margin-top: 8px;">
Security audit: ${securityLabel}${info > 0 ? ` · ${info} info` : ""}. Run
<span class="mono">openclaw security audit --deep</span> for details.
${t("debug.security.audit")}:
${securityLabel}${info > 0
? ` · ${t("debug.security.info", { count: String(info) })}`
: ""}.
${t("debug.security.runPrefix")}
<span class="mono">openclaw security audit --deep</span>
${t("debug.security.runSuffix")}
</div>`
: nothing}
<pre class="code-block">${JSON.stringify(props.status ?? {}, null, 2)}</pre>
</div>
<div>
<div class="muted">Health</div>
<div class="muted">${t("debug.health")}</div>
<pre class="code-block">${JSON.stringify(props.health ?? {}, null, 2)}</pre>
</div>
<div>
<div class="muted">Last heartbeat</div>
<div class="muted">${t("debug.lastHeartbeat")}</div>
<pre class="code-block">${JSON.stringify(props.heartbeat ?? {}, null, 2)}</pre>
</div>
</div>
</div>
<div class="card">
<div class="card-title">Manual RPC</div>
<div class="card-sub">Send a raw gateway method with JSON params.</div>
<div class="card-title">${t("debug.manualRpcTitle")}</div>
<div class="card-sub">${t("debug.manualRpcSubtitle")}</div>
<div class="stack" style="margin-top: 16px;">
<label class="field">
<span>Method</span>
<span>${t("debug.method")}</span>
<select
.value=${props.callMethod}
@change=${(e: Event) =>
props.onCallMethodChange((e.target as HTMLSelectElement).value)}
>
${!props.callMethod
? html` <option value="" disabled>Select a method</option> `
? html` <option value="" disabled>${t("debug.selectMethod")}</option> `
: nothing}
${props.methods.map((m) => html`<option value=${m}>${m}</option>`)}
</select>
</label>
<label class="field">
<span>Params (JSON)</span>
<span>${t("debug.paramsJson")}</span>
<textarea
.value=${props.callParams}
@input=${(e: Event) =>
@@ -108,18 +117,18 @@ export function renderDebug(props: DebugProps) {
</section>
<section class="card" style="margin-top: 18px;">
<div class="card-title">Models</div>
<div class="card-sub">Catalog from models.list.</div>
<div class="card-title">${t("debug.modelsTitle")}</div>
<div class="card-sub">${t("debug.modelsSubtitle")}</div>
<pre class="code-block" style="margin-top: 12px;">
${JSON.stringify(props.models ?? [], null, 2)}</pre
>
</section>
<section class="card" style="margin-top: 18px;">
<div class="card-title">Event Log</div>
<div class="card-sub">Latest gateway events.</div>
<div class="card-title">${t("debug.eventLogTitle")}</div>
<div class="card-sub">${t("debug.eventLogSubtitle")}</div>
${props.eventLog.length === 0
? html` <div class="muted" style="margin-top: 12px">No events yet.</div> `
? html` <div class="muted" style="margin-top: 12px">${t("debug.noEvents")}</div> `
: html`
<div class="list debug-event-log" style="margin-top: 12px;">
${props.eventLog.map(

View File

@@ -2,6 +2,8 @@
import { nothing, render } from "lit";
import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
import { i18n } from "../../i18n/index.ts";
import { createStorageMock } from "../../test-helpers/storage.ts";
import type { AppViewState } from "../app-view-state.ts";
import { type OpenClawModalDialog } from "../components/modal-dialog.ts";
import type { ExecApprovalRequest } from "../controllers/exec-approval.ts";
@@ -101,17 +103,22 @@ function createExecState(
}
describe("approval and confirmation modals", () => {
beforeEach(() => {
beforeEach(async () => {
installDialogPolyfill();
vi.stubGlobal("localStorage", createStorageMock());
await i18n.setLocale("en");
container = document.createElement("div");
document.body.append(container);
});
afterEach(() => {
afterEach(async () => {
render(nothing, container);
container.remove();
await i18n.setLocale("en");
restoreDescriptor("showModal", showModalDescriptor);
restoreDescriptor("close", closeDescriptor);
vi.useRealTimers();
vi.unstubAllGlobals();
vi.restoreAllMocks();
});
@@ -160,6 +167,48 @@ describe("approval and confirmation modals", () => {
expect(handleExecApprovalDecision).not.toHaveBeenCalled();
});
it("renders exec approval chrome from the active locale", async () => {
vi.useFakeTimers();
vi.setSystemTime(new Date("2026-04-29T00:00:00.000Z"));
await i18n.setLocale("zh-CN");
const active: ExecApprovalRequest = {
id: "approval-1",
kind: "exec",
request: {
command: "pnpm check:changed",
host: "gateway",
agentId: "main",
sessionKey: "main",
cwd: "/tmp/project",
resolvedPath: "/tmp/project",
security: "workspace-write",
ask: "on-request",
},
createdAtMs: Date.now(),
expiresAtMs: Date.now() + 61_000,
};
const queued: ExecApprovalRequest = {
...active,
id: "approval-2",
createdAtMs: Date.now() + 1,
expiresAtMs: Date.now() + 62_000,
};
render(
renderExecApprovalPrompt(createExecState({ execApprovalQueue: [active, queued] })),
container,
);
expect(container.textContent).toContain("需要 Exec 审批");
expect(container.textContent).toContain("1m 后过期");
expect(container.textContent).toContain("2 个待处理");
expect(container.textContent).toContain("主机");
expect(container.textContent).toContain("代理");
expect(container.textContent).toContain("允许一次");
expect(container.textContent).toContain("始终允许");
expect(container.textContent).toContain("拒绝");
});
it("uses the shared modal primitive for gateway URL confirmation and cancels on Escape", async () => {
const handleGatewayUrlCancel = vi.fn();
render(

View File

@@ -1,5 +1,6 @@
import { html, nothing } from "lit";
import { formatApprovalDisplayPath } from "../../../../src/infra/approval-display-paths.ts";
import { t } from "../../i18n/index.ts";
import type { AppViewState } from "../app-view-state.ts";
import "../components/modal-dialog.ts";
import type {
@@ -35,13 +36,15 @@ function renderExecBody(request: ExecApprovalRequestPayload) {
return html`
<div class="exec-approval-command mono">${request.command}</div>
<div class="exec-approval-meta">
${renderMetaRow("Host", request.host)} ${renderMetaRow("Agent", request.agentId)}
${renderMetaRow("Session", request.sessionKey)}
${renderMetaRow("CWD", request.cwd, {
${renderMetaRow(t("execApproval.labels.host"), request.host)}
${renderMetaRow(t("execApproval.labels.agent"), request.agentId)}
${renderMetaRow(t("execApproval.labels.session"), request.sessionKey)}
${renderMetaRow(t("execApproval.labels.cwd"), request.cwd, {
path: true,
})}
${renderMetaRow("Resolved", request.resolvedPath, { path: true })}
${renderMetaRow("Security", request.security)} ${renderMetaRow("Ask", request.ask)}
${renderMetaRow(t("execApproval.labels.resolved"), request.resolvedPath, { path: true })}
${renderMetaRow(t("execApproval.labels.security"), request.security)}
${renderMetaRow(t("execApproval.labels.ask"), request.ask)}
</div>
`;
}
@@ -54,9 +57,10 @@ ${active.pluginDescription}</pre
>`
: nothing}
<div class="exec-approval-meta">
${renderMetaRow("Severity", active.pluginSeverity)}
${renderMetaRow("Plugin", active.pluginId)} ${renderMetaRow("Agent", active.request.agentId)}
${renderMetaRow("Session", active.request.sessionKey)}
${renderMetaRow(t("execApproval.labels.severity"), active.pluginSeverity)}
${renderMetaRow(t("execApproval.labels.plugin"), active.pluginId)}
${renderMetaRow(t("execApproval.labels.agent"), active.request.agentId)}
${renderMetaRow(t("execApproval.labels.session"), active.request.sessionKey)}
</div>
`;
}
@@ -68,12 +72,15 @@ export function renderExecApprovalPrompt(state: AppViewState) {
}
const request = active.request;
const remainingMs = active.expiresAtMs - Date.now();
const remaining = remainingMs > 0 ? `expires in ${formatRemaining(remainingMs)}` : "expired";
const remaining =
remainingMs > 0
? t("execApproval.expiresIn", { time: formatRemaining(remainingMs) })
: t("execApproval.expired");
const queueCount = state.execApprovalQueue.length;
const isPlugin = active.kind === "plugin";
const title = isPlugin
? (active.pluginTitle ?? "Plugin approval needed")
: "Exec approval needed";
? (active.pluginTitle ?? t("execApproval.pluginApprovalNeeded"))
: t("execApproval.execApprovalNeeded");
const titleId = "exec-approval-title";
const descriptionId = "exec-approval-description";
const handleCancel = () => {
@@ -90,7 +97,9 @@ export function renderExecApprovalPrompt(state: AppViewState) {
<div id=${descriptionId} class="exec-approval-sub">${remaining}</div>
</div>
${queueCount > 1
? html`<div class="exec-approval-queue">${queueCount} pending</div>`
? html`<div class="exec-approval-queue">
${t("execApproval.pending", { count: String(queueCount) })}
</div>`
: nothing}
</div>
${isPlugin ? renderPluginBody(active) : renderExecBody(request)}
@@ -103,21 +112,21 @@ export function renderExecApprovalPrompt(state: AppViewState) {
?disabled=${state.execApprovalBusy}
@click=${() => state.handleExecApprovalDecision("allow-once")}
>
Allow once
${t("execApproval.allowOnce")}
</button>
<button
class="btn"
?disabled=${state.execApprovalBusy}
@click=${() => state.handleExecApprovalDecision("allow-always")}
>
Always allow
${t("execApproval.alwaysAllow")}
</button>
<button
class="btn danger"
?disabled=${state.execApprovalBusy}
@click=${() => state.handleExecApprovalDecision("deny")}
>
Deny
${t("execApproval.deny")}
</button>
</div>
</div>