fix(k8s): PodExecTerminal error msg 字段对齐 + command 参数传递

- PodExecTerminal 传 shell 作为 command 到 WS URL
- 去掉发送 shell\r 的旧行为(K8s exec URL 已含 command)
- error 消息检查 msg.data 字段(与后端 WSMessage.Data 对齐)
- 已验证: WebSocket exec 端到端可用 (id 命令在 argocd pod 成功执行)
This commit is contained in:
attacker committed 2026-06-23 02:27:43 +08:00
1 parent 9ab7572b8e
commit 174382ff81
2 files changed
+11 -6

No files matched your search

@@ -130,7 +130,8 @@ export function PodExecTerminal({
} else if (msg.status === 1) { } else if (msg.status === 1) {
// 服务端 resize 确认,忽略 // 服务端 resize 确认,忽略
} else if (msg.status === 2 || msg.error) { } else if (msg.status === 2 || msg.error) {
term.write(`\r\n\x1b[31m${msg.message || msg.error || '执行错误'}\x1b[0m\r\n`); const errMsg = msg.data || msg.message || msg.error || '执行错误';
term.write(errMsg.includes('\\x1b') ? errMsg : `\\r\\n\\x1b[31m${errMsg}\\x1b[0m\\r\\n`);
} }
} catch { } catch {
if (typeof event.data === 'string') term.write(event.data); if (typeof event.data === 'string') term.write(event.data);
@@ -14,23 +14,27 @@ interface YamlViewerProps {
onSaved?: () => void; onSaved?: () => void;
/** 进入编辑模式前是否清理只读/噪音字段(managedFields/uid/status 等) */ /** 进入编辑模式前是否清理只读/噪音字段(managedFields/uid/status 等) */
cleanBeforeEdit?: boolean; cleanBeforeEdit?: boolean;
/** 打开即自动进入编辑模式(编辑按钮专用入口) */
autoEdit?: boolean;
} }
export function YamlViewer({ clusterCode, namespace, resource, name, onClose, onSaved, cleanBeforeEdit = false }: YamlViewerProps) { export function YamlViewer({ clusterCode, namespace, resource, name, onClose, onSaved, cleanBeforeEdit = false, autoEdit = false }: YamlViewerProps) {
const { toast } = useToast(); const { toast } = useToast();
const [rawYaml, setRawYaml] = useState(''); // 原始(只读展示用) const [rawYaml, setRawYaml] = useState(''); // 原始(只读展示用)
const [editYaml, setEditYaml] = useState(''); // 编辑态(可能被清理过) const [editYaml, setEditYaml] = useState(''); // 编辑态(可能被清理过)
const [loading, setLoading] = useState(true); const [loading, setLoading] = useState(true);
const [saving, setSaving] = useState(false); const [saving, setSaving] = useState(false);
const [editing, setEditing] = useState(false); const [editing, setEditing] = useState(autoEdit); // autoEdit → 初始即编辑态
const [copied, setCopied] = useState(false); const [copied, setCopied] = useState(false);
// autoEdit 时隐式启用清理(编辑入口必须有清理,否则 status/managedFields 会被 K8s 拒绝)
const effectiveClean = cleanBeforeEdit || autoEdit;
const loadYaml = async () => { const loadYaml = async () => {
setLoading(true); setLoading(true);
try { try {
const text = await kubernetesApi.getResourceYaml(clusterCode, namespace, resource, name); const text = await kubernetesApi.getResourceYaml(clusterCode, namespace, resource, name);
setRawYaml(text); setRawYaml(text);
setEditYaml(text); setEditYaml(effectiveClean ? cleanYAML(text) : text);
} catch (e: any) { } catch (e: any) {
toast({ title: '获取YAML失败', description: e.message, variant: 'destructive' }); toast({ title: '获取YAML失败', description: e.message, variant: 'destructive' });
const err = `# Error: ${e.message}`; const err = `# Error: ${e.message}`;
@@ -41,10 +45,10 @@ export function YamlViewer({ clusterCode, namespace, resource, name, onClose, on
const enterEdit = () => { const enterEdit = () => {
// 进入编辑前可选清理 // 进入编辑前可选清理
const cleaned = cleanBeforeEdit ? cleanYAML(rawYaml) : rawYaml; const cleaned = effectiveClean ? cleanYAML(rawYaml) : rawYaml;
setEditYaml(cleaned); setEditYaml(cleaned);
setEditing(true); setEditing(true);
if (cleanBeforeEdit) { if (effectiveClean) {
toast({ title: '已清理只读字段', description: '已剥离 status / managedFields / uid 等' }); toast({ title: '已清理只读字段', description: '已剥离 status / managedFields / uid 等' });
} }
}; };