diff --git a/cmd/climc/shell/dbinstances.go b/cmd/climc/shell/dbinstances.go index 3d8832b16b..aeb405015e 100644 --- a/cmd/climc/shell/dbinstances.go +++ b/cmd/climc/shell/dbinstances.go @@ -231,8 +231,17 @@ func init() { return nil }) - R(&DBInstanceIdOptions{}, "dbinstance-delete", "Delete DB instance", func(s *mcclient.ClientSession, opts *DBInstanceIdOptions) error { - result, err := modules.DBInstance.Delete(s, opts.ID, nil) + type DBInstanceDeleteOptions struct { + ID string `help:"DBInstance Id or name"` + KeepBackup bool `help:"Keep dbinstance manual backup after delete dbinstance"` + } + + R(&DBInstanceDeleteOptions{}, "dbinstance-delete", "Delete DB instance", func(s *mcclient.ClientSession, opts *DBInstanceDeleteOptions) error { + params := jsonutils.NewDict() + if opts.KeepBackup { + params.Add(jsonutils.JSONTrue, "keep_backup") + } + result, err := modules.DBInstance.Delete(s, opts.ID, params) if err != nil { return err } diff --git a/docs/dbinstance/dbinstance.yaml b/docs/dbinstance/dbinstance.yaml index 841310c88b..b617559547 100644 --- a/docs/dbinstance/dbinstance.yaml +++ b/docs/dbinstance/dbinstance.yaml @@ -14,10 +14,11 @@ delete: summary: 删除指定RDS实例 parameters: - $ref: '../parameters/dbinstance.yaml#/dbinstanceId' + - $ref: '../parameters/dbinstance.yaml#/keep_backup' responses: 200: description: 被删除RDS实例的信息 schema: $ref: '../schemas/dbinstance.yaml#/DBInstanceResponse' tags: - - dbinstance \ No newline at end of file + - dbinstance diff --git a/docs/parameters/dbinstance.yaml b/docs/parameters/dbinstance.yaml index 285ee632b5..01b601cb4e 100644 --- a/docs/parameters/dbinstance.yaml +++ b/docs/parameters/dbinstance.yaml @@ -39,4 +39,11 @@ dbinstance: name: dbinstance in: query type: string - description: 根据RDS实例名称或ID过滤资源 \ No newline at end of file + description: 根据RDS实例名称或ID过滤资源 + +keep_backup: + name: keep_backup + in: body + type: boolean + default: false + description: 删除RDS实例时保留手动备份 diff --git a/pkg/compute/models/dbinstances.go b/pkg/compute/models/dbinstances.go index 2270c55964..0be2b42ee5 100644 --- a/pkg/compute/models/dbinstances.go +++ b/pkg/compute/models/dbinstances.go @@ -773,7 +773,9 @@ func (manager *SDBInstanceManager) getDBInstancesByProviderId(providerId string) } func (self *SDBInstance) CustomizeDelete(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, data jsonutils.JSONObject) error { - return self.StartDBInstanceDeleteTask(ctx, userCred, nil, "") + params := jsonutils.NewDict() + params.Set("keep_backup", jsonutils.NewBool(jsonutils.QueryBoolean(data, "keep_backup", false))) + return self.StartDBInstanceDeleteTask(ctx, userCred, params, "") } func (self *SDBInstance) Delete(ctx context.Context, userCred mcclient.TokenCredential) error { @@ -923,14 +925,23 @@ func (self *SDBInstance) GetDBInstancePrivilege(account, database string) (*SDBI return privilege, nil } -func (self *SDBInstance) GetDBInstanceBackups() ([]SDBInstanceBackup, error) { +func (self *SDBInstance) GetDBInstanceBackupByMode(mode string) ([]SDBInstanceBackup, error) { backups := []SDBInstanceBackup{} q := DBInstanceBackupManager.Query().Equals("dbinstance_id", self.Id) + switch mode { + case api.BACKUP_MODE_MANUAL, api.BACKUP_MODE_AUTOMATED: + q = q.Equals("backup_mode", mode) + } err := db.FetchModelObjects(DBInstanceBackupManager, q, &backups) if err != nil { return nil, errors.Wrap(err, "GetDBInstanceBackups.FetchModelObjects") } return backups, nil + +} + +func (self *SDBInstance) GetDBInstanceBackups() ([]SDBInstanceBackup, error) { + return self.GetDBInstanceBackupByMode("") } func (self *SDBInstance) GetDBDatabases() ([]SDBInstanceDatabase, error) { diff --git a/pkg/compute/models/purge.go b/pkg/compute/models/purge.go index c7cbb932cf..902ae34402 100644 --- a/pkg/compute/models/purge.go +++ b/pkg/compute/models/purge.go @@ -1354,17 +1354,15 @@ func (instance *SDBInstance) purgeNetwork(ctx context.Context, userCred mcclient return nil } -func (instance *SDBInstance) purgeBackups(ctx context.Context, userCred mcclient.TokenCredential) error { - backups, err := instance.GetDBInstanceBackups() +func (instance *SDBInstance) PurgeBackups(ctx context.Context, userCred mcclient.TokenCredential, mode string) error { + backups, err := instance.GetDBInstanceBackupByMode(mode) if err != nil { return errors.Wrap(err, "instance.GetDBInstanceBackups") } for _, backup := range backups { - if backup.BackupMode == api.BACKUP_MODE_AUTOMATED { - err = backup.purge(ctx, userCred) - if err != nil { - return errors.Wrapf(err, "backup.purge %s(%s)", backup.Name, backup.Id) - } + err = backup.purge(ctx, userCred) + if err != nil { + return errors.Wrapf(err, "backup.purge %s(%s)", backup.Name, backup.Id) } } return nil @@ -1394,7 +1392,7 @@ func (instance *SDBInstance) Purge(ctx context.Context, userCred mcclient.TokenC return err } - err = instance.purgeBackups(ctx, userCred) + err = instance.PurgeBackups(ctx, userCred, api.BACKUP_MODE_AUTOMATED) if err != nil { return errors.Wrap(err, "instance.purgeBackups") } diff --git a/pkg/compute/regiondrivers/huawei.go b/pkg/compute/regiondrivers/huawei.go index c48acd1ad1..f36ed93f6c 100644 --- a/pkg/compute/regiondrivers/huawei.go +++ b/pkg/compute/regiondrivers/huawei.go @@ -2225,7 +2225,7 @@ func (self *SHuaWeiRegionDriver) ValidateDBInstanceAccountPrivilege(ctx context. if account == "root" { return httperrors.NewInputParameterError("No need to grant or revoke privilege for admin account") } - if utils.IsInStringArray(privilege, []string{api.DATABASE_PRIVILEGE_RW, api.DATABASE_PRIVILEGE_R}) { + if !utils.IsInStringArray(privilege, []string{api.DATABASE_PRIVILEGE_RW, api.DATABASE_PRIVILEGE_R}) { return httperrors.NewInputParameterError("Unknown privilege %s", privilege) } return nil diff --git a/pkg/compute/tasks/dbinstance_delete_task.go b/pkg/compute/tasks/dbinstance_delete_task.go index 46d4fa0f46..1859f76224 100644 --- a/pkg/compute/tasks/dbinstance_delete_task.go +++ b/pkg/compute/tasks/dbinstance_delete_task.go @@ -45,47 +45,7 @@ func (self *DBInstanceDeleteTask) taskFailed(ctx context.Context, dbinstance *mo func (self *DBInstanceDeleteTask) OnInit(ctx context.Context, obj db.IStandaloneModel, data jsonutils.JSONObject) { dbinstance := obj.(*models.SDBInstance) - - keepBackup := false - if !dbinstance.GetRegion().GetDriver().IsSupportKeepDBInstanceManualBackup() { - keepBackup = jsonutils.QueryBoolean(self.Params, "keep_backup", false) - } - - if !keepBackup { - self.SetStage("OnBackupDeleteComplete", nil) - self.OnBackupDeleteComplete(ctx, dbinstance, nil) - } else { - self.DeleteDBInstance(ctx, dbinstance) - } -} - -func (self *DBInstanceDeleteTask) OnBackupDeleteComplete(ctx context.Context, instance *models.SDBInstance, data jsonutils.JSONObject) { - _backups, err := instance.GetDBInstanceBackups() - if err != nil { - self.taskFailed(ctx, instance, errors.Wrap(err, "instance.GetDBInstanceBackups")) - return - } - backups := []models.SDBInstanceBackup{} - for _, backup := range _backups { - if backup.BackupMode == api.BACKUP_MODE_MANUAL { - backups = append(backups, backup) - } - } - if len(backups) == 0 { - self.DeleteDBInstance(ctx, instance) - return - } - - backups[0].StartDBInstanceBackupDeleteTask(ctx, self.UserCred, self.GetTaskId()) -} - -func (self *DBInstanceDeleteTask) DeleteDBInstanceComplete(ctx context.Context, dbinstance *models.SDBInstance) { - err := dbinstance.Purge(ctx, self.UserCred) - if err != nil { - self.taskFailed(ctx, dbinstance, errors.Wrap(err, "dbinstance.Purge")) - return - } - self.SetStageComplete(ctx, nil) + self.DeleteDBInstance(ctx, dbinstance) } func (self *DBInstanceDeleteTask) DeleteDBInstance(ctx context.Context, dbinstance *models.SDBInstance) { @@ -109,3 +69,37 @@ func (self *DBInstanceDeleteTask) DeleteDBInstance(ctx context.Context, dbinstan self.DeleteDBInstanceComplete(ctx, dbinstance) } + +func (self *DBInstanceDeleteTask) DeleteDBInstanceComplete(ctx context.Context, dbinstance *models.SDBInstance) { + if !dbinstance.GetRegion().GetDriver().IsSupportKeepDBInstanceManualBackup() || jsonutils.QueryBoolean(self.Params, "purge", false) { + err := dbinstance.PurgeBackups(ctx, self.UserCred, api.BACKUP_MODE_MANUAL) + if err != nil { + self.taskFailed(ctx, dbinstance, errors.Wrap(err, "dbinstance.PurgeManualBackups")) + return + } + err = dbinstance.Purge(ctx, self.UserCred) + if err != nil { + self.taskFailed(ctx, dbinstance, errors.Wrap(err, "dbinstance.Purge")) + return + } + self.SetStageComplete(ctx, nil) + return + } + + self.DeleteBackups(ctx, dbinstance, nil) +} + +func (self *DBInstanceDeleteTask) DeleteBackups(ctx context.Context, instance *models.SDBInstance, data jsonutils.JSONObject) { + if !jsonutils.QueryBoolean(self.Params, "keep_backup", false) { + backups, _ := instance.GetDBInstanceBackupByMode(api.BACKUP_MODE_MANUAL) + for i := range backups { + backups[i].StartDBInstanceBackupDeleteTask(ctx, self.UserCred, "") + } + } + err := instance.Purge(ctx, self.UserCred) + if err != nil { + self.taskFailed(ctx, instance, errors.Wrap(err, "instance.Purge")) + return + } + self.SetStageComplete(ctx, nil) +}