From 220d329d8ecb4e3e23d1f41a6adfe9ca495a2cbb Mon Sep 17 00:00:00 2001 From: ssongliu Date: Thu, 9 Mar 2023 14:53:29 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E9=9D=A2=E6=9D=BF=E8=AE=BE=E7=BD=AE?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E6=95=B0=E5=AD=97=E8=8C=83=E5=9B=B4=E9=99=90?= =?UTF-8?q?=E5=88=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend/app/service/snapshot.go | 21 ++++--- frontend/src/lang/modules/en.ts | 1 + frontend/src/lang/modules/zh.ts | 1 + .../setting/backup-account/operate/index.vue | 61 +++++++++++-------- frontend/src/views/setting/monitor/index.vue | 4 +- frontend/src/views/setting/panel/index.vue | 4 +- frontend/src/views/setting/safe/index.vue | 6 +- 7 files changed, 58 insertions(+), 40 deletions(-) diff --git a/backend/app/service/snapshot.go b/backend/app/service/snapshot.go index a34a045b3..f94b4478d 100644 --- a/backend/app/service/snapshot.go +++ b/backend/app/service/snapshot.go @@ -124,15 +124,15 @@ func (u *SnapshotService) SnapshotCreate(req dto.SnapshotCreate) error { backupDockerDir := fmt.Sprintf("%s/docker", rootDir) _ = os.MkdirAll(backupDockerDir, os.ModePerm) + _ = settingRepo.Update("SystemStatus", "Snapshoting") snap := model.Snapshot{ Name: fmt.Sprintf("1panel_%s_%s", versionItem.Value, timeNow), Description: req.Description, From: req.From, Version: versionItem.Value, - Status: constant.StatusWaiting, + Status: constant.StatusSuccess, } _ = snapshotRepo.Create(&snap) - _ = settingRepo.Update("SystemStatus", "Snapshoting") go func() { defer func() { _ = os.RemoveAll(rootDir) @@ -153,7 +153,6 @@ func (u *SnapshotService) SnapshotCreate(req dto.SnapshotCreate) error { updateSnapshotStatus(snap.ID, constant.StatusFailed, err.Error()) return } - _, _ = cmd.Exec("systemctl restart docker") if err := u.handlePanelBinary(fileOp, "snapshot", "", backupPanelDir+"/1panel"); err != nil { updateSnapshotStatus(snap.ID, constant.StatusFailed, err.Error()) @@ -177,6 +176,7 @@ func (u *SnapshotService) SnapshotCreate(req dto.SnapshotCreate) error { updateSnapshotStatus(snap.ID, constant.StatusFailed, err.Error()) return } + _, _ = cmd.Exec("systemctl restart docker") snapJson := SnapshotJson{ BaseDir: global.CONF.BaseDir, @@ -664,11 +664,9 @@ func (u *SnapshotService) handlePanelDatas(snapID uint, fileOp files.FileOp, ope exclusionRules += ("." + strings.ReplaceAll(dockerDir, source, "") + ";") } - _ = snapshotRepo.Update(snapID, map[string]interface{}{"status": constant.StatusSuccess}) if err := u.handleTar(source, target, "1panel_data.tar.gz", exclusionRules); err != nil { return fmt.Errorf("backup panel data failed, err: %v", err) } - _ = snapshotRepo.Update(snapID, map[string]interface{}{"status": constant.StatusWaiting}) case "recover": exclusionRules := "./tmp/;./cache;" if strings.Contains(backupDir, target) { @@ -852,9 +850,9 @@ func (u *SnapshotService) handleTar(sourceDir, targetDir, name, exclusionRules s exStr += exclude } - ss := fmt.Sprintf("tar --warning=no-file-changed -zcf %s %s -C %s .", targetDir+"/"+name, exStr, sourceDir) - global.LOG.Debug(ss) - stdout, err := cmd.Exec(ss) + commands := fmt.Sprintf("tar -zcf %s %s -C %s .", targetDir+"/"+name, exStr, sourceDir) + global.LOG.Debug(commands) + stdout, err := cmd.Exec(commands) if err != nil { global.LOG.Errorf("do handle tar failed, stdout: %s, err: %v", stdout, err) return errors.New(stdout) @@ -868,10 +866,13 @@ func (u *SnapshotService) handleUnTar(sourceDir, targetDir string) error { return err } } - stdout, err := cmd.Exec(fmt.Sprintf("tar zxf %s -C %s .", sourceDir, targetDir)) + + commands := fmt.Sprintf("tar -zxf %s -C %s .", sourceDir, targetDir) + global.LOG.Debug(commands) + stdout, err := cmd.Exec(commands) if err != nil { global.LOG.Errorf("do handle untar failed, stdout: %s, err: %v", stdout, err) - return errors.New(string(stdout)) + return errors.New(stdout) } return nil } diff --git a/frontend/src/lang/modules/en.ts b/frontend/src/lang/modules/en.ts index 7896e2f93..6b4d67832 100644 --- a/frontend/src/lang/modules/en.ts +++ b/frontend/src/lang/modules/en.ts @@ -96,6 +96,7 @@ export default { fileExist: 'The file already exists in the current folder. Repeat uploading is not supported!', fileNameErr: 'You can upload only files whose name contains 1 to 50 characters, including English, Chinese, digits, or periods (.-_)', + comfimNoNull: 'Make sure the value {0} is not empty', }, login: { firstLogin: 'First login, please create an initial administrator user!', diff --git a/frontend/src/lang/modules/zh.ts b/frontend/src/lang/modules/zh.ts index 5c0a01d00..586a5e5f6 100644 --- a/frontend/src/lang/modules/zh.ts +++ b/frontend/src/lang/modules/zh.ts @@ -101,6 +101,7 @@ export default { unSupportSize: '上传文件超过 {0}M,请确认!', fileExist: '当前文件夹已存在该文件,不支持重复上传!', fileNameErr: '仅支持上传名称包含英文、中文、数字或者 .-_ ,长度 1-50 位的文件', + comfimNoNull: '请确认 {0} 值不为空', }, login: { firstLogin: '首次登录,请创建初始管理员用户!', diff --git a/frontend/src/views/setting/backup-account/operate/index.vue b/frontend/src/views/setting/backup-account/operate/index.vue index 6ebf6ce03..d3ae75c7f 100644 --- a/frontend/src/views/setting/backup-account/operate/index.vue +++ b/frontend/src/views/setting/backup-account/operate/index.vue @@ -72,14 +72,14 @@ v-if="dialogData.rowData!.type !== '' && hasBucket(dialogData.rowData!.type)" label="Bucket" prop="bucket" - :rules="Rules.requiredSelect" > - + - + {{ $t('setting.loadBucket') }} + {{ $t('commons.rule.requiredSelect') }}
@@ -139,6 +139,7 @@ const loading = ref(false); type FormInstance = InstanceType; const formRef = ref(); const buckets = ref(); +const errBuckets = ref(); const endpoints = ref('http'); @@ -181,33 +182,41 @@ function hasBucket(val: string) { return val === 'OSS' || val === 'S3' || val === 'MINIO'; } -const getBuckets = async () => { - loading.value = true; - let item = deepCopy(dialogData.value.rowData!.varsJson); - if (dialogData.value.rowData!.type === 'MINIO') { - dialogData.value.rowData!.varsJson['endpointItem'] = dialogData.value - .rowData!.varsJson['endpointItem'].replace('https://', '') - .replace('http://', ''); - item['endpoint'] = endpoints.value + '://' + dialogData.value.rowData!.varsJson['endpointItem']; - item['endpointItem'] = undefined; - } - listBucket({ - type: dialogData.value.rowData!.type, - vars: JSON.stringify(item), - accessKey: dialogData.value.rowData!.accessKey, - credential: dialogData.value.rowData!.credential, - }) - .then((res) => { - loading.value = false; - buckets.value = res.data; +const getBuckets = async (formEl: FormInstance | undefined) => { + if (!formEl) return; + formEl.validate(async (valid) => { + if (!valid) return; + loading.value = true; + let item = deepCopy(dialogData.value.rowData!.varsJson); + if (dialogData.value.rowData!.type === 'MINIO') { + dialogData.value.rowData!.varsJson['endpointItem'] = dialogData.value + .rowData!.varsJson['endpointItem'].replace('https://', '') + .replace('http://', ''); + item['endpoint'] = endpoints.value + '://' + dialogData.value.rowData!.varsJson['endpointItem']; + item['endpointItem'] = undefined; + } + listBucket({ + type: dialogData.value.rowData!.type, + vars: JSON.stringify(item), + accessKey: dialogData.value.rowData!.accessKey, + credential: dialogData.value.rowData!.credential, }) - .catch(() => { - buckets.value = []; - loading.value = false; - }); + .then((res) => { + loading.value = false; + buckets.value = res.data; + }) + .catch(() => { + buckets.value = []; + loading.value = false; + }); + }); }; const onSubmit = async (formEl: FormInstance | undefined) => { + if (!dialogData.value.rowData.bucket) { + errBuckets.value = true; + return; + } if (!formEl) return; formEl.validate(async (valid) => { if (!valid) return; diff --git a/frontend/src/views/setting/monitor/index.vue b/frontend/src/views/setting/monitor/index.vue index 5e04afb19..b8228cf90 100644 --- a/frontend/src/views/setting/monitor/index.vue +++ b/frontend/src/views/setting/monitor/index.vue @@ -20,7 +20,7 @@ @@ -51,7 +51,7 @@ import { FormInstance } from 'element-plus'; import LayoutContent from '@/layout/layout-content.vue'; import { cleanMonitors, getSettingInfo, updateSetting } from '@/api/modules/setting'; import { useDeleteData } from '@/hooks/use-delete-data'; -import { Rules } from '@/global/form-rules'; +import { Rules, checkNumberRange } from '@/global/form-rules'; import i18n from '@/lang'; import { MsgSuccess } from '@/utils/message'; diff --git a/frontend/src/views/setting/panel/index.vue b/frontend/src/views/setting/panel/index.vue index d5fd5afc2..ede0a7404 100644 --- a/frontend/src/views/setting/panel/index.vue +++ b/frontend/src/views/setting/panel/index.vue @@ -105,7 +105,9 @@ > {{ $t('commons.button.sync') }} - {{ count }} {{ $t('setting.second') }} +
+ {{ count }} {{ $t('setting.second') }} +
diff --git a/frontend/src/views/setting/safe/index.vue b/frontend/src/views/setting/safe/index.vue index 21709a303..091d8883f 100644 --- a/frontend/src/views/setting/safe/index.vue +++ b/frontend/src/views/setting/safe/index.vue @@ -141,7 +141,7 @@ import { updateSetting, getMFA, bindMFA, getSettingInfo, updatePort } from '@/ap import i18n from '@/lang'; import { Rules } from '@/global/form-rules'; import { dateFormatSimple } from '@/utils/util'; -import { MsgSuccess } from '@/utils/message'; +import { MsgError, MsgSuccess } from '@/utils/message'; const loading = ref(false); const form = reactive({ @@ -264,6 +264,10 @@ const handleClose = () => { }; const onBind = async () => { + if (!mfaCode.value) { + MsgError(i18n.global.t('commons.msg.comfimNoNull', ['code'])); + return; + } loading.value = true; await bindMFA({ code: mfaCode.value, secret: otp.secret }) .then(() => {