diff --git a/src/views/dashboard/modules/card-data.vue b/src/views/dashboard/modules/card-data.vue index 0505e45..3493ca5 100644 --- a/src/views/dashboard/modules/card-data.vue +++ b/src/views/dashboard/modules/card-data.vue @@ -8,9 +8,9 @@ import { EditOutlined, DeleteOutlined } from '@ant-design/icons-vue'; -import { getDashboardSiteList, addSite, deleteSite, getSiteConfig, updateSite } from '@/service/api/auth'; +import { getDashboardSiteList, addSite, deleteSite, getSiteConfig, updateSite, getMeshConfig, updateMeshConfig, getRoamingConfig, updateRoamingConfig } from '@/service/api/auth'; import { useI18n } from 'vue-i18n'; -import { Form, Modal } from 'ant-design-vue'; +import { Form, Modal, Divider, Checkbox, Select, Input, Button } from 'ant-design-vue'; import { message } from 'ant-design-vue'; import { regionOptions, timeZoneOptions } from '@/constants/site-options'; const { t } = useI18n(); @@ -250,6 +250,13 @@ const editFormData = ref({ region: '', timeZone: '', scenario: '', + meshEnable: false, + autoFailoverEnable: false, + defGatewayEnable: true, + gateway: '', + fastRoamingEnable: false, + nonStickRoamingEnable: false, + aiRoamingEnable: false }); // 当前编辑的站点ID @@ -269,18 +276,53 @@ const { validate: validateEdit, validateInfos: validateEditInfos } = useForm(edi scenario: [{ required: true, message: t('page.carddata.scenarioRequired') }] }); +// IP分段输入 +const gatewayIpParts = ref(['', '', '', '']); + +// 拆分IP到4段 +function splitGatewayIp(ip: string) { + if (!ip) return ['', '', '', '']; + const parts = ip.split('.'); + return [parts[0] || '', parts[1] || '', parts[2] || '', parts[3] || '']; +} +// 拼接4段为IP +function joinGatewayIp(parts: string[]) { + return parts.map(p => p.trim()).join('.'); +} + +// 弹窗打开时同步分段 +watch(() => editFormData.value.gateway, (val) => { + gatewayIpParts.value = splitGatewayIp(val); +}, { immediate: true }); +// 分段输入时同步到gateway +watch(gatewayIpParts, (val) => { + editFormData.value.gateway = joinGatewayIp(val); +}, { deep: true }); + // 处理编辑按钮点击 const handleEdit = async (record: Api.DashboardSite) => { try { currentEditSiteId.value = record.siteId; - const response = await getSiteConfig(record.siteId); - if (response.data) { + const [siteRes, meshRes, roamingRes] = await Promise.all([ + getSiteConfig(record.siteId), + getMeshConfig(record.siteId), + getRoamingConfig(record.siteId) + ]); + if (siteRes.data) { editFormData.value = { - name: response.data.name, - region: response.data.region, - timeZone: response.data.timeZone, - scenario: response.data.scenario + name: siteRes.data.name, + region: siteRes.data.region, + timeZone: siteRes.data.timeZone, + scenario: siteRes.data.scenario, + meshEnable: meshRes.data?.mesh?.meshEnable ?? false, + autoFailoverEnable: meshRes.data?.mesh?.autoFailoverEnable ?? false, + defGatewayEnable: meshRes.data?.mesh?.defGatewayEnable ?? true, + gateway: meshRes.data?.mesh?.gateway ?? '', + fastRoamingEnable: roamingRes.data?.roaming?.fastRoamingEnable ?? false, + nonStickRoamingEnable: roamingRes.data?.roaming?.nonStickRoamingEnable ?? false, + aiRoamingEnable: roamingRes.data?.roaming?.aiRoamingEnable ?? false }; + gatewayIpParts.value = splitGatewayIp(editFormData.value.gateway); showEditDialog.value = true; } } catch (error) { @@ -293,7 +335,32 @@ const handleEdit = async (record: Api.DashboardSite) => { const handleUpdateSite = async () => { try { await validateEdit(); - await updateSite(currentEditSiteId.value, editFormData.value); + // 先保存基础配置 + await updateSite(currentEditSiteId.value, { + name: editFormData.value.name, + region: editFormData.value.region, + timeZone: editFormData.value.timeZone, + scenario: editFormData.value.scenario + }); + // mesh 配置为嵌套结构,meshEnable为true时才携带defGatewayEnable和gateway + const meshData: any = { mesh: { meshEnable: editFormData.value.meshEnable } }; + if (editFormData.value.meshEnable) { + meshData.mesh.autoFailoverEnable = editFormData.value.autoFailoverEnable; + meshData.mesh.defGatewayEnable = editFormData.value.defGatewayEnable; + if (editFormData.value.defGatewayEnable === false) { + meshData.mesh.gateway = editFormData.value.gateway; + } + } + // roaming 配置为嵌套结构 + const roamingData: any = { roaming: { fastRoamingEnable: editFormData.value.fastRoamingEnable } }; + if (editFormData.value.fastRoamingEnable) { + roamingData.roaming.nonStickRoamingEnable = editFormData.value.nonStickRoamingEnable; + roamingData.roaming.aiRoamingEnable = editFormData.value.aiRoamingEnable; + } + await Promise.all([ + updateMeshConfig(currentEditSiteId.value, meshData), + updateRoamingConfig(currentEditSiteId.value, roamingData) + ]); message.success(t('page.carddata.updateSuccess')); showEditDialog.value = false; fetchSiteList(); // 刷新列表 @@ -478,6 +545,7 @@ const handleUpdateSite = async () => { @ok="handleUpdateSite" @cancel="showEditDialog = false" :maskClosable="false" + :width="700" > { :options="scenarioOptions" /> + + +
组网配置
+ + Mesh + + + + Auto(Recommended) + Custom + + + + + Auto Failover + + + Fast Roaming + + + Non-Stick Roaming + + + AI Roaming +