Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[CONTROLLER/DB] optimizes deleting org performence #6706

Closed
wants to merge 1 commit into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 8 additions & 3 deletions server/controller/db/mysql/migrator/common/migrator.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,24 +58,28 @@ func (dc *DBConfig) SetConfig(c config.MySqlConfig) {
}

func LogDBName(databaseName string, format string, a ...any) string {
return fmt.Sprintf("db: %s, ", databaseName) + fmt.Sprintf(format, a...)
return fmt.Sprintf("[DBName-%s] ", databaseName) + fmt.Sprintf(format, a...)
}

func DropDatabase(dc *DBConfig) error {
log.Infof(LogDBName(dc.Config.Database, "drop database"))
defer log.Infof(LogDBName(dc.Config.Database, "dropped database"))

var databaseName string
log.Infof(LogDBName(dc.Config.Database, "drop database, check if database exists"))
dc.DB.Raw(fmt.Sprintf("SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA WHERE SCHEMA_NAME='%s'", dc.Config.Database)).Scan(&databaseName)
if databaseName == dc.Config.Database {
log.Infof(LogDBName(dc.Config.Database, "drop database, database exists"))
return dc.DB.Exec(fmt.Sprintf("DROP DATABASE %s", dc.Config.Database)).Error
} else {
log.Infof(LogDBName(dc.Config.Database, "database doesn't exist"))
log.Infof(LogDBName(dc.Config.Database, "drop database, database doesn't exist"))
return nil
}
}

func CreateDatabase(dc *DBConfig) error {
log.Infof(LogDBName(dc.Config.Database, "create database"))
log.Infof("%#v", dc.DB)
defer log.Infof(LogDBName(dc.Config.Database, "created database"))
return dc.DB.Exec(fmt.Sprintf("CREATE DATABASE %s", dc.Config.Database)).Error
}

