515 lines
14 KiB
Vue
515 lines
14 KiB
Vue
<template>
|
|
<AppPage>
|
|
<n-card>
|
|
<n-tabs default-value="Server" justify-content="space-evenly" type="line" @update-value="tabChange">
|
|
<n-tab-pane name="Server" tab="服务端">
|
|
<n-form
|
|
ref="serverFormRef"
|
|
:model="serverFormModel"
|
|
:rules="serverFormRules"
|
|
>
|
|
<n-form-item label="IP段" path="ipScope" :rule="{
|
|
required: true,
|
|
type: 'array',
|
|
message: 'IP段不能为空',
|
|
trigger: ['change','blur']
|
|
}">
|
|
<n-select
|
|
v-model:value="serverFormModel.ipScope"
|
|
filterable
|
|
multiple
|
|
tag
|
|
placeholder="输入,按回车确认"
|
|
:show-arrow="false"
|
|
:show="false"
|
|
/>
|
|
</n-form-item>
|
|
<n-form-item label="监听端口" path="listenPort" :rule="[
|
|
{
|
|
required: true,
|
|
type: 'number',
|
|
message: '监听端口不能为空',
|
|
trigger: ['change','blur']
|
|
},
|
|
{
|
|
min: 1120,
|
|
type: 'number',
|
|
message: '端口最低设置为1120',
|
|
trigger: ['change','blur']
|
|
},
|
|
{
|
|
max: 65535,
|
|
type: 'number',
|
|
message: '端口最高设置为65535',
|
|
trigger: ['change','blur']
|
|
}
|
|
]">
|
|
<n-input-number :min="1120" :max="65535" v-model:value="serverFormModel.listenPort"/>
|
|
</n-form-item>
|
|
<n-form-item label="私钥" path="privateKey">
|
|
<n-input v-model:value="serverFormModel.privateKey"/>
|
|
</n-form-item>
|
|
<n-form-item label="公钥" path="publicKey">
|
|
<n-input v-model:value="serverFormModel.publicKey"/>
|
|
</n-form-item>
|
|
<n-form-item label="上行脚本" path="postUpScript">
|
|
<n-input v-model:value="serverFormModel.postUpScript"/>
|
|
</n-form-item>
|
|
<n-form-item label="下行脚本" path="postDownScript">
|
|
<n-input v-model:value="serverFormModel.postDownScript"/>
|
|
</n-form-item>
|
|
<n-form-item>
|
|
<n-button type="info" @click="updateServerConf">确认</n-button>
|
|
</n-form-item>
|
|
</n-form>
|
|
</n-tab-pane>
|
|
<n-tab-pane name="Global" tab="全局">
|
|
<n-form
|
|
ref="globalFormRef"
|
|
:model="globalFormModel"
|
|
:rules="globalFormRules"
|
|
>
|
|
<n-form-item label="公网IP" path="endpointAddress" class="pid">
|
|
<n-input v-model:value="globalFormModel.endpointAddress"/>
|
|
<n-button style="margin-top: 5px" size="small" type="warning" @click="getPublicAddr">获取地址</n-button>
|
|
</n-form-item>
|
|
<n-form-item label="DNS" path="dnsServer" :rule="{
|
|
required: true,
|
|
type: 'array',
|
|
message: 'dns不能为空',
|
|
trigger: ['change','blur']
|
|
}">
|
|
<n-select
|
|
v-model:value="globalFormModel.dnsServer"
|
|
filterable
|
|
multiple
|
|
tag
|
|
placeholder="输入,按回车确认"
|
|
:show-arrow="false"
|
|
:show="false"
|
|
/>
|
|
</n-form-item>
|
|
<n-form-item label="MTU" path="MTU" :rule="[
|
|
{
|
|
required: true,
|
|
type: 'number',
|
|
message: 'MTU不能为空',
|
|
trigger: ['change','blur']
|
|
},
|
|
{
|
|
min: 1120,
|
|
type: 'number',
|
|
message: 'MTU最低设置为100',
|
|
trigger: ['change','blur']
|
|
},
|
|
{
|
|
max: 3000,
|
|
type: 'number',
|
|
message: 'MTU最高设置为3000',
|
|
trigger: ['change','blur']
|
|
}
|
|
]">
|
|
<n-input-number :min="100" :max="3000" v-model:value="globalFormModel.MTU"/>
|
|
</n-form-item>
|
|
<n-form-item label="persistentKeepalive" path="persistentKeepalive" :rule="[
|
|
{
|
|
required: true,
|
|
type: 'number',
|
|
message: 'persistentKeepalive不能为空',
|
|
trigger: ['change','blur']
|
|
},
|
|
{
|
|
min: 15,
|
|
type: 'number',
|
|
message: 'persistentKeepalive最低设置为15',
|
|
trigger: ['change','blur']
|
|
},
|
|
{
|
|
max: 300,
|
|
type: 'number',
|
|
message: 'persistentKeepalive最高设置为300',
|
|
trigger: ['change','blur']
|
|
}
|
|
]">
|
|
<n-input-number :min="15" :max="300" v-model:value="globalFormModel.persistentKeepalive"/>
|
|
</n-form-item>
|
|
<n-form-item label="firewallMark" path="firewallMark">
|
|
<n-input v-model:value="globalFormModel.firewallMark"/>
|
|
</n-form-item>
|
|
<n-form-item label="table" path="table">
|
|
<n-input v-model:value="globalFormModel.table"/>
|
|
</n-form-item>
|
|
<n-form-item label="configPath" path="configFilePath">
|
|
<n-input v-model:value="globalFormModel.configFilePath"/>
|
|
</n-form-item>
|
|
<n-form-item>
|
|
<n-button type="info" @click="updateGlobalConf">确认</n-button>
|
|
</n-form-item>
|
|
</n-form>
|
|
</n-tab-pane>
|
|
<n-tab-pane name="Other" tab="其他">
|
|
<n-button style="float:right;margin-bottom: 10px" size="small" type="info" @click="showAddModal = !showAddModal">添加</n-button>
|
|
<n-data-table
|
|
:columns="tableColumns"
|
|
:data="taleData.data"
|
|
/>
|
|
</n-tab-pane>
|
|
</n-tabs>
|
|
</n-card>
|
|
<n-modal
|
|
:title="editFormModel.describe"
|
|
v-model:show="showEditModal"
|
|
preset="card"
|
|
style="width: 30%"
|
|
>
|
|
<n-form
|
|
ref="editFormRef"
|
|
:model="editFormModel"
|
|
>
|
|
<n-form-item v-for="(item,index) in editFormModel.data" :label="index">
|
|
<n-input v-if="typeof item === 'string'" v-model:value="editFormModel.data[index]"/>
|
|
<n-input-number v-else-if="typeof item === 'number'" v-model:value="editFormModel.data[index]"/>
|
|
<n-radio-group v-else-if="typeof item === 'boolean'" :value="editFormModel.data[index]">
|
|
<n-radio :value="true" :checked="editFormModel.data[index] === true" @change="editFormModel.data[index] = true">是</n-radio>
|
|
<n-radio :value="false" :checked="editFormModel.data[index] === false" @change="editFormModel.data[index] = false">否</n-radio>
|
|
</n-radio-group>
|
|
</n-form-item>
|
|
<n-form-item label="配置描述">
|
|
<n-input v-model:value="editFormModel.describe" />
|
|
</n-form-item>
|
|
<n-form-item>
|
|
<n-button type="info" @click="updateSetting">确认</n-button>
|
|
</n-form-item>
|
|
</n-form>
|
|
</n-modal>
|
|
<n-modal
|
|
title="添加"
|
|
v-model:show="showAddModal"
|
|
preset="card"
|
|
style="width: 30%"
|
|
>
|
|
<n-form :model="addFormModel" ref="addFormRef">
|
|
<n-form-item label="Code">
|
|
<n-input v-model:value="addFormModel.code"></n-input>
|
|
</n-form-item>
|
|
<n-form-item label="选项">
|
|
<n-dynamic-input v-model:value="addFormModel.data" preset="pair" key-placeholder="键" value-placeholder="值"/>
|
|
</n-form-item>
|
|
<n-form-item label="描述">
|
|
<n-input v-model:value="addFormModel.describe"></n-input>
|
|
</n-form-item>
|
|
<n-form-item>
|
|
<n-button type="info" @click="addSetting">确认</n-button>
|
|
</n-form-item>
|
|
</n-form>
|
|
</n-modal>
|
|
</AppPage>
|
|
</template>
|
|
<script setup>
|
|
|
|
// 服务端配置表单ref
|
|
import AppPage from '@/components/page/AppPage.vue'
|
|
import api from '@/views/setting/api'
|
|
import { NButton } from 'naive-ui'
|
|
import { renderIcon } from '@/utils'
|
|
import event from '@/utils/event/event'
|
|
|
|
const { $bus } = event();
|
|
const tabCode = ref("")
|
|
|
|
// 表头
|
|
const tableColumns = [
|
|
{
|
|
title: 'code',
|
|
key: 'code',
|
|
align: 'center',
|
|
titleAlign: 'center',
|
|
},
|
|
{
|
|
title: "描述",
|
|
key: "describe",
|
|
align: 'center',
|
|
titleAlign: 'center',
|
|
},
|
|
{
|
|
title: '操作',
|
|
key: 'action',
|
|
align: 'center',
|
|
titleAlign: 'center',
|
|
render: (row) => {
|
|
return [
|
|
h(NButton, {
|
|
size: 'small',
|
|
color: '#4389DA',
|
|
onClick: () => listBtn(row, "EDIT")
|
|
}, {
|
|
icon: renderIcon('mingcute:edit-line', { size: 14 }),
|
|
}),
|
|
h(NButton, {
|
|
size: 'small',
|
|
style: 'margin-left: 5px',
|
|
color: '#ED1518',
|
|
onClick: () => listBtn(row, "DELETE")
|
|
}, {
|
|
icon: renderIcon('icon-park-outline:delete', { size: 14 }),
|
|
})
|
|
]
|
|
}
|
|
}
|
|
]
|
|
|
|
const taleData = ref({
|
|
data: []
|
|
})
|
|
|
|
// 服务端表单ref
|
|
const serverFormRef = ref(null)
|
|
// 全局设置表单ref
|
|
const globalFormRef = ref(null)
|
|
// 编辑模态框表单ref
|
|
const editFormRef = ref(null)
|
|
// 添加模态框表单ref
|
|
const addFormRef = ref(null)
|
|
// 编辑模态框展示
|
|
const showEditModal = ref(false)
|
|
// 添加模态框展示
|
|
const showAddModal = ref(false)
|
|
|
|
// 服务端表单数据
|
|
const serverFormModel = ref({
|
|
ipScope: [],
|
|
listenPort: 51820,
|
|
privateKey: '',
|
|
publicKey: '',
|
|
postUpScript: '',
|
|
postDownScript: ''
|
|
})
|
|
// 全局设置表单数据
|
|
const globalFormModel = ref({
|
|
MTU: 1450,
|
|
configFilePath: '',
|
|
dnsServer: [],
|
|
endpointAddress: '',
|
|
firewallMark: '',
|
|
persistentKeepalive: 15,
|
|
table: ''
|
|
})
|
|
// 编辑表单数据
|
|
const editFormModel = ref({
|
|
code: '',
|
|
data: '',
|
|
describe: ''
|
|
})
|
|
// 添加表单数据
|
|
const addFormModel = ref({
|
|
code: '',
|
|
data: [
|
|
{
|
|
key: '',
|
|
value: ''
|
|
}
|
|
],
|
|
describe: ''
|
|
})
|
|
|
|
// 服务端表单数据验证
|
|
const serverFormRules = {
|
|
privateKey: [
|
|
{ required: true, message: '密钥不能为空', trigger: 'blur' }
|
|
],
|
|
publicKey: [
|
|
{ required: true, message: '公钥不能为空', trigger: 'blur' }
|
|
]
|
|
}
|
|
// 全局表单数据验证
|
|
const globalFormRules = {
|
|
endpointAddress: [
|
|
{ required: true, message: '公网IP不能为空', trigger: 'blur' }
|
|
],
|
|
configFilePath: [
|
|
{ required: true, message: '文件地址不能为空', trigger: 'blur' }
|
|
]
|
|
}
|
|
|
|
// 获取服务端配置
|
|
async function getServerConfig () {
|
|
const res = await api.getSetting({
|
|
code: "WG_SERVER"
|
|
})
|
|
if (res.data.code === 200) {
|
|
serverFormModel.value = JSON.parse(res.data.data)
|
|
}
|
|
}
|
|
|
|
// 获取全局配置
|
|
async function getGlobalConfig () {
|
|
const res = await api.getSetting({
|
|
code: "WG_SETTING"
|
|
})
|
|
if (res.data.code === 200) {
|
|
globalFormModel.value = JSON.parse(res.data.data)
|
|
}
|
|
}
|
|
|
|
// 更改服务端配置
|
|
async function updateServerConf() {
|
|
serverFormRef.value?.validate(async (errors) => {
|
|
if (errors) {
|
|
return errors
|
|
}
|
|
const res = await api.setSetting({
|
|
code: "WG_SERVER",
|
|
data: JSON.stringify(serverFormModel.value)
|
|
})
|
|
if (res.data.code === 200) {
|
|
await getServerConfig()
|
|
$message.success("操作成功")
|
|
}
|
|
})
|
|
|
|
}
|
|
|
|
// 更改全局配置
|
|
async function updateGlobalConf() {
|
|
globalFormRef.value?.validate(async (errors) => {
|
|
if (errors) {
|
|
return errors
|
|
}
|
|
const res = await api.setSetting({
|
|
code: "WG_SETTING",
|
|
data: JSON.stringify(globalFormModel.value)
|
|
})
|
|
if (res.data.code === 200) {
|
|
await getGlobalConfig()
|
|
$message.success("操作成功")
|
|
}
|
|
})
|
|
}
|
|
|
|
// 获取公网IP地址
|
|
async function getPublicAddr() {
|
|
const res = await api.publicAddr()
|
|
if (res.data.code === 200) {
|
|
globalFormModel.value.endpointAddress = res.data.data
|
|
}
|
|
}
|
|
|
|
// 获取全部配置
|
|
function allSetting() {
|
|
api.allSettings().then(res => {
|
|
if (res.data.code === 200) {
|
|
taleData.value.data = res.data.data
|
|
}
|
|
})
|
|
}
|
|
|
|
// tab切换事件
|
|
function tabChange(code) {
|
|
switch (code) {
|
|
case "Server":
|
|
getServerConfig()
|
|
tabCode.value = "Server"
|
|
break;
|
|
case "Global":
|
|
getGlobalConfig()
|
|
tabCode.value = "Global"
|
|
break;
|
|
case "Other":
|
|
allSetting()
|
|
tabCode.value = "Other"
|
|
break;
|
|
}
|
|
}
|
|
|
|
// 列表操作按钮
|
|
function listBtn(row,code) {
|
|
switch (code) {
|
|
case "EDIT":
|
|
showEditModal.value = true
|
|
editFormModel.value.describe = row.describe
|
|
editFormModel.value.data = JSON.parse(row.data)
|
|
editFormModel.value.code = row.code
|
|
break;
|
|
case "DELETE":
|
|
$dialog.confirm({
|
|
type: 'warning',
|
|
title: '删除',
|
|
content: `是否删除设置:【${row.describe}】?`,
|
|
async confirm() {
|
|
const res = await api.delSetting(row.code)
|
|
if (res.data.code === 200) {
|
|
$message.success("操作成功")
|
|
allSetting()
|
|
}
|
|
},
|
|
})
|
|
break;
|
|
}
|
|
}
|
|
|
|
// 更改配置信息
|
|
async function updateSetting() {
|
|
const res = await api.setSetting({
|
|
code: editFormModel.value.code,
|
|
data: JSON.stringify(editFormModel.value.data),
|
|
describe: editFormModel.value.describe
|
|
})
|
|
if (res.data.code === 200) {
|
|
showEditModal.value = false
|
|
allSetting()
|
|
}
|
|
}
|
|
|
|
// 添加设置
|
|
async function addSetting() {
|
|
const dataObj = {}
|
|
for (const item of addFormModel.value.data) {
|
|
dataObj[item.key] = item.value
|
|
}
|
|
|
|
const addFormData = {
|
|
code: addFormModel.value.code,
|
|
data: JSON.stringify(dataObj),
|
|
describe: addFormModel.value.describe
|
|
}
|
|
|
|
const res = await api.setSetting(addFormData)
|
|
if (res.data.code === 200) {
|
|
showAddModal.value = false
|
|
addFormModel.value = {
|
|
code: '',
|
|
data: [
|
|
{
|
|
key: '',
|
|
value: ''
|
|
}
|
|
],
|
|
describe: ''
|
|
}
|
|
allSetting()
|
|
}
|
|
}
|
|
|
|
$bus.on("refreshSetting",value => {
|
|
if (value) {
|
|
if (tabCode.value === "" || tabCode.value === undefined) {
|
|
getServerConfig()
|
|
} else {
|
|
switch (tabCode.value) {
|
|
case "Server":
|
|
getServerConfig()
|
|
break;
|
|
case "Global":
|
|
getGlobalConfig()
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
})
|
|
getServerConfig()
|
|
</script>
|
|
<style lang="scss">
|
|
.pid .n-form-item-blank {
|
|
display: inline;
|
|
}
|
|
</style> |