优化: AI Chat全栈多批审查修复与架构清理(risk_level清理/路由解耦/工具渲染/测试补测/死代码)
This commit is contained in:
75
src/components/ErrorBoundary.vue
Normal file
75
src/components/ErrorBoundary.vue
Normal file
@@ -0,0 +1,75 @@
|
||||
<template>
|
||||
<!-- 全局错误兜底:子树渲染/生命周期抛错时显示降级 UI,防止白屏。
|
||||
用法:用 <ErrorBoundary> 包裹可能出错的子组件树(slot 透传)。 -->
|
||||
<template v-if="error">
|
||||
<div class="error-boundary">
|
||||
<div class="error-boundary-icon">⚠</div>
|
||||
<div class="error-boundary-title">{{ $t('error.title') }}</div>
|
||||
<div class="error-boundary-desc">{{ $t('error.desc') }}</div>
|
||||
<button class="error-boundary-retry" @click="reset">{{ $t('error.retry') }}</button>
|
||||
</div>
|
||||
</template>
|
||||
<slot v-else />
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { ref, onErrorCaptured } from 'vue'
|
||||
|
||||
// errorCaptured 捕获子组件树抛出的错误(渲染/生命周期),返回 false 阻止继续向上冒泡
|
||||
const error = ref<unknown>(null)
|
||||
|
||||
onErrorCaptured((err) => {
|
||||
error.value = err
|
||||
console.error('[ErrorBoundary] 子树渲染错误:', err)
|
||||
return false
|
||||
})
|
||||
|
||||
// 重试:重置 errorState,slot 重新挂载子树
|
||||
function reset() {
|
||||
error.value = null
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.error-boundary {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 8px;
|
||||
padding: 32px 16px;
|
||||
color: var(--df-text-secondary, #888);
|
||||
text-align: center;
|
||||
}
|
||||
.error-boundary-icon {
|
||||
font-size: 28px;
|
||||
color: var(--df-danger, #e5484d);
|
||||
line-height: 1;
|
||||
}
|
||||
.error-boundary-title {
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
color: var(--df-text, #333);
|
||||
}
|
||||
.error-boundary-desc {
|
||||
font-size: 12px;
|
||||
line-height: 1.5;
|
||||
max-width: 360px;
|
||||
}
|
||||
.error-boundary-retry {
|
||||
margin-top: 8px;
|
||||
padding: 5px 16px;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
font-family: var(--df-font-sans);
|
||||
background: var(--df-accent, #7b6ff0);
|
||||
color: #fff;
|
||||
border: none;
|
||||
border-radius: var(--df-radius-sm, 4px);
|
||||
cursor: pointer;
|
||||
transition: filter 0.15s;
|
||||
}
|
||||
.error-boundary-retry:hover {
|
||||
filter: brightness(1.1);
|
||||
}
|
||||
</style>
|
||||
Reference in New Issue
Block a user