From d100edb75b50dd0efb1f45240bfad642f0599b85 Mon Sep 17 00:00:00 2001 From: zhengkunwang <31820853+zhengkunwang223@users.noreply.github.com> Date: Tue, 13 Aug 2024 15:28:39 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E4=BC=98=E5=8C=96=E5=BA=94=E7=94=A8?= =?UTF-8?q?=E5=AE=89=E8=A3=85=E5=92=8C=E5=88=A0=E9=99=A4=E9=80=BB=E8=BE=91?= =?UTF-8?q?=20(#6112)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- agent/app/repo/app_install.go | 2 +- agent/app/service/app_install.go | 4 +- agent/app/service/app_utils.go | 41 ++++++++++--------- agent/constant/app.go | 29 ++++++------- agent/utils/docker/compose.go | 6 ++- agent/utils/files/utils.go | 23 +++++++---- frontend/src/components/status/index.vue | 1 + frontend/src/lang/modules/en.ts | 1 + frontend/src/lang/modules/tw.ts | 1 + frontend/src/lang/modules/zh.ts | 1 + .../src/views/app-store/installed/index.vue | 34 ++++++++++++--- 11 files changed, 91 insertions(+), 52 deletions(-) diff --git a/agent/app/repo/app_install.go b/agent/app/repo/app_install.go index 1b3c3ae68..46596e9cd 100644 --- a/agent/app/repo/app_install.go +++ b/agent/app/repo/app_install.go @@ -136,7 +136,7 @@ func (a *AppInstallRepo) Create(ctx context.Context, install *model.AppInstall) } func (a *AppInstallRepo) Save(ctx context.Context, install *model.AppInstall) error { - return getTx(ctx).Save(&install).Error + return getTx(ctx).Debug().Omit("App").Save(&install).Error } func (a *AppInstallRepo) DeleteBy(opts ...DBOption) error { diff --git a/agent/app/service/app_install.go b/agent/app/service/app_install.go index c12da544d..e7311dd3f 100644 --- a/agent/app/service/app_install.go +++ b/agent/app/service/app_install.go @@ -446,7 +446,7 @@ func (a *AppInstallService) SyncAll(systemInit bool) error { return err } for _, i := range allList { - if i.Status == constant.Installing || i.Status == constant.Upgrading || i.Status == constant.Rebuilding { + if i.Status == constant.Installing || i.Status == constant.Upgrading || i.Status == constant.Rebuilding || i.Status == constant.Uninstalling { if systemInit { i.Status = constant.Error i.Message = "1Panel restart causes the task to terminate" @@ -755,7 +755,7 @@ func (a *AppInstallService) GetParams(id uint) (*response.AppConfig, error) { } func syncAppInstallStatus(appInstall *model.AppInstall, force bool) error { - if appInstall.Status == constant.Installing || appInstall.Status == constant.Rebuilding || appInstall.Status == constant.Upgrading { + if appInstall.Status == constant.Installing || appInstall.Status == constant.Rebuilding || appInstall.Status == constant.Upgrading || appInstall.Status == constant.Uninstalling { return nil } cli, err := docker.NewClient() diff --git a/agent/app/service/app_utils.go b/agent/app/service/app_utils.go index bd2ccf222..d8a001c8d 100644 --- a/agent/app/service/app_utils.go +++ b/agent/app/service/app_utils.go @@ -330,6 +330,8 @@ func deleteAppInstall(deleteReq request.AppInstallDelete) error { } uninstall := func(t *task.Task) error { + install.Status = constant.Uninstalling + _ = appInstallRepo.Save(context.Background(), &install) dir, _ := os.Stat(appDir) if dir != nil { logStr := i18n.GetMsgByKey("Stop") + i18n.GetMsgByKey("App") @@ -346,7 +348,15 @@ func deleteAppInstall(deleteReq request.AppInstallDelete) error { } if deleteReq.DeleteImage { delImageStr := i18n.GetMsgByKey("TaskDelete") + i18n.GetMsgByKey("Image") - images, _ := getImages(install) + projectName := strings.ToLower(install.Name) + content, err := op.GetContent(install.GetEnvPath()) + if err != nil { + return err + } + images, err := composeV2.GetDockerComposeImages(projectName, content, []byte(install.DockerCompose)) + if err != nil { + return err + } client, err := docker.NewClient() if err != nil { return err @@ -440,7 +450,12 @@ func deleteAppInstall(deleteReq request.AppInstallDelete) error { return nil } uninstallTask.AddSubTask(task.GetTaskName(install.Name, task.TaskUninstall, task.TaskScopeApp), uninstall, nil) - go uninstallTask.Execute() + go func() { + if err := uninstallTask.Execute(); err != nil { + install.Status = constant.Error + _ = appInstallRepo.Save(context.Background(), &install) + } + }() return nil } @@ -746,22 +761,6 @@ func getContainerNames(install model.AppInstall) ([]string, error) { return containerNames, nil } -func getImages(install model.AppInstall) ([]string, error) { - envStr, err := coverEnvJsonToStr(install.Env) - if err != nil { - return nil, err - } - project, err := composeV2.GetComposeProject(install.Name, install.GetPath(), []byte(install.DockerCompose), []byte(envStr), true) - if err != nil { - return nil, err - } - var images []string - for _, service := range project.AllServices() { - images = append(images, service.Image) - } - return images, nil -} - func coverEnvJsonToStr(envJson string) (string, error) { envMap := make(map[string]interface{}) _ = json.Unmarshal([]byte(envJson), &envMap) @@ -1254,10 +1253,11 @@ func handleErr(install model.AppInstall, err error, out string) error { func doNotNeedSync(installed model.AppInstall) bool { return installed.Status == constant.Installing || installed.Status == constant.Rebuilding || installed.Status == constant.Upgrading || - installed.Status == constant.Syncing + installed.Status == constant.Syncing || installed.Status == constant.Uninstalling } func synAppInstall(containers map[string]types.Container, appInstall *model.AppInstall, force bool) { + oldStatus := appInstall.Status containerNames := strings.Split(appInstall.ContainerName, ",") if len(containers) == 0 { if appInstall.Status == constant.UpErr && !force { @@ -1294,6 +1294,9 @@ func synAppInstall(containers map[string]types.Container, appInstall *model.AppI appInstall.Status = constant.Stopped case runningCount == total: appInstall.Status = constant.Running + if oldStatus == constant.Running { + return + } case pausedCount == total: appInstall.Status = constant.Paused case len(notFoundNames) == total: diff --git a/agent/constant/app.go b/agent/constant/app.go index 44f696cc2..73039cd12 100644 --- a/agent/constant/app.go +++ b/agent/constant/app.go @@ -1,20 +1,21 @@ package constant const ( - Running = "Running" - UnHealthy = "UnHealthy" - Error = "Error" - Stopped = "Stopped" - Installing = "Installing" - DownloadErr = "DownloadErr" - Upgrading = "Upgrading" - UpgradeErr = "UpgradeErr" - Rebuilding = "Rebuilding" - Syncing = "Syncing" - SyncSuccess = "SyncSuccess" - Paused = "Paused" - UpErr = "UpErr" - InstallErr = "InstallErr" + Running = "Running" + UnHealthy = "UnHealthy" + Error = "Error" + Stopped = "Stopped" + Installing = "Installing" + DownloadErr = "DownloadErr" + Upgrading = "Upgrading" + UpgradeErr = "UpgradeErr" + Rebuilding = "Rebuilding" + Syncing = "Syncing" + SyncSuccess = "SyncSuccess" + Paused = "Paused" + UpErr = "UpErr" + InstallErr = "InstallErr" + Uninstalling = "Uninstalling" ContainerPrefix = "1Panel-" diff --git a/agent/utils/docker/compose.go b/agent/utils/docker/compose.go index 6b78c59a0..988ca46a8 100644 --- a/agent/utils/docker/compose.go +++ b/agent/utils/docker/compose.go @@ -59,6 +59,7 @@ func GetDockerComposeImages(projectName string, env, yml []byte) ([]string, erro var ( configFiles []types.ConfigFile images []string + imagesMap = make(map[string]struct{}) ) configFiles = append(configFiles, types.ConfigFile{ Filename: "docker-compose.yml", @@ -81,7 +82,10 @@ func GetDockerComposeImages(projectName string, env, yml []byte) ([]string, erro return nil, err } for _, service := range project.AllServices() { - images = append(images, service.Image) + imagesMap[service.Image] = struct{}{} + } + for image := range imagesMap { + images = append(images, image) } return images, nil } diff --git a/agent/utils/files/utils.go b/agent/utils/files/utils.go index 76ba78156..5347ce964 100644 --- a/agent/utils/files/utils.go +++ b/agent/utils/files/utils.go @@ -72,16 +72,21 @@ func countLines(path string) (int, error) { return 0, err } defer file.Close() - - scanner := bufio.NewScanner(file) - lineCount := 0 - for scanner.Scan() { - lineCount++ + reader := bufio.NewReader(file) + count := 0 + for { + _, err := reader.ReadString('\n') + if err != nil { + if err == io.EOF { + if count > 0 { + count++ + } + return count, nil + } + return count, err + } + count++ } - if err := scanner.Err(); err != nil { - return 0, err - } - return lineCount, nil } func ReadFileByLine(filename string, page, pageSize int, latest bool) (lines []string, isEndOfFile bool, total int, err error) { diff --git a/frontend/src/components/status/index.vue b/frontend/src/components/status/index.vue index b130ff31c..5e01dfd6f 100644 --- a/frontend/src/components/status/index.vue +++ b/frontend/src/components/status/index.vue @@ -51,6 +51,7 @@ const loadingStatus = [ 'starting', 'removing', 'applying', + 'uninstalling', ]; const loadingIcon = (status: string): boolean => { diff --git a/frontend/src/lang/modules/en.ts b/frontend/src/lang/modules/en.ts index 57476e15e..07aefb7e7 100644 --- a/frontend/src/lang/modules/en.ts +++ b/frontend/src/lang/modules/en.ts @@ -280,6 +280,7 @@ const message = { applyerror: 'Failure', syncerr: 'Error', uperr: 'Error', + uninstalling: 'Uninstalling', }, units: { second: 'Second', diff --git a/frontend/src/lang/modules/tw.ts b/frontend/src/lang/modules/tw.ts index d01782619..df5ab6850 100644 --- a/frontend/src/lang/modules/tw.ts +++ b/frontend/src/lang/modules/tw.ts @@ -275,6 +275,7 @@ const message = { applyerror: '失敗', syncerr: '失敗', uperr: '失败', + uninstalling: '卸載中', }, units: { second: '秒', diff --git a/frontend/src/lang/modules/zh.ts b/frontend/src/lang/modules/zh.ts index 393128321..5d037213b 100644 --- a/frontend/src/lang/modules/zh.ts +++ b/frontend/src/lang/modules/zh.ts @@ -275,6 +275,7 @@ const message = { applyerror: '失败', syncerr: '失败', uperr: '失败', + uninstalling: '卸载中', }, units: { second: '秒', diff --git a/frontend/src/views/app-store/installed/index.vue b/frontend/src/views/app-store/installed/index.vue index ffe112a92..548c059d3 100644 --- a/frontend/src/views/app-store/installed/index.vue +++ b/frontend/src/views/app-store/installed/index.vue @@ -520,7 +520,12 @@ const buttons = [ openOperate(row, 'sync'); }, disabled: (row: any) => { - return row.status === 'DownloadErr' || row.status === 'Upgrading' || row.status === 'Rebuilding'; + return ( + row.status === 'DownloadErr' || + row.status === 'Upgrading' || + row.status === 'Rebuilding' || + row.status === 'Uninstalling' + ); }, }, { @@ -529,7 +534,12 @@ const buttons = [ openOperate(row, 'rebuild'); }, disabled: (row: any) => { - return row.status === 'DownloadErr' || row.status === 'Upgrading' || row.status === 'Rebuilding'; + return ( + row.status === 'DownloadErr' || + row.status === 'Upgrading' || + row.status === 'Rebuilding' || + row.status === 'Uninstalling' + ); }, }, { @@ -538,7 +548,12 @@ const buttons = [ openOperate(row, 'restart'); }, disabled: (row: any) => { - return row.status === 'DownloadErr' || row.status === 'Upgrading' || row.status === 'Rebuilding'; + return ( + row.status === 'DownloadErr' || + row.status === 'Upgrading' || + row.status === 'Rebuilding' || + row.status === 'Uninstalling' + ); }, }, { @@ -552,7 +567,8 @@ const buttons = [ row.status === 'Error' || row.status === 'DownloadErr' || row.status === 'Upgrading' || - row.status === 'Rebuilding' + row.status === 'Rebuilding' || + row.status === 'Uninstalling' ); }, }, @@ -566,7 +582,8 @@ const buttons = [ row.status !== 'Running' || row.status === 'DownloadErr' || row.status === 'Upgrading' || - row.status === 'Rebuilding' + row.status === 'Rebuilding' || + row.status === 'Uninstalling' ); }, }, @@ -582,7 +599,12 @@ const buttons = [ openParam(row); }, disabled: (row: any) => { - return row.status === 'DownloadErr' || row.status === 'Upgrading' || row.status === 'Rebuilding'; + return ( + row.status === 'DownloadErr' || + row.status === 'Upgrading' || + row.status === 'Rebuilding' || + row.status === 'Uninstalling' + ); }, }, ];