Expand Down Expand Up @@ -118,6 +122,7 @@ func initCEORGTables(dc *DBConfig) error {
return err
}
err = dc.DB.Exec(string(initSQL)).Error
log.Info(LogDBName(dc.Config.Database, "read CE org file successfully"))
if err != nil {
log.Error(LogDBName(dc.Config.Database, "failed to initialize CE org tables: %s", err.Error()))
return err
Expand Down
6 changes: 6 additions & 0 deletions server/controller/db/mysql/migrator/migrator.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,31 +84,37 @@ func upgradeDatabase(cfg config.MySqlConfig, run bool) error {
}

func CreateDatabase(cfg config.MySqlConfig) (databaseExisted bool, err error) {
log.Infof(common.LogDBName(cfg.Database, "create database, get db session without name"))
db, err := common.GetSessionWithoutName(cfg)
if err != nil {
return
}
log.Infof(common.LogDBName(cfg.Database, "create database, got db session without name"))
dc := common.NewDBConfig(db, cfg)
databaseExisted, err = common.CreateDatabaseIfNotExists(dc)
if err != nil {
log.Error(common.LogDBName(cfg.Database, "database is not ready: %v", err))
return
}
if !databaseExisted {
log.Infof(common.LogDBName(cfg.Database, "create database, get db session with name %s", cfg.Database))
db, err = common.GetSessionWithName(cfg)
if err != nil {
return
}
log.Infof(common.LogDBName(cfg.Database, "create database, got db session with name %s", cfg.Database))
dc.SetDB(db)
err = table.DropDatabaseIfInitTablesFailed(dc)
}
return
}

func DropDatabase(cfg config.MySqlConfig) error {
log.Infof("drop database, get db session with name %s", cfg.Database)
db, err := common.GetSessionWithName(cfg)
if err != nil {
return err
}
log.Infof("drop database, got db session with name %s", cfg.Database)
return common.DropDatabase(common.NewDBConfig(db, cfg))
}
108 changes: 54 additions & 54 deletions server/controller/db/mysql/org.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,12 @@ package mysql

import (
"fmt"
"reflect"
// "reflect"
"strings"

"github.com/deepflowio/deepflow/server/controller/db/mysql/common"
"gorm.io/gorm"
"gorm.io/gorm/clause"
// "gorm.io/gorm"
// "gorm.io/gorm/clause"
)

const ORG_TABLE = "org"
Expand Down Expand Up @@ -72,60 +72,60 @@ func SyncDefaultOrgData[T any](data []T) error {
return nil
}

// get fields to update
dataType := reflect.TypeOf(data[0])
var fields []string
for i := 0; i < dataType.NumField(); i++ {
field := dataType.Field(i)
dbTag := field.Tag.Get("gorm")
if dbTag != "" {
columnName := GetColumnNameFromTag(dbTag)
if columnName != "" {
fields = append(fields, columnName)
}
}
}
// // get fields to update
// dataType := reflect.TypeOf(data[0])
// var fields []string
// for i := 0; i < dataType.NumField(); i++ {
// field := dataType.Field(i)
// dbTag := field.Tag.Get("gorm")
// if dbTag != "" {
// columnName := GetColumnNameFromTag(dbTag)
// if columnName != "" {
// fields = append(fields, columnName)
// }
// }
// }

for orgID, db := range dbs.orgIDToDB {
if orgID == DefaultDB.ORGID {
continue
}
// for orgID, db := range dbs.orgIDToDB {
// if orgID == DefaultDB.ORGID {
// continue
// }

err := db.Transaction(func(tx *gorm.DB) error {
// delete
var existingIDs []int
var t T
if err := db.Model(&t).Pluck("id", &existingIDs).Error; err != nil {
return err
}
existingIDMap := make(map[int]bool)
for _, id := range existingIDs {
existingIDMap[id] = true
}
for _, item := range data {
id := reflect.ValueOf(item).FieldByName("ID").Int()
existingIDMap[int(id)] = false
}
for id, exists := range existingIDMap {
if exists {
if err := db.Where("id = ?", id).Delete(&t).Error; err != nil {
return err
}
}
}
// err := db.Transaction(func(tx *gorm.DB) error {
// // delete
// var existingIDs []int
// var t T
// if err := db.Model(&t).Pluck("id", &existingIDs).Error; err != nil {
// return err
// }
// existingIDMap := make(map[int]bool)
// for _, id := range existingIDs {
// existingIDMap[id] = true
// }
// for _, item := range data {
// id := reflect.ValueOf(item).FieldByName("ID").Int()
// existingIDMap[int(id)] = false
// }
// for id, exists := range existingIDMap {
// if exists {
// if err := db.Where("id = ?", id).Delete(&t).Error; err != nil {
// return err
// }
// }
// }

// add or update
if err := db.Clauses(clause.OnConflict{
DoUpdates: clause.AssignmentColumns(fields), // `UpdateAll: true,` can not update time
}).Save(&data).Error; err != nil {
return fmt.Errorf("failed to sync data: %v", err)
}
return nil
})
if err != nil {
log.Errorf("org(id:%d, name:%s) error: %s", db.ORGID, db.Name, err.Error())
}
}
// // add or update
// if err := db.Clauses(clause.OnConflict{
// DoUpdates: clause.AssignmentColumns(fields), // `UpdateAll: true,` can not update time
// }).Save(&data).Error; err != nil {
// return fmt.Errorf("failed to sync data: %v", err)
// }
// return nil
// })
// if err != nil {
// log.Errorf("org(id:%d, name:%s) error: %s", db.ORGID, db.Name, err.Error())
// }
// }
return nil
}

Expand Down
6 changes: 5 additions & 1 deletion server/controller/http/service/org_data.go
Original file line number Diff line number Diff line change
Expand Up @@ -69,11 +69,15 @@ func CreateORGData(dataCreate model.ORGDataCreate, mysqlCfg mysqlcfg.MySqlConfig
}

func DeleteORGData(orgID int, mysqlCfg mysqlcfg.MySqlConfig) (err error) {
log.Infof("delete org (id: %d) data", orgID)
log.Infof("drop org (id: %d) data", orgID)
defer log.Infof("drop org (id: %d) data, dropped", orgID)

cfg := common.ReplaceConfigDatabaseName(mysqlCfg, orgID)
log.Infof("drop org, replaced database name: %s", cfg.Database)
if err = migrator.DropDatabase(cfg); err != nil {
return err
}
log.Infof("drop org, database dropped")
return servercommon.DropOrg(uint16(orgID))
}

Expand Down
Loading