feat(i18n): 安全批量转换 135 文件 — 覆盖率 34%→62%
使用 i18n.t() 全局方式(避免 hook 定位问题): - 288 目标文件中 135 个成功转换 - 2228 处中文替换为 i18n.t() 调用 - 1006 个新翻译 key 添加到 zh-CN.json + en-US.json - 词典总量: 3554 keys (22 namespaces) - tsc 零错误 + Vite 构建成功 - 6 个含代码示例/数据字符串的文件安全回退
This commit is contained in:
1 parent
72bfb0e12d
commit
55f216cfbb
131 files changed
+4049
-1908
No files matched your search
@@ -40,6 +40,7 @@ import { CREATE_DEPLOYMENT_SLUG, isCreateDeployment } from './deployment-constan
|
||||
import { extractContainers } from './deployment-detail/helpers';
|
||||
import { PageShell } from '@/components/layout/PageShell';
|
||||
import type { ActionModal, DeploymentWorkloadProps } from './deployment-workload/types';
|
||||
import i18n from '@/i18n';
|
||||
|
||||
export type { DeploymentWorkloadProps, WorkloadMode } from './deployment-workload/types';
|
||||
|
||||
@@ -117,7 +118,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
|
||||
setRevisions(toArray(revRes));
|
||||
} catch (e) {
|
||||
console.error('加载详情失败:', e);
|
||||
console.error(i18n.t('kubernetes.deploymentdetai.sb46ea9c4'), e);
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
@@ -132,7 +133,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
const { manifest: parsed } = await parseEditableManifest(yamlText);
|
||||
setManifest(parsed || deployment);
|
||||
} catch (e) {
|
||||
console.warn('加载 manifest 失败(编辑功能降级):', e);
|
||||
console.warn(i18n.t('kubernetes.deploymentworkl.sce123fbd'), e);
|
||||
setManifest(deployment);
|
||||
}
|
||||
}, [clusterCode, namespace, deploymentName, deployment]);
|
||||
@@ -160,10 +161,10 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
setActionLoading('scale');
|
||||
try {
|
||||
await kubernetesApi.scaleDeployment(clusterCode, namespace, deploymentName, newReplicas);
|
||||
toast({ title: '扩缩容成功', description: `副本数已设置为 ${newReplicas}` });
|
||||
toast({ title: i18n.t('k8s.workloads.scaleSuccess'), description: `副本数已设置为 ${newReplicas}` });
|
||||
loadData();
|
||||
} catch (e) {
|
||||
toast({ title: '操作失败', description: e?.message || String(e), variant: 'destructive' });
|
||||
toast({ title: i18n.t('cloud.operationFailed'), description: e?.message || String(e), variant: 'destructive' });
|
||||
} finally { setActionLoading(''); }
|
||||
};
|
||||
|
||||
@@ -171,34 +172,34 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
setActionLoading('scale');
|
||||
try {
|
||||
await kubernetesApi.scaleDeployment(clusterCode, namespace, deploymentName, scaleValue);
|
||||
toast({ title: '伸缩成功', description: `副本数已设置为 ${scaleValue}` });
|
||||
toast({ title: i18n.t('kubernetes.msg.scaleSuccess'), description: `副本数已设置为 ${scaleValue}` });
|
||||
setModal(null);
|
||||
loadData();
|
||||
} catch (e) {
|
||||
toast({ title: '操作失败', description: e?.message || String(e), variant: 'destructive' });
|
||||
toast({ title: i18n.t('cloud.operationFailed'), description: e?.message || String(e), variant: 'destructive' });
|
||||
} finally { setActionLoading(''); }
|
||||
};
|
||||
|
||||
const handleRestart = async () => {
|
||||
const ok = await confirm({
|
||||
title: '滚动重启',
|
||||
title: i18n.t('kubernetes.deployment.restart'),
|
||||
description: `确认滚动重启 Deployment "${deploymentName}"?`,
|
||||
confirmText: '重启',
|
||||
confirmText: i18n.t('agent.agentServiceRestart'),
|
||||
});
|
||||
if (!ok) return;
|
||||
setActionLoading('restart');
|
||||
try {
|
||||
await kubernetesApi.restartDeployment(clusterCode, namespace, deploymentName);
|
||||
toast({ title: '重启指令已下发', description: 'Deployment 正在滚动重启' });
|
||||
toast({ title: i18n.t('kubernetes.deploymentdetai.s68a70009'), description: i18n.t('kubernetes.deploymentdetai.sd187617a') });
|
||||
setTimeout(loadData, 1500);
|
||||
} catch (e) {
|
||||
toast({ title: '重启失败', description: e?.message || String(e), variant: 'destructive' });
|
||||
toast({ title: i18n.t('kubernetes.deployment.restartFailed'), description: e?.message || String(e), variant: 'destructive' });
|
||||
} finally { setActionLoading(''); }
|
||||
};
|
||||
|
||||
const handleTogglePause = async () => {
|
||||
const isPaused = !!deployment?.paused;
|
||||
const action = isPaused ? '恢复' : '暂停';
|
||||
const action = isPaused ? i18n.t('kubernetes.deployment.resume') : i18n.t('kubernetes.job.suspend');
|
||||
const ok = await confirm({
|
||||
title: `${action}滚动更新`,
|
||||
description: `确认${action} Deployment "${deploymentName}" 的滚动更新?`,
|
||||
@@ -232,11 +233,11 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
await kubernetesApi.updateDeploymentImage(
|
||||
clusterCode, namespace, deploymentName, newImage, cicdContainerName || undefined,
|
||||
);
|
||||
toast({ title: '镜像更新成功', description: `正在滚动更新为 ${newImage}` });
|
||||
toast({ title: i18n.t('kubernetes.deploymentdetai.s6df3c303'), description: `正在滚动更新为 ${newImage}` });
|
||||
setModal(null);
|
||||
loadData();
|
||||
} catch (e) {
|
||||
toast({ title: '更新失败', description: e?.message || String(e), variant: 'destructive' });
|
||||
toast({ title: i18n.t('kubernetes.deployment.imageUpdateFailed'), description: e?.message || String(e), variant: 'destructive' });
|
||||
} finally { setActionLoading(''); }
|
||||
};
|
||||
|
||||
@@ -249,11 +250,11 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
const url = `${baseUrl}/api/v1/kubernetes/${clusterCode}/namespace/${namespace}/deployments/${deploymentName}`;
|
||||
const resp = await fetch(url, { method: 'DELETE', headers: { Authorization: `Bearer ${tk}` } });
|
||||
if (!resp.ok) throw new Error(`HTTP ${resp.status}`);
|
||||
toast({ title: '删除成功', description: `${deploymentName} 已删除` });
|
||||
toast({ title: i18n.t('kubernetes.msg.deleteSuccess'), description: `${deploymentName} 已删除` });
|
||||
setModal(null);
|
||||
setTimeout(() => navigate(`/kubernetes/${clusterCode}/namespace/${namespace}/deployments`), 800);
|
||||
} catch (e) {
|
||||
toast({ title: '删除失败', description: e?.message || String(e), variant: 'destructive' });
|
||||
toast({ title: i18n.t('kubernetes.msg.deleteFailed2'), description: e?.message || String(e), variant: 'destructive' });
|
||||
} finally { setActionLoading(''); }
|
||||
};
|
||||
|
||||
@@ -269,24 +270,24 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
|
||||
const handleDeletePod = async (pod: any) => {
|
||||
const ok = await confirm({
|
||||
title: '删除 Pod',
|
||||
title: i18n.t('kubernetes.pod.deletePod'),
|
||||
description: `确认删除 Pod "${pod.name}"?操作不可恢复。`,
|
||||
confirmText: '删除',
|
||||
confirmText: i18n.t('kubernetes.storage.delete2'),
|
||||
});
|
||||
if (!ok) return;
|
||||
try {
|
||||
await kubernetesApi.deletePod(clusterCode, namespace, pod.name);
|
||||
toast({ title: 'Pod 已删除' });
|
||||
toast({ title: i18n.t('kubernetes.msg.podDeleted') });
|
||||
loadData();
|
||||
} catch (e) {
|
||||
toast({ title: '删除失败', description: (e as any)?.message || String(e), variant: 'destructive' });
|
||||
toast({ title: i18n.t('kubernetes.msg.deleteFailed2'), description: (e as any)?.message || String(e), variant: 'destructive' });
|
||||
}
|
||||
};
|
||||
|
||||
// ============ 渲染 // Logan.Li ============
|
||||
if (loading) {
|
||||
return (
|
||||
<PageShell variant="workspace" title={deploymentName} subtitle={`${clusterCode} / ${namespace}`} loading loadingLabel="加载 Deployment..." actions={<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" />返回</Button>}>
|
||||
<PageShell variant="workspace" title={deploymentName} subtitle={`${clusterCode} / ${namespace}`} loading loadingLabel={i18n.t('kubernetes.deploymentworkl.seb300b29')} actions={<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" /> {i18n.t('common.back')} </Button>}>
|
||||
{null}
|
||||
</PageShell>
|
||||
);
|
||||
@@ -294,7 +295,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
|
||||
if (!deployment && !isCreate) {
|
||||
return (
|
||||
<PageShell variant="default" title={deploymentName} subtitle={`${clusterCode} / ${namespace}`} actions={<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" />返回</Button>}>
|
||||
<PageShell variant="default" title={deploymentName} subtitle={`${clusterCode} / ${namespace}`} actions={<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" /> {i18n.t('common.back')} </Button>}>
|
||||
<Card className="dg-card"><CardContent className="p-12 text-center"><XCircle className="h-8 w-8 mx-auto dg-text-red" /><p className="dg-text-secondary mt-3">未找到 Deployment: {deploymentName}</p></CardContent></Card>
|
||||
</PageShell>
|
||||
);
|
||||
@@ -306,7 +307,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
if (name) navigate(`/kubernetes/${clusterCode}/namespace/${namespace}/workload/view/Deployment/${name}`);
|
||||
};
|
||||
return (
|
||||
<PageShell variant="workspace" title="新建 Deployment" subtitle={`${clusterCode} / ${namespace}`} actions={<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" />返回</Button>}>
|
||||
<PageShell variant="workspace" title={i18n.t('kubernetes.deploymentworkl.se2c85a21')} subtitle={`${clusterCode} / ${namespace}`} actions={<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" /> {i18n.t('common.back')} </Button>}>
|
||||
<EditModeContainer clusterCode={clusterCode} namespace={namespace} deploymentName={CREATE_DEPLOYMENT_SLUG} manifest={manifest} isCreate onSaved={handleCreated} onCancel={onBack} />
|
||||
</PageShell>
|
||||
);
|
||||
@@ -318,8 +319,8 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
|
||||
const modeTabs = (
|
||||
<div className="inline-flex rounded-md border border-[var(--dg-border)] overflow-hidden">
|
||||
<button className={`px-3 py-1.5 text-xs font-medium transition-colors ${mode === 'view' ? 'bg-[var(--dg-bg-active)] text-[var(--dg-text-primary)]' : 'bg-transparent dg-text-secondary hover:text-[var(--dg-text-primary)]'}`} onClick={() => onModeChange('view')}>查看</button>
|
||||
<button className={`px-3 py-1.5 text-xs font-medium transition-colors ${mode === 'edit' ? 'bg-blue-600 text-white' : 'bg-transparent dg-text-secondary hover:text-[var(--dg-text-primary)]'}`} onClick={() => onModeChange('edit')}>编辑</button>
|
||||
<button className={`px-3 py-1.5 text-xs font-medium transition-colors ${mode === 'view' ? 'bg-[var(--dg-bg-active)] text-[var(--dg-text-primary)]' : 'bg-transparent dg-text-secondary hover:text-[var(--dg-text-primary)]'}`} onClick={() => onModeChange('view')}> {i18n.t('common.view')} </button>
|
||||
<button className={`px-3 py-1.5 text-xs font-medium transition-colors ${mode === 'edit' ? 'bg-blue-600 text-white' : 'bg-transparent dg-text-secondary hover:text-[var(--dg-text-primary)]'}`} onClick={() => onModeChange('edit')}> {i18n.t('common.edit')} </button>
|
||||
<button className={`px-3 py-1.5 text-xs font-medium transition-colors ${mode === 'yaml' ? 'bg-emerald-600 text-white' : 'bg-transparent dg-text-secondary hover:text-[var(--dg-text-primary)]'}`} onClick={() => onModeChange('yaml')}>YAML</button>
|
||||
</div>
|
||||
);
|
||||
@@ -331,16 +332,16 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
subtitle={`${clusterCode} / ${namespace} · Deployment · 镜像: ${deployment?.image || '-'}`}
|
||||
actions={(
|
||||
<>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" />返回</Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={onBack}><ArrowLeft className="h-4 w-4 mr-1" /> {i18n.t('common.back')} </Button>
|
||||
{modeTabs}
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={loadData}><RefreshCw className="h-4 w-4" /></Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={() => { setNewImage(deployment?.image || ''); setModal({ kind: 'image' }); }}><ImageIcon className="h-3.5 w-3.5 mr-1" />调整镜像</Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={handleRestart}><RotateCw className="h-3.5 w-3.5 mr-1" />重启</Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={() => { setNewImage(deployment?.image || ''); setModal({ kind: 'image' }); }}><ImageIcon className="h-3.5 w-3.5 mr-1" /> {i18n.t('kubernetes.deploymentworkl.sf2e0208b')} </Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={handleRestart}><RotateCw className="h-3.5 w-3.5 mr-1" /> {i18n.t('agent.agentServiceRestart')} </Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" disabled={!!actionLoading} onClick={handleTogglePause}>
|
||||
{deployment?.paused ? <><Play className="h-3.5 w-3.5 mr-1 dg-text-green" />恢复</> : <><Pause className="h-3.5 w-3.5 mr-1 dg-text-orange" />暂停</>}
|
||||
{deployment?.paused ? <><Play className="h-3.5 w-3.5 mr-1 dg-text-green" /> {i18n.t('kubernetes.deployment.resume')} </> : <><Pause className="h-3.5 w-3.5 mr-1 dg-text-orange" /> {i18n.t('kubernetes.job.suspend')} </>}
|
||||
</Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-secondary" onClick={handleCICD}><Rocket className="h-3.5 w-3.5 mr-1 dg-text-purple" />CI/CD</Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-danger" onClick={() => setModal({ kind: 'delete' })}><Trash2 className="h-3.5 w-3.5 mr-1" />删除</Button>
|
||||
<Button variant="outline" size="sm" className="dg-btn-danger" onClick={() => setModal({ kind: 'delete' })}><Trash2 className="h-3.5 w-3.5 mr-1" /> {i18n.t('kubernetes.storage.delete2')} </Button>
|
||||
</>
|
||||
)}
|
||||
>
|
||||
@@ -350,7 +351,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
<Badge className={isHealthy ? 'bg-emerald-500/20 dg-text-green border-emerald-500/30' : 'bg-amber-500/20 dg-text-yellow border-amber-500/30'}>
|
||||
{isHealthy ? <CheckCircle className="h-3 w-3 mr-1" /> : <AlertTriangle className="h-3 w-3 mr-1" />}{ready}/{total}
|
||||
</Badge>
|
||||
{deployment?.paused && <Badge className="bg-orange-500/20 dg-text-orange border-orange-500/30"><Pause className="h-3 w-3 mr-1" />已暂停更新</Badge>}
|
||||
{deployment?.paused && <Badge className="bg-orange-500/20 dg-text-orange border-orange-500/30"><Pause className="h-3 w-3 mr-1" /> {i18n.t('kubernetes.deploymentworkl.s8be2521d')} </Badge>}
|
||||
</div>
|
||||
|
||||
{/* ============ 主体:view / edit / yaml ============ */}
|
||||
@@ -377,7 +378,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
resource="deployments"
|
||||
name={deploymentName}
|
||||
inline
|
||||
resourceHint="含关联 Service"
|
||||
resourceHint={i18n.t('kubernetes.deploymentworkl.s239604b0')}
|
||||
loadYamlFn={loadBundleYaml}
|
||||
saveYamlFn={saveBundleYaml}
|
||||
onSaved={loadData}
|
||||
@@ -402,7 +403,7 @@ export function DeploymentWorkload({ clusterCode, namespace, deploymentName, mod
|
||||
namespace={namespace}
|
||||
resource="deployments"
|
||||
name={deploymentName}
|
||||
resourceHint="含关联 Service"
|
||||
resourceHint={i18n.t('kubernetes.deploymentworkl.s239604b0')}
|
||||
loadYamlFn={loadBundleYaml}
|
||||
saveYamlFn={saveBundleYaml}
|
||||
onClose={() => setModal(null)}
|
||||
|
||||
Reference in new issue
Block a user