From 351235484c537876604cc66ec58857d8ae21e031 Mon Sep 17 00:00:00 2001 From: auto-bot Date: Sun, 14 Jun 2026 01:12:07 +0000 Subject: [PATCH] =?UTF-8?q?feat(log):=20=E9=BB=98=E8=AE=A4=E4=B8=8D?= =?UTF-8?q?=E5=B1=95=E5=BC=80=E8=AF=A6=E6=83=85=20+=20Error=E8=AF=A6?= =?UTF-8?q?=E6=83=85=E8=A7=84=E8=8C=83=E5=8C=96=20+=20=E6=89=93=E5=8D=B0/H?= =?UTF-8?q?TML=E5=AF=BC=E5=87=BA=E5=9B=BE=E7=89=87?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/stores/log.ts | 26 ++++++- src/views/LogView.vue | 160 ++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 180 insertions(+), 6 deletions(-) diff --git a/src/stores/log.ts b/src/stores/log.ts index b5a967d..9589db8 100644 --- a/src/stores/log.ts +++ b/src/stores/log.ts @@ -52,13 +52,37 @@ export const useLogStore = defineStore('log', () => { const ss = now.getSeconds().toString().padStart(2, '0'); const ms = now.getMilliseconds().toString().padStart(3, '0'); + // Error 对象属性不可枚举(JSON.stringify 会得到 {}),这里先规范化 + let normalizedDetail = detail; + if (detail instanceof Error) { + normalizedDetail = { + name: detail.name, + message: detail.message, + stack: detail.stack, + cause: (detail as any).cause, + __isError: true, + }; + } else if (detail && typeof detail === 'object') { + // 避免 Proxy 等响应式包装的干扰 — 简单浅拷贝为纯对象 + try { + normalizedDetail = JSON.parse(JSON.stringify(detail, (_, v) => { + if (v instanceof Error) { + return { name: v.name, message: v.message, stack: v.stack, __isError: true }; + } + return v; + })); + } catch { + normalizedDetail = String(detail); + } + } + const entry: LogEntry = { id: nextId++, time: `${hh}:${mm}:${ss}.${ms}`, level, module, message, - detail, + detail: normalizedDetail, }; logs.value.push(entry); diff --git a/src/views/LogView.vue b/src/views/LogView.vue index 887665b..96a1359 100644 --- a/src/views/LogView.vue +++ b/src/views/LogView.vue @@ -46,6 +46,14 @@ {{ expandedAll ? '收起详情' : '展开详情' }} + +