diff --git a/ROADMAP.md b/ROADMAP.md index e27b4a9..11b6f92 100644 --- a/ROADMAP.md +++ b/ROADMAP.md @@ -517,6 +517,7 @@ services/api.ts (1324L) | U23 | Task 模块 i18n 治理(CronJobManager + CronJobFormDialog + ScriptManager + RemoteExecPage 4 文件 — `import i18n` 全局调用 → `useTranslation()` hook;42 处 phantom key (`i18n.t('Chinese text')` → 语义化 `task.cronJob.*`/`task.scriptList.*`/`task.remoteExec.*` 键);28 个孤儿 hash 键清理 (cronjobformdial.s*/remoteexecpaget.s*/systemtaskspanel.s*);50+ 处硬编码 JSX 中文 → t() 调用;zh/en 6825→6886 +61 键对齐,tsc -b=0,npm build✓ (17.46s),ESLint=0/45/0,go build=0,17/17 测试通过) | P3 | **done** | | U24 | Monitor 模块 i18n hook 迁移(26 个 .tsx 文件从 `import i18n` 全局 → `useTranslation()` hook + 89 个 phantom 中文文本键 → `monitor.lbl.*` 语义化键;299 处 `i18n.t()` 调用 → 74 处保留(模块级/.ts 工具文件) + 225 处迁移到 `t()` hook;1 个 .ts 工具文件 helpers.ts 中文文本键替换为语义化键;zh/en 6886→6975 +89 键对齐,tsc -b=0,npm build✓ (17.16s),ESLint=0/53/0,go build=0,Docker healthy) | P3 | **done** | | U26 | Kubernetes 模块 phantom key 大规模清理(32 个 .tsx/.ts 文件,171 个中文 phantom key → 8 个残留(均为 ANSI 转义码/JSX 表达式误匹配),163 个成功替换为 k8s.* 语义化键;新增 19 个子命名空间(nsResource/nsOverview/deploymentWorkload/deploymentView/workloadView/controlBar/clusterOverview/nodes/podLogs/podExec/pvc/configMap/secret/service/ingress/nsMgmt/editContainers/capacityPage/podFile)+ 扩展 8 个已有子命名空间;zh/en 6990→7185 +195 键对齐,k8s 命名空间 65 子命名空间/940 键,tsc -b=0,npm build✓ (17.59s),ESLint=0/53/0,go build=0,17/17 测试通过) | P3 | **done** | +| U27 | 多模块 phantom key 批量清理(Cloud/Deploy/Agent/Monitor/System 5 模块 25 个文件,180 个中文 phantom key → 51 个残留,129 个成功替换为语义化键;新增 12 个子命名空间(cloud.platform/deploy.buildNodes/deploy.rbac.policy/deploy.stage/deploy.target/deploy.userGroup/agent.alerts/agent.monitor/agent.alertHelper/agent.ruleDialog/monitor.alertRulesTab/system.ldapMgmt 等);硬编码 JSX 中文(刷新/添加/启用/禁用/Master内置/执行器/标签等) → i18n.t() 调用;zh/en 7185→7294 +109 键对齐,tsc -b=0,npm build✓ (16.31s),ESLint=0/0/0,go build=0,17/17 测试通过) | P3 | **done** | --- diff --git a/frontend/src/components/agent/AgentAlerts.tsx b/frontend/src/components/agent/AgentAlerts.tsx index 0538a4e..728fa0c 100644 --- a/frontend/src/components/agent/AgentAlerts.tsx +++ b/frontend/src/components/agent/AgentAlerts.tsx @@ -53,7 +53,7 @@ export function AgentAlerts() { setRules(asList(rulesRes)); } catch (err) { console.error(err); - toast.error(i18n.t('加载告警数据失败')); + toast.error(i18n.t('agent.alerts.loadFailed')); } finally { setLoading(false); } @@ -65,11 +65,11 @@ export function AgentAlerts() { // ============ 告警事件 ============ const handleResolve = async (id: number) => { - const ok = await confirm({ title: i18n.t('恢复告警'), description: i18n.t('确定将此告警标记为已恢复?'), confirmText: i18n.t('kubernetes.deployment.resume') }); + const ok = await confirm({ title: i18n.t('agent.alerts.resolveAlert'), description: i18n.t('agent.alerts.resolveConfirm'), confirmText: i18n.t('kubernetes.deployment.resume') }); if (!ok) return; try { await agentApi.resolveAlert(id); - toast.success(i18n.t('告警已恢复')); + toast.success(i18n.t('agent.alerts.resolved')); loadData(); } catch (err) { toast.error(err?.message || i18n.t('cloud.operationFailed')); @@ -88,11 +88,11 @@ export function AgentAlerts() { }; const handleDeleteRule = async (id: number) => { - const ok = await confirm({ title: i18n.t('monitor.deleteRule'), description: i18n.t('删除规则'), confirmText: i18n.t('kubernetes.storage.delete2'), variant: 'destructive' }); + const ok = await confirm({ title: i18n.t('monitor.deleteRule'), description: i18n.t('agent.alerts.deleteRule'), confirmText: i18n.t('kubernetes.storage.delete2'), variant: 'destructive' }); if (!ok) return; try { await agentApi.deleteRule(id); - toast.success(i18n.t('告警已恢复')); + toast.success(i18n.t('agent.alerts.resolved')); loadData(); } catch (err) { toast.error(err?.message || i18n.t('kubernetes.msg.deleteFailed2')); @@ -114,7 +114,7 @@ export function AgentAlerts() {

Agent 告警

-

{i18n.t('触发告警阈值')}

+

{i18n.t('agent.alerts.thresholdTriggered')}

-

{alert.message || alert.description || i18n.t('触发告警阈值')}

+

{alert.message || alert.description || i18n.t('agent.alerts.thresholdTriggered')}

diff --git a/frontend/src/components/agent/AgentMonitor.tsx b/frontend/src/components/agent/AgentMonitor.tsx index 59e9de8..e6d843e 100644 --- a/frontend/src/components/agent/AgentMonitor.tsx +++ b/frontend/src/components/agent/AgentMonitor.tsx @@ -71,7 +71,7 @@ export function AgentMonitor() { if (fresh) setSelectedHost(fresh); } } catch (err) { - if (!silent) toast.error(i18n.t('加载主机列表失败')); + if (!silent) toast.error(i18n.t('agent.monitor.loadHostFailed')); console.error(err); } finally { setLoading(false); @@ -100,7 +100,7 @@ export function AgentMonitor() { // 提交远程命令(直连 SSH 即时返回) const submitCommand = async () => { if (!cmdCommand.trim()) { - toast.error(i18n.t('请输入要执行的命令')); + toast.error(i18n.t('agent.monitor.enterCommand')); return; } setCmdSubmitting(true); @@ -114,7 +114,7 @@ export function AgentMonitor() { const resData = (res?.data ?? {}) as Record; setCmdResult({ status: res?.code === 200 ? 'completed' : 'failed', - result: (resData.output as string) || (res?.message as string) || i18n.t('无输出'), + result: (resData.output as string) || (res?.message as string) || i18n.t('agent.monitor.noOutput'), error: resData.error as string | undefined, }); } catch (err) { @@ -154,7 +154,7 @@ export function AgentMonitor() { className="dg-input text-[var(--dg-text-secondary)] hover:bg-[var(--dg-bg-hover)] hover:text-[var(--dg-text-primary)]" > - {t('例如:free -m && df -h')} + {t('agent.monitor.commandPlaceholder')}
@@ -325,7 +325,7 @@ export function AgentMonitor() {