优化多个组件的远程加载逻辑,移除不必要的属性绑定,增强错误处理机制,提升用户体验。

This commit is contained in:
jxxghp
2025-05-06 23:31:37 +08:00
parent 703204c69a
commit 4586f6982a
10 changed files with 640 additions and 182 deletions

View File

@@ -28,7 +28,7 @@ const getImgUrl = computed(() => {
</script>
<template>
<VHover v-bind="props">
<VHover>
<template #default="hover">
<VCard
v-bind="hover.props"

View File

@@ -151,7 +151,7 @@ onMounted(async () => {
</script>
<template>
<VHover v-bind="props" :height="props.height" :width="props.width">
<VHover>
<template #default="hover">
<VCard
v-bind="hover.props"

View File

@@ -37,7 +37,7 @@ function goPlay(isHovering: boolean | null = false) {
</script>
<template>
<VHover v-bind="props">
<VHover>
<template #default="hover">
<VCard
v-bind="hover.props"

View File

@@ -46,9 +46,6 @@ const isRefreshed = ref(false)
// 渲染模式: 'vuetify' 或 'vue'
const renderMode = ref('vuetify')
// 远程组件加载错误
const remoteComponentError = ref<Error | string | null>(null)
// Vue 模式:动态加载的组件
const dynamicComponent = defineAsyncComponent({
// 工厂函数
@@ -61,46 +58,28 @@ const dynamicComponent = defineAsyncComponent({
// 动态加载远程组件
const module = await loadRemoteComponent(props.plugin.id, 'Config')
// 返回组件
return module.default
// 直接返回加载的组件无需再获取default
return module
} catch (error) {
console.error('加载远程组件失败:', error)
remoteComponentError.value = error instanceof Error ? error.message : String(error)
// 返回一个简单的错误组件
return {
template: `
<div class="pa-4">
<VAlert type="error" title="组件加载失败">
无法加载远程组件: {{ error }}
</VAlert>
</div>
`,
props: ['error'],
setup() {
return { error: remoteComponentError.value }
},
}
}
},
// 加载中显示的组件
loadingComponent: {
template: '<VSkeletonLoader type="card"></VSkeletonLoader>',
},
// 如果加载组件超时
timeout: 10000,
// 在显示loadingComponent之前的延迟 | 默认值200毫秒
delay: 200,
// 定义组件是否可挂起 | 默认值true
suspensible: false,
onError(error, retry, fail, attempts) {
if (attempts <= 3) {
// 重试3次
retry()
} else {
// 超过重试次数后不再重试
fail()
}
// 添加错误处理
errorComponent: {
template: `
<div class="pa-4">
<VAlert type="error" title="组件加载错误">
无法加载组件,请稍后再试
</VAlert>
</div>
`,
},
// 添加超时设置
timeout: 20000,
})
//调用API读取UI和配置数据
@@ -110,7 +89,6 @@ async function loadPluginUIData() {
pluginFormItems = []
pluginConfigForm.value = {}
renderMode.value = 'vuetify'
remoteComponentError.value = null
try {
// 获取UI定义
@@ -184,9 +162,6 @@ onBeforeMount(async () => {
<!-- Vue 渲染模式 -->
<div v-else-if="renderMode === 'vue'">
<component :is="dynamicComponent" :initial-config="pluginConfigForm" @save="handleVueComponentSave" />
<div v-if="remoteComponentError">
<v-alert type="error" title="组件加载失败"> 无法加载远程组件: {{ remoteComponentError }} </v-alert>
</div>
</div>
</VCardText>
<VCardActions class="pt-3">

View File

@@ -29,9 +29,6 @@ const renderMode = ref('vuetify')
// 插件数据页面配置项
let pluginPageItems = ref([])
// 远程组件加载错误
const remoteComponentError = ref<Error | string | null>(null)
// Vue 模式:动态加载的组件
const dynamicComponent = defineAsyncComponent({
// 工厂函数
@@ -44,46 +41,27 @@ const dynamicComponent = defineAsyncComponent({
// 动态加载远程组件
const module = await loadRemoteComponent(props.plugin.id, 'Page')
// 返回组件
return module.default
return module
} catch (error) {
console.error('加载远程组件失败:', error)
remoteComponentError.value = error instanceof Error ? error.message : String(error)
// 返回一个简单的错误组件
return {
template: `
<div class="pa-4">
<VAlert type="error" title="组件加载失败">
无法加载远程组件: {{ error }}
</VAlert>
</div>
`,
props: ['error'],
setup() {
return { error: remoteComponentError.value }
},
}
}
},
// 加载中显示的组件
loadingComponent: {
template: '<VSkeletonLoader type="card"></VSkeletonLoader>',
},
// 如果加载组件超时
timeout: 10000,
// 在显示loadingComponent之前的延迟 | 默认值200毫秒
delay: 200,
// 定义组件是否可挂起 | 默认值true
suspensible: false,
onError(error, retry, fail, attempts) {
if (attempts <= 3) {
// 重试3次
retry()
} else {
// 超过重试次数后不再重试
fail()
}
// 添加错误处理
errorComponent: {
template: `
<div class="pa-4">
<VAlert type="error" title="组件加载错误">
无法加载组件,请稍后再试
</VAlert>
</div>
`,
},
// 添加超时设置
timeout: 20000,
})
// 调用API读取数据页面UI
@@ -91,7 +69,6 @@ async function loadPluginUIData() {
isRefreshed.value = false
pluginPageItems.value = []
renderMode.value = 'vuetify'
remoteComponentError.value = null
try {
const result: { [key: string]: any } = await api.get(`plugin/page/${props.plugin?.id}`)
@@ -134,9 +111,6 @@ onMounted(() => {
<!-- Vue 渲染模式 -->
<div v-else-if="renderMode === 'vue'">
<component :is="dynamicComponent" @action="handleAction" />
<div v-if="remoteComponentError">
<v-alert type="error" title="组件加载失败"> 无法加载远程组件: {{ remoteComponentError }} </v-alert>
</div>
</div>
</VCardText>
<VFab

View File

@@ -33,9 +33,6 @@ const emit = defineEmits(['update:refreshStatus'])
// 插件UI渲染模式 ('vuetify' 或 'vue')
const pluginRenderMode = computed(() => props.config?.render_mode || 'vuetify')
// 远程组件加载错误
const remoteComponentError = ref<Error | string | null>(null)
// Vue 模式:动态加载的组件
const dynamicPluginComponent = defineAsyncComponent({
// 工厂函数
@@ -48,45 +45,25 @@ const dynamicPluginComponent = defineAsyncComponent({
// 动态加载远程组件
const module = await loadRemoteComponent(props.config.id, 'Dashboard')
// 返回组件
return module.default
// 直接返回加载的组件无需再获取default
return module
} catch (error) {
console.error('加载远程组件失败:', error)
remoteComponentError.value = error instanceof Error ? error.message : String(error)
// 返回一个简单的错误组件
return {
template: `
<div class="pa-4">
<VAlert type="error" title="组件加载失败">
无法加载远程组件: {{ error }}
</VAlert>
</div>
`,
props: ['error'],
setup() {
return { error: remoteComponentError.value }
},
}
}
},
// 加载中显示的组件
loadingComponent: {
template: '<VSkeletonLoader type="card"></VSkeletonLoader>',
},
// 如果加载组件超时
timeout: 10000,
// 在显示loadingComponent之前的延迟 | 默认值200毫秒
delay: 200,
// 定义组件是否可挂起 | 默认值true
suspensible: false,
onError(error, retry, fail, attempts) {
if (attempts <= 3) {
// 重试3次
retry()
} else {
// 超过重试次数后不再重试
fail()
}
// 添加错误处理
errorComponent: {
template: `
<div class="pa-4">
<VAlert type="error" title="组件加载错误">
无法加载组件,请稍后再试
</VAlert>
</div>
`,
},
})
@@ -112,9 +89,6 @@ onUnmounted(() => {
<!-- Vue 渲染模式 -->
<div v-if="pluginRenderMode === 'vue'">
<component :is="dynamicPluginComponent" :config="props.config" :allow-refresh="props.allowRefresh" />
<div v-if="remoteComponentError" class="mt-2">
<VAlert type="error" title="组件加载失败"> 无法加载远程组件: {{ remoteComponentError }} </VAlert>
</div>
<!-- Vue 模式下也可以显示拖拽句柄 -->
<div class="absolute right-5 top-5">
<VIcon class="cursor-move">mdi-drag</VIcon>