Commit 8a1eb84518538c58903f619d5dc16d9d2ef5d23a

Authored by 王家文
1 parent 69fcd276
Exists in master and in 1 other branch dev-wjw

refactor: orm重构

dto/cardholder-record.go
@@ -2,8 +2,8 @@ package dto @@ -2,8 +2,8 @@ package dto
2 2
3 import ( 3 import (
4 "apigame/service/constd" 4 "apigame/service/constd"
  5 + "apigame/util/utdto"
5 "apigame/util/util-lx/lxtime" 6 "apigame/util/util-lx/lxtime"
6 - "apigame/util/utildto"  
7 ) 7 )
8 8
9 // CardHolderRecordBase 开卡包活动日志公共 9 // CardHolderRecordBase 开卡包活动日志公共
@@ -39,7 +39,7 @@ type CardHolderRecordOpen struct { @@ -39,7 +39,7 @@ type CardHolderRecordOpen struct {
39 } 39 }
40 40
41 func (d *CardHolderRecordOpen) TableName() string { 41 func (d *CardHolderRecordOpen) TableName() string {
42 - return utildto.MYSQL_TABLE_TEMPLATE 42 + return utdto.MYSQL_TABLE_TEMPLATE
43 } 43 }
44 func (d *CardHolderRecordOpen) GetTableName(gameId string) string { 44 func (d *CardHolderRecordOpen) GetTableName(gameId string) string {
45 return constd.MYSQL_TABLE_S_CARDHOLDER_RECORD_OPEN + gameId 45 return constd.MYSQL_TABLE_S_CARDHOLDER_RECORD_OPEN + gameId
@@ -62,7 +62,7 @@ type CardHolderRecordRewardAlbum struct { @@ -62,7 +62,7 @@ type CardHolderRecordRewardAlbum struct {
62 } 62 }
63 63
64 func (d *CardHolderRecordRewardAlbum) TableName() string { 64 func (d *CardHolderRecordRewardAlbum) TableName() string {
65 - return utildto.MYSQL_TABLE_TEMPLATE 65 + return utdto.MYSQL_TABLE_TEMPLATE
66 } 66 }
67 func (d *CardHolderRecordRewardAlbum) GetTableName(gameId string) string { 67 func (d *CardHolderRecordRewardAlbum) GetTableName(gameId string) string {
68 return constd.MYSQL_TABLE_S_CARDHOLDER_RECORD_REWARDALBUM + gameId 68 return constd.MYSQL_TABLE_S_CARDHOLDER_RECORD_REWARDALBUM + gameId
@@ -84,7 +84,7 @@ type CardHolderRecordRewardRound struct { @@ -84,7 +84,7 @@ type CardHolderRecordRewardRound struct {
84 } 84 }
85 85
86 func (d *CardHolderRecordRewardRound) TableName() string { 86 func (d *CardHolderRecordRewardRound) TableName() string {
87 - return utildto.MYSQL_TABLE_TEMPLATE 87 + return utdto.MYSQL_TABLE_TEMPLATE
88 } 88 }
89 func (d *CardHolderRecordRewardRound) GetTableName(gameId string) string { 89 func (d *CardHolderRecordRewardRound) GetTableName(gameId string) string {
90 return constd.MYSQL_TABLE_S_CARDHOLDER_RECORD_REWARDROUND + gameId 90 return constd.MYSQL_TABLE_S_CARDHOLDER_RECORD_REWARDROUND + gameId
dto/cardholder.go
@@ -2,9 +2,9 @@ package dto @@ -2,9 +2,9 @@ package dto
2 2
3 import ( 3 import (
4 "apigame/service/constd" 4 "apigame/service/constd"
  5 + "apigame/util/utdto"
5 "apigame/util/util-lx/lxalilog" 6 "apigame/util/util-lx/lxalilog"
6 "apigame/util/util-lx/lxtime" 7 "apigame/util/util-lx/lxtime"
7 - "apigame/util/utildto"  
8 "encoding/json" 8 "encoding/json"
9 ) 9 )
10 10
@@ -47,7 +47,7 @@ func NewCardHolderDataDetails() *CardHolderDataDetails { @@ -47,7 +47,7 @@ func NewCardHolderDataDetails() *CardHolderDataDetails {
47 } 47 }
48 48
49 func (d *CardHolderData) TableName() string { 49 func (d *CardHolderData) TableName() string {
50 - return utildto.MYSQL_TABLE_TEMPLATE 50 + return utdto.MYSQL_TABLE_TEMPLATE
51 } 51 }
52 52
53 func (d *CardHolderData) GetTableName(gameId string) string { 53 func (d *CardHolderData) GetTableName(gameId string) string {
1 package dto 1 package dto
2 2
3 import ( 3 import (
4 - "apigame/util/utildto" 4 + "apigame/util/utdto"
  5 + "apigame/util/util-lx/lxalilog"
5 "gorm.io/gorm" 6 "gorm.io/gorm"
  7 + "strings"
6 ) 8 )
7 9
8 -func InitTable(db *gorm.DB, tb ITableData, gameId string) { 10 +func InitTable(db *gorm.DB, gameId string, tb IDtoData) {
9 tableName := tb.GetTableName(gameId) 11 tableName := tb.GetTableName(gameId)
10 - utildto.InitTable(db, tb, tableName) 12 + utdto.InitTable(db, tb, tableName)
  13 +}
  14 +
  15 +func Insert(db *gorm.DB, gameId string, data IDtoData) {
  16 + utdto.Insert(db, data, data.GetTableName(gameId))
  17 +}
  18 +
  19 +func Update(db *gorm.DB, gameId string, data IDtoData) {
  20 + utdto.Update(db, data, data.GetTableName(gameId))
  21 +}
  22 +
  23 +func Save(db *gorm.DB, gameId string, data IDtoData) {
  24 + utdto.Save(db, data, data.GetTableName(gameId))
  25 +}
  26 +
  27 +func First(db *gorm.DB, gameId string, data IDtoData) (has bool, err error) {
  28 + result := utdto.First(db, data, data.GetTableName(gameId))
  29 + err = result.Error
  30 + if err == nil {
  31 + has = true
  32 + } else {
  33 + has = false
  34 + if strings.Contains(err.Error(), "record not found") {
  35 + err = nil
  36 + } else {
  37 + lxalilog.Errors(err, gameId)
  38 + return
  39 + }
  40 + }
  41 + return
11 } 42 }
dto/init-dto.go
@@ -2,7 +2,7 @@ package dto @@ -2,7 +2,7 @@ package dto
2 2
3 import ( 3 import (
4 "apigame/service/constd" 4 "apigame/service/constd"
5 - "apigame/util/utildto" 5 + "apigame/util/utdto"
6 "fmt" 6 "fmt"
7 "github.com/astaxie/beego" 7 "github.com/astaxie/beego"
8 "gorm.io/gorm" 8 "gorm.io/gorm"
@@ -16,12 +16,12 @@ var ( @@ -16,12 +16,12 @@ var (
16 func InitDto() { 16 func InitDto() {
17 17
18 // ConnectMySQL 18 // ConnectMySQL
19 - if db, err := utildto.ConnectMySQL(beego.AppConfig.String("mysql::mergecommon")); err == nil { 19 + if db, err := utdto.ConnectMySQL(beego.AppConfig.String("mysql::mergecommon")); err == nil {
20 DbCommon = db 20 DbCommon = db
21 } else { 21 } else {
22 fmt.Println(" InitMysqls Error::" + err.Error()) 22 fmt.Println(" InitMysqls Error::" + err.Error())
23 } 23 }
24 - if db, err := utildto.ConnectMySQL(beego.AppConfig.String("mysql::" + constd.MYSQL_MERGECONFIG)); err == nil { 24 + if db, err := utdto.ConnectMySQL(beego.AppConfig.String("mysql::" + constd.MYSQL_MERGECONFIG)); err == nil {
25 DbConfig = db 25 DbConfig = db
26 } else { 26 } else {
27 27
@@ -30,10 +30,10 @@ func InitDto() { @@ -30,10 +30,10 @@ func InitDto() {
30 // create table 30 // create table
31 // 卡牌卡包 31 // 卡牌卡包
32 for _, gameId := range constd.GameListCardHolder { 32 for _, gameId := range constd.GameListCardHolder {
33 - InitTable(DbCommon, new(CardHolderData), gameId)  
34 - InitTable(DbCommon, new(CardHolderRecordOpen), gameId)  
35 - InitTable(DbCommon, new(CardHolderRecordRewardAlbum), gameId)  
36 - InitTable(DbCommon, new(CardHolderRecordRewardRound), gameId) 33 + InitTable(DbCommon, gameId, new(CardHolderData))
  34 + InitTable(DbCommon, gameId, new(CardHolderRecordOpen))
  35 + InitTable(DbCommon, gameId, new(CardHolderRecordRewardAlbum))
  36 + InitTable(DbCommon, gameId, new(CardHolderRecordRewardRound))
37 } 37 }
38 38
39 } 39 }
dto/interface.go
1 package dto 1 package dto
2 2
3 -// ITableData 数据库表  
4 -type ITableData interface {  
5 - // GetTableName 表名 后缀是 gameId  
6 - GetTableName(gameId string) string  
7 -}  
8 -  
9 -type IRecordData interface {  
10 - // TableName 表名模板  
11 - TableName() string  
12 - // GetTableName 表名 后缀是 gameId  
13 - GetTableName(gameId string) string  
14 -}  
15 -  
16 -// IPlayerData 玩家数据表  
17 -type IPlayerData interface { 3 +// IDtoData dto数据
  4 +type IDtoData interface {
18 // TableName 表名模板 5 // TableName 表名模板
19 TableName() string 6 TableName() string
20 // GetTableName 表名 后缀是 gameId 7 // GetTableName 表名 后缀是 gameId
21 GetTableName(gameId string) string 8 GetTableName(gameId string) string
22 - // Init 新建  
23 - Init(uid int64)  
24 } 9 }
dto/player-data.go
@@ -1,37 +0,0 @@ @@ -1,37 +0,0 @@
1 -package dto  
2 -  
3 -import (  
4 - "apigame/util/util-lx/lxalilog"  
5 - "apigame/util/utildto"  
6 - "strings"  
7 -)  
8 -  
9 -func LoadPlayerData(gameId string, uid int64, data IPlayerData) (has bool, err error) {  
10 - result := utildto.First(DbCommon, data, data.GetTableName(gameId))  
11 - err = result.Error  
12 - if err == nil {  
13 - has = true  
14 - } else {  
15 - has = false  
16 - if strings.Contains(err.Error(), "record not found") {  
17 - err = nil  
18 - } else {  
19 - lxalilog.Errors(err, gameId, uid)  
20 - return  
21 - }  
22 - }  
23 - // 档案不存在 新建  
24 - if !has {  
25 - data.Init(uid)  
26 - CreatePlayerData(gameId, data)  
27 - }  
28 - return  
29 -}  
30 -  
31 -func CreatePlayerData(gameId string, data IPlayerData) {  
32 - utildto.Insert(DbCommon, data, data.GetTableName(gameId))  
33 -}  
34 -  
35 -func SavePlayerData(gameId string, data IPlayerData) {  
36 - utildto.Save(DbCommon, data, data.GetTableName(gameId))  
37 -}  
1 package dto 1 package dto
2 2
3 -import "apigame/util/utildto" 3 +import "apigame/util/utdto"
4 4
5 -func SaveRecord(gameId string, data IRecordData) {  
6 - utildto.Insert(DbCommon, data, data.GetTableName(gameId)) 5 +func SaveRecord(gameId string, data IDtoData) {
  6 + utdto.Insert(DbCommon, data, data.GetTableName(gameId))
7 } 7 }
service/cardholder/logic.go
@@ -14,13 +14,13 @@ func SaveData(gameId string, d *dto.CardHolderData) { @@ -14,13 +14,13 @@ func SaveData(gameId string, d *dto.CardHolderData) {
14 d.UpdateTime = lxtime.NowUninx() 14 d.UpdateTime = lxtime.NowUninx()
15 d.Encode() 15 d.Encode()
16 16
17 - dto.SavePlayerData(gameId, d) 17 + dto.Update(dto.DbCommon, gameId, d)
18 } 18 }
19 19
20 func _LoadData(gameId string, uid int64) (d *dto.CardHolderData) { 20 func _LoadData(gameId string, uid int64) (d *dto.CardHolderData) {
21 d = dto.NewCardHolderData(uid) 21 d = dto.NewCardHolderData(uid)
22 22
23 - has, err := dto.LoadPlayerData(gameId, uid, d) 23 + has, err := dto.First(dto.DbCommon, gameId, d)
24 if err != nil { 24 if err != nil {
25 lxalilog.Errors(err, "cardholder._LoadData", gameId, uid) 25 lxalilog.Errors(err, "cardholder._LoadData", gameId, uid)
26 return 26 return
@@ -28,6 +28,9 @@ func _LoadData(gameId string, uid int64) (d *dto.CardHolderData) { @@ -28,6 +28,9 @@ func _LoadData(gameId string, uid int64) (d *dto.CardHolderData) {
28 // 解析 28 // 解析
29 if has { 29 if has {
30 d.Decode() 30 d.Decode()
  31 + } else {
  32 + d.Init(uid)
  33 + dto.Insert(dto.DbCommon, gameId, d)
31 } 34 }
32 return 35 return
33 } 36 }
util/utdto/action.go 0 → 100644
@@ -0,0 +1,2 @@ @@ -0,0 +1,2 @@
  1 +package utdto
  2 +
util/utdto/base.go 0 → 100644
@@ -0,0 +1,37 @@ @@ -0,0 +1,37 @@
  1 +package utdto
  2 +
  3 +import (
  4 + "gorm.io/gorm"
  5 + "strings"
  6 +)
  7 +
  8 +// Insert 插入
  9 +func Insert(db *gorm.DB, value any, tableName string) *gorm.DB {
  10 + stmt := db.Session(&gorm.Session{DryRun: true}).Create(value).Statement
  11 + stmtSQL := stmt.SQL.String()
  12 + sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)
  13 + return db.Exec(sql, stmt.Vars...)
  14 +}
  15 +
  16 +// Update 更新
  17 +func Update(db *gorm.DB, value any, tableName string) *gorm.DB {
  18 + stmt := db.Session(&gorm.Session{DryRun: true}).Updates(value).Statement
  19 + stmtSQL := stmt.SQL.String()
  20 + sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)
  21 + return db.Exec(sql, stmt.Vars...)
  22 +}
  23 +
  24 +// Save 保存
  25 +func Save(db *gorm.DB, value any, tableName string) *gorm.DB {
  26 + stmt := db.Session(&gorm.Session{DryRun: true}).Save(value).Statement
  27 + stmtSQL := stmt.SQL.String()
  28 + sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)
  29 + return db.Exec(sql, stmt.Vars...)
  30 +}
  31 +
  32 +func First(db *gorm.DB, value any, tableName string) *gorm.DB {
  33 + stmt := db.Session(&gorm.Session{DryRun: true}).First(value).Statement
  34 + stmtSQL := stmt.SQL.String()
  35 + sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)
  36 + return db.Raw(sql, stmt.Vars...).Scan(value)
  37 +}
util/utdto/mysql.go 0 → 100644
@@ -0,0 +1,12 @@ @@ -0,0 +1,12 @@
  1 +package utdto
  2 +
  3 +import (
  4 + "gorm.io/driver/mysql"
  5 + "gorm.io/gorm"
  6 +)
  7 +
  8 +const MYSQL_TABLE_TEMPLATE = "all_table_template" // 表名模板
  9 +
  10 +func ConnectMySQL(dsn string) (db *gorm.DB, err error) {
  11 + return gorm.Open(mysql.Open(dsn), &gorm.Config{})
  12 +}
util/utdto/table.go 0 → 100644
@@ -0,0 +1,132 @@ @@ -0,0 +1,132 @@
  1 +package utdto
  2 +
  3 +import (
  4 + "fmt"
  5 + "gorm.io/driver/mysql"
  6 + "gorm.io/gorm"
  7 + "gorm.io/gorm/clause"
  8 + "gorm.io/gorm/migrator"
  9 + "strings"
  10 +)
  11 +
  12 +func InitTable(db *gorm.DB, value any, tableName string) {
  13 + m := db.Migrator().(mysql.Migrator).Migrator
  14 + queryTx, execTx := m.GetQueryAndExecTx()
  15 + if HasTable(queryTx.Migrator().(mysql.Migrator).Migrator, value, tableName) {
  16 + fmt.Println(tableName + " exist, skip!")
  17 + } else {
  18 + err := CreateTable(execTx, value, tableName)
  19 + if err != nil {
  20 + fmt.Println("err", err)
  21 + }
  22 + }
  23 +}
  24 +
  25 +func HasTable(m migrator.Migrator, value interface{}, tableName string) bool {
  26 + var count int64
  27 +
  28 + m.RunWithValue(value, func(stmt *gorm.Statement) error {
  29 + currentDatabase := m.DB.Migrator().CurrentDatabase()
  30 + return m.DB.Raw("SELECT count(*) FROM information_schema.tables WHERE table_schema = ? AND table_name = ? AND table_type = ?", currentDatabase, tableName, "BASE TABLE").Row().Scan(&count)
  31 + })
  32 +
  33 + return count > 0
  34 +}
  35 +
  36 +func CreateTable(execTx *gorm.DB, value any, tableName string) error {
  37 + m := execTx.Migrator().(mysql.Migrator).Migrator
  38 + tx := m.DB.Session(&gorm.Session{})
  39 +
  40 + if err := m.RunWithValue(value, func(stmt *gorm.Statement) (err error) {
  41 + var (
  42 + createTableSQL = "CREATE TABLE ? ("
  43 + values = []interface{}{clause.Table{Name: tableName}}
  44 + hasPrimaryKeyInDataType bool
  45 + )
  46 +
  47 + for _, dbName := range stmt.Schema.DBNames {
  48 + field := stmt.Schema.FieldsByDBName[dbName]
  49 + if !field.IgnoreMigration {
  50 + createTableSQL += "? ?"
  51 + hasPrimaryKeyInDataType = hasPrimaryKeyInDataType || strings.Contains(strings.ToUpper(m.DataTypeOf(field)), "PRIMARY KEY")
  52 + values = append(values, clause.Column{Name: dbName}, m.DB.Migrator().FullDataTypeOf(field))
  53 + createTableSQL += ","
  54 + }
  55 + }
  56 +
  57 + if !hasPrimaryKeyInDataType && len(stmt.Schema.PrimaryFields) > 0 {
  58 + createTableSQL += "PRIMARY KEY ?,"
  59 + primaryKeys := make([]interface{}, 0, len(stmt.Schema.PrimaryFields))
  60 + for _, field := range stmt.Schema.PrimaryFields {
  61 + primaryKeys = append(primaryKeys, clause.Column{Name: field.DBName})
  62 + }
  63 +
  64 + values = append(values, primaryKeys)
  65 + }
  66 +
  67 + for _, idx := range stmt.Schema.ParseIndexes() {
  68 + if m.CreateIndexAfterCreateTable {
  69 + defer func(value interface{}, name string) {
  70 + if err == nil {
  71 + err = tx.Migrator().CreateIndex(value, name)
  72 + }
  73 + }(value, idx.Name)
  74 + } else {
  75 + if idx.Class != "" {
  76 + createTableSQL += idx.Class + " "
  77 + }
  78 + createTableSQL += "INDEX ? ?"
  79 +
  80 + if idx.Comment != "" {
  81 + createTableSQL += fmt.Sprintf(" COMMENT '%s'", idx.Comment)
  82 + }
  83 +
  84 + if idx.Option != "" {
  85 + createTableSQL += " " + idx.Option
  86 + }
  87 +
  88 + createTableSQL += ","
  89 + values = append(values, clause.Column{Name: idx.Name}, tx.Migrator().(migrator.BuildIndexOptionsInterface).BuildIndexOptions(idx.Fields, stmt))
  90 + }
  91 + }
  92 +
  93 + if !m.DB.DisableForeignKeyConstraintWhenMigrating && !m.DB.IgnoreRelationshipsWhenMigrating {
  94 + for _, rel := range stmt.Schema.Relationships.Relations {
  95 + if rel.Field.IgnoreMigration {
  96 + continue
  97 + }
  98 + if constraint := rel.ParseConstraint(); constraint != nil {
  99 + if constraint.Schema == stmt.Schema {
  100 + sql, vars := constraint.Build()
  101 + createTableSQL += sql + ","
  102 + values = append(values, vars...)
  103 + }
  104 + }
  105 + }
  106 + }
  107 +
  108 + for _, uni := range stmt.Schema.ParseUniqueConstraints() {
  109 + createTableSQL += "CONSTRAINT ? UNIQUE (?),"
  110 + values = append(values, clause.Column{Name: uni.Name}, clause.Expr{SQL: stmt.Quote(uni.Field.DBName)})
  111 + }
  112 +
  113 + for _, chk := range stmt.Schema.ParseCheckConstraints() {
  114 + createTableSQL += "CONSTRAINT ? CHECK (?),"
  115 + values = append(values, clause.Column{Name: chk.Name}, clause.Expr{SQL: chk.Constraint})
  116 + }
  117 +
  118 + createTableSQL = strings.TrimSuffix(createTableSQL, ",")
  119 +
  120 + createTableSQL += ")"
  121 +
  122 + if tableOption, ok := m.DB.Get("gorm:table_options"); ok {
  123 + createTableSQL += fmt.Sprint(tableOption)
  124 + }
  125 +
  126 + err = tx.Exec(createTableSQL, values...).Error
  127 + return err
  128 + }); err != nil {
  129 + return err
  130 + }
  131 + return nil
  132 +}
util/utildto/mysql.go
@@ -1,169 +0,0 @@ @@ -1,169 +0,0 @@
1 -package utildto  
2 -  
3 -import (  
4 - "fmt"  
5 - "gorm.io/driver/mysql"  
6 - "gorm.io/gorm"  
7 - "gorm.io/gorm/clause"  
8 - "gorm.io/gorm/migrator"  
9 - "strings"  
10 -)  
11 -  
12 -const MYSQL_TABLE_TEMPLATE = "all_table_template" // 表名模板  
13 -  
14 -func ConnectMySQL(dsn string) (db *gorm.DB, err error) {  
15 - return gorm.Open(mysql.Open(dsn), &gorm.Config{})  
16 -}  
17 -  
18 -func InitTable(db *gorm.DB, value any, tableName string) {  
19 - m := db.Migrator().(mysql.Migrator).Migrator  
20 - queryTx, execTx := m.GetQueryAndExecTx()  
21 - if HasTable(queryTx.Migrator().(mysql.Migrator).Migrator, value, tableName) {  
22 - fmt.Println(tableName + " exist, skip!")  
23 - } else {  
24 - err := CreateTable(execTx, value, tableName)  
25 - if err != nil {  
26 - fmt.Println("err", err)  
27 - }  
28 - }  
29 -}  
30 -  
31 -func HasTable(m migrator.Migrator, value interface{}, tableName string) bool {  
32 - var count int64  
33 -  
34 - m.RunWithValue(value, func(stmt *gorm.Statement) error {  
35 - currentDatabase := m.DB.Migrator().CurrentDatabase()  
36 - return m.DB.Raw("SELECT count(*) FROM information_schema.tables WHERE table_schema = ? AND table_name = ? AND table_type = ?", currentDatabase, tableName, "BASE TABLE").Row().Scan(&count)  
37 - })  
38 -  
39 - return count > 0  
40 -}  
41 -  
42 -func CreateTable(execTx *gorm.DB, value any, tableName string) error {  
43 - m := execTx.Migrator().(mysql.Migrator).Migrator  
44 - tx := m.DB.Session(&gorm.Session{})  
45 -  
46 - if err := m.RunWithValue(value, func(stmt *gorm.Statement) (err error) {  
47 - var (  
48 - createTableSQL = "CREATE TABLE ? ("  
49 - values = []interface{}{clause.Table{Name: tableName}}  
50 - hasPrimaryKeyInDataType bool  
51 - )  
52 -  
53 - for _, dbName := range stmt.Schema.DBNames {  
54 - field := stmt.Schema.FieldsByDBName[dbName]  
55 - if !field.IgnoreMigration {  
56 - createTableSQL += "? ?"  
57 - hasPrimaryKeyInDataType = hasPrimaryKeyInDataType || strings.Contains(strings.ToUpper(m.DataTypeOf(field)), "PRIMARY KEY")  
58 - values = append(values, clause.Column{Name: dbName}, m.DB.Migrator().FullDataTypeOf(field))  
59 - createTableSQL += ","  
60 - }  
61 - }  
62 -  
63 - if !hasPrimaryKeyInDataType && len(stmt.Schema.PrimaryFields) > 0 {  
64 - createTableSQL += "PRIMARY KEY ?,"  
65 - primaryKeys := make([]interface{}, 0, len(stmt.Schema.PrimaryFields))  
66 - for _, field := range stmt.Schema.PrimaryFields {  
67 - primaryKeys = append(primaryKeys, clause.Column{Name: field.DBName})  
68 - }  
69 -  
70 - values = append(values, primaryKeys)  
71 - }  
72 -  
73 - for _, idx := range stmt.Schema.ParseIndexes() {  
74 - if m.CreateIndexAfterCreateTable {  
75 - defer func(value interface{}, name string) {  
76 - if err == nil {  
77 - err = tx.Migrator().CreateIndex(value, name)  
78 - }  
79 - }(value, idx.Name)  
80 - } else {  
81 - if idx.Class != "" {  
82 - createTableSQL += idx.Class + " "  
83 - }  
84 - createTableSQL += "INDEX ? ?"  
85 -  
86 - if idx.Comment != "" {  
87 - createTableSQL += fmt.Sprintf(" COMMENT '%s'", idx.Comment)  
88 - }  
89 -  
90 - if idx.Option != "" {  
91 - createTableSQL += " " + idx.Option  
92 - }  
93 -  
94 - createTableSQL += ","  
95 - values = append(values, clause.Column{Name: idx.Name}, tx.Migrator().(migrator.BuildIndexOptionsInterface).BuildIndexOptions(idx.Fields, stmt))  
96 - }  
97 - }  
98 -  
99 - if !m.DB.DisableForeignKeyConstraintWhenMigrating && !m.DB.IgnoreRelationshipsWhenMigrating {  
100 - for _, rel := range stmt.Schema.Relationships.Relations {  
101 - if rel.Field.IgnoreMigration {  
102 - continue  
103 - }  
104 - if constraint := rel.ParseConstraint(); constraint != nil {  
105 - if constraint.Schema == stmt.Schema {  
106 - sql, vars := constraint.Build()  
107 - createTableSQL += sql + ","  
108 - values = append(values, vars...)  
109 - }  
110 - }  
111 - }  
112 - }  
113 -  
114 - for _, uni := range stmt.Schema.ParseUniqueConstraints() {  
115 - createTableSQL += "CONSTRAINT ? UNIQUE (?),"  
116 - values = append(values, clause.Column{Name: uni.Name}, clause.Expr{SQL: stmt.Quote(uni.Field.DBName)})  
117 - }  
118 -  
119 - for _, chk := range stmt.Schema.ParseCheckConstraints() {  
120 - createTableSQL += "CONSTRAINT ? CHECK (?),"  
121 - values = append(values, clause.Column{Name: chk.Name}, clause.Expr{SQL: chk.Constraint})  
122 - }  
123 -  
124 - createTableSQL = strings.TrimSuffix(createTableSQL, ",")  
125 -  
126 - createTableSQL += ")"  
127 -  
128 - if tableOption, ok := m.DB.Get("gorm:table_options"); ok {  
129 - createTableSQL += fmt.Sprint(tableOption)  
130 - }  
131 -  
132 - err = tx.Exec(createTableSQL, values...).Error  
133 - return err  
134 - }); err != nil {  
135 - return err  
136 - }  
137 - return nil  
138 -}  
139 -  
140 -// Insert 插入  
141 -func Insert(db *gorm.DB, value any, tableName string) *gorm.DB {  
142 - stmt := db.Session(&gorm.Session{DryRun: true}).Create(value).Statement  
143 - stmtSQL := stmt.SQL.String()  
144 - sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)  
145 - return db.Exec(sql, stmt.Vars...)  
146 -}  
147 -  
148 -// Update 更新  
149 -func Update(db *gorm.DB, value any, tableName string) *gorm.DB {  
150 - stmt := db.Session(&gorm.Session{DryRun: true}).Updates(value).Statement  
151 - stmtSQL := stmt.SQL.String()  
152 - sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)  
153 - return db.Exec(sql, stmt.Vars...)  
154 -}  
155 -  
156 -// Save 保存  
157 -func Save(db *gorm.DB, value any, tableName string) *gorm.DB {  
158 - stmt := db.Session(&gorm.Session{DryRun: true}).Save(value).Statement  
159 - stmtSQL := stmt.SQL.String()  
160 - sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)  
161 - return db.Exec(sql, stmt.Vars...)  
162 -}  
163 -  
164 -func First(db *gorm.DB, value any, tableName string) *gorm.DB {  
165 - stmt := db.Session(&gorm.Session{DryRun: true}).First(value).Statement  
166 - stmtSQL := stmt.SQL.String()  
167 - sql := strings.Replace(stmtSQL, MYSQL_TABLE_TEMPLATE, tableName, -1)  
168 - return db.Raw(sql, stmt.Vars...).Scan(value)  
169 -}