feat: 计划任务支持自定义日志保留份数 (#548)

This commit is contained in:
ssongliu 2023-04-09 22:22:13 +08:00 committed by GitHub
parent 24246da71c
commit 18b4c98daa
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 44 additions and 82 deletions

View File

@ -80,21 +80,15 @@ func (u *CronjobService) SearchRecords(search dto.SearchRecord) (int64, interfac
}
func (u *CronjobService) CleanRecord(id uint) error {
_, records, err := cronjobRepo.PageRecords(1, 7, cronjobRepo.WithByJobID(int(id)), commonRepo.WithOrderBy("created_at desc"))
if err != nil {
return err
}
if len(records) < 7 {
return nil
}
delRecords, err := cronjobRepo.ListRecord(cronjobRepo.WithByJobID(int(id)), cronjobRepo.WithByRecordDropID(int(records[6].ID)))
delRecords, err := cronjobRepo.ListRecord(cronjobRepo.WithByJobID(int(id)))
if err != nil {
return err
}
for _, del := range delRecords {
_ = os.RemoveAll(del.File)
_ = os.RemoveAll(del.Records)
}
if err := cronjobRepo.DeleteRecord(cronjobRepo.WithByJobID(int(id)), cronjobRepo.WithByRecordDropID(int(records[6].ID))); err != nil {
if err := cronjobRepo.DeleteRecord(cronjobRepo.WithByJobID(int(id))); err != nil {
return err
}
return nil

View File

@ -1,7 +1,6 @@
package service
import (
"context"
"fmt"
"os"
"strings"
@ -23,6 +22,7 @@ func (u *CronjobService) HandleJob(cronjob *model.Cronjob) {
err error
)
record := cronjobRepo.StartRecords(cronjob.ID, cronjob.KeepLocal, "")
logDir := fmt.Sprintf("%s/1panel/task/%s/%s", global.CONF.System.BaseDir, cronjob.Type, cronjob.Name)
go func() {
switch cronjob.Type {
case "shell":
@ -34,6 +34,7 @@ func (u *CronjobService) HandleJob(cronjob *model.Cronjob) {
err = errExec
}
message = []byte(stdout)
u.HandleRmExpired("LOCAL", logDir, cronjob, nil)
case "website":
record.File, err = u.HandleBackup(cronjob, record.StartTime)
case "database":
@ -52,6 +53,7 @@ func (u *CronjobService) HandleJob(cronjob *model.Cronjob) {
err = errCurl
}
message = []byte(stdout)
u.HandleRmExpired("LOCAL", logDir, cronjob, nil)
}
if err != nil {
cronjobRepo.EndRecords(record, constant.StatusFailed, err.Error(), string(message))
@ -169,39 +171,13 @@ func (u *CronjobService) HandleRmExpired(backType, backupDir string, cronjob *mo
}
return
}
files, err := os.ReadDir(backupDir)
if err != nil {
global.LOG.Errorf("read dir %s failed, err: %v", backupDir, err)
return
}
if len(files) == 0 {
return
}
prefix := ""
switch cronjob.Type {
case "database":
prefix = "db_"
case "website":
prefix = "website_"
case "directory":
prefix = "directory_"
}
dbCopies := uint64(0)
for i := len(files) - 1; i >= 0; i-- {
if strings.HasPrefix(files[i].Name(), prefix) {
dbCopies++
if dbCopies > cronjob.RetainCopies {
_ = os.Remove(backupDir + "/" + files[i].Name())
_ = backupRepo.DeleteRecord(context.Background(), backupRepo.WithByFileName(files[i].Name()))
}
}
}
records, _ := cronjobRepo.ListRecord(cronjobRepo.WithByJobID(int(cronjob.ID)))
records, _ := cronjobRepo.ListRecord(cronjobRepo.WithByJobID(int(cronjob.ID)), commonRepo.WithOrderBy("created_at desc"))
if len(records) > int(cronjob.RetainCopies) {
for i := int(cronjob.RetainCopies); i < len(records); i++ {
_ = cronjobRepo.DeleteRecord(cronjobRepo.WithByJobID(int(records[i].ID)))
_ = cronjobRepo.DeleteRecord(commonRepo.WithByID(uint(records[i].ID)))
_ = os.Remove(records[i].File)
_ = os.Remove(records[i].Records)
}
}
}
@ -292,7 +268,8 @@ func (u *CronjobService) handleDatabase(cronjob model.Cronjob, app *repo.RootInf
record.Source = backup.Type
record.FileDir = itemFileDir
}
if err := saveBackupRecord(record); err != nil {
if err := backupRepo.CreateRecord(&record); err != nil {
global.LOG.Errorf("save backup record failed, err: %v", err)
return err
}
if backup.Type == "LOCAL" {
@ -356,7 +333,8 @@ func (u *CronjobService) handleWebsite(cronjob model.Cronjob, backup model.Backu
return err
}
record.Name = website.PrimaryDomain
if err := saveBackupRecord(record); err != nil {
if err := backupRepo.CreateRecord(&record); err != nil {
global.LOG.Errorf("save backup record failed, err: %v", err)
return err
}
if backup.Type == "LOCAL" {
@ -382,11 +360,3 @@ func (u *CronjobService) handleWebsite(cronjob model.Cronjob, backup model.Backu
}
return nil
}
func saveBackupRecord(record model.BackupRecord) error {
if err := backupRepo.CreateRecord(&record); err != nil {
global.LOG.Errorf("save backup record failed, err: %v", err)
return err
}
return nil
}

View File

@ -585,7 +585,7 @@ const message = {
cronSpec: 'Lifecycle',
cronSpecHelper: 'Enter the correct execution period',
cleanHelper:
'This operation will retain the latest seven task execution records and log files. Do you want to continue?',
'This operation records all job execution records, backup files, and log files. Do you want to continue?',
directory: 'Backup directory',
sourceDir: 'Backup directory',
allOptionHelper:
@ -595,6 +595,7 @@ const message = {
url: 'URL Address',
target: 'Target',
retainCopies: 'Retain copies',
retainCopiesHelper: 'Number of copies of execution records, log files, and backup files',
cronSpecRule: 'Please enter a correct lifecycle',
perMonth: 'Every monthly',
perWeek: 'Every week',

View File

@ -588,7 +588,7 @@ const message = {
taskName: '任务名称',
cronSpec: '执行周期',
cronSpecHelper: '请输入正确的执行周期',
cleanHelper: '该操作将保留最新的 7 份任务执行记录和日志文件是否继续',
cleanHelper: '该操作将所有任务执行记录备份文件和日志文件是否继续',
directory: '备份目录',
sourceDir: '备份目录',
allOptionHelper: '当前计划任务为备份所有 {0}暂不支持直接下载可在 {0} 备份列表中查看',
@ -597,6 +597,7 @@ const message = {
url: 'URL 地址',
target: '备份到',
retainCopies: '保留份数',
retainCopiesHelper: '执行记录日志文件备份文件保留份数',
cronSpecRule: '请输入正确的执行周期',
perMonth: '每月',
perWeek: '每周',

View File

@ -91,11 +91,7 @@
{{ $t('cronjob.handle') }}
</template>
</el-table-column>
<el-table-column :label="$t('cronjob.retainCopies')" :min-width="90" prop="retainCopies">
<template #default="{ row }">
{{ loadCopies(row) }}
</template>
</el-table-column>
<el-table-column :label="$t('cronjob.retainCopies')" :min-width="90" prop="retainCopies" />
<el-table-column :label="$t('cronjob.lastRecrodTime')" :min-width="120" prop="lastRecrodTime">
<template #default="{ row }">
@ -246,14 +242,6 @@ const onHandle = async (row: Cronjob.CronjobInfo) => {
});
};
const loadCopies = (item) => {
if (item.type === 'shell' || item.type === 'curl') {
return '-';
} else {
return item.retainCopies + '';
}
};
const loadDetail = (row: any) => {
isRecordShow.value = true;
let params = {

View File

@ -129,17 +129,19 @@
{{ $t('cronjob.saveLocal') }}
</el-checkbox>
</el-form-item>
<el-form-item :label="$t('cronjob.retainCopies')" prop="retainCopies">
<el-input-number
:min="1"
:max="30"
step-strictly
:step="1"
v-model.number="dialogData.rowData!.retainCopies"
></el-input-number>
</el-form-item>
</div>
<el-form-item :label="$t('cronjob.retainCopies')" prop="retainCopies">
<el-input-number
:min="1"
:max="300"
step-strictly
:step="1"
v-model.number="dialogData.rowData!.retainCopies"
></el-input-number>
<span class="input-help">{{ $t('cronjob.retainCopiesHelper') }}</span>
</el-form-item>
<el-form-item v-if="dialogData.rowData!.type === 'curl'" :label="$t('cronjob.url')" prop="url">
<el-input style="width: 100%" clearable v-model.trim="dialogData.rowData!.url" />
</el-form-item>

View File

@ -70,7 +70,7 @@
>
{{ $t('commons.button.enable') }}
</el-button>
<el-button type="primary" :disabled="records.length <= 7" @click="cleanRecord()" link>
<el-button type="primary" @click="cleanRecord()" link>
{{ $t('commons.button.clean') }}
</el-button>
</span>
@ -130,7 +130,7 @@
</el-card>
</el-col>
<el-col :span="16">
<el-form label-position="top">
<el-form label-position="top" :v-key="refresh">
<el-row type="flex" justify="center">
<el-form-item class="descriptionWide" v-if="isBackup()">
<template #label>
@ -301,6 +301,7 @@ import { oneDark } from '@codemirror/theme-one-dark';
import { MsgError, MsgInfo, MsgSuccess } from '@/utils/message';
const loading = ref();
const refresh = ref(false);
const hasRecords = ref();
let timer: NodeJS.Timer | null = null;
@ -324,7 +325,7 @@ const acceptParams = async (params: DialogProps): Promise<void> => {
search(true);
timer = setInterval(() => {
onRefresh();
}, 1000 * 10);
}, 1000 * 5);
};
const shortcuts = [
@ -402,10 +403,7 @@ const onHandle = async (row: Cronjob.CronjobInfo) => {
.then(() => {
loading.value = false;
MsgSuccess(i18n.global.t('commons.msg.operationSuccess'));
searchInfo.pageSize = searchInfo.pageSize * searchInfo.page;
searchInfo.page = 1;
records.value = [];
search(false);
onRefresh();
})
.catch(() => {
loading.value = false;
@ -483,7 +481,15 @@ const onRefresh = async () => {
status: searchInfo.status,
};
const res = await searchRecords(params);
records.value = res.data.items || [];
if (res.data.items) {
records.value = res.data.items;
hasRecords.value = true;
currentRecord.value = records.value[0];
} else {
records.value = [];
hasRecords.value = false;
refresh.value = !refresh.value;
}
};
const onDownload = async (record: any, backupID: number) => {