github.com/unionj-cloud/go-doudou/v2@v2.3.5/toolkit/dbvendor/ivendor.go (about)

     1  package dbvendor
     2  
     3  import (
     4  	"context"
     5  	"database/sql"
     6  	"fmt"
     7  	"github.com/pkg/errors"
     8  	"github.com/unionj-cloud/go-doudou/v2/toolkit/errorx"
     9  	"github.com/unionj-cloud/go-doudou/v2/toolkit/templateutils"
    10  	"github.com/unionj-cloud/go-doudou/v2/toolkit/zlogger"
    11  	"gorm.io/gorm"
    12  )
    13  
    14  var Registry = &registry{
    15  	vendors: map[string]IVendor{},
    16  }
    17  
    18  type registry struct {
    19  	vendors map[string]IVendor
    20  }
    21  
    22  func (receiver *registry) Register(driver string, vendor IVendor) {
    23  	receiver.vendors[driver] = vendor
    24  }
    25  
    26  func (receiver *registry) GetVendor(driver string) IVendor {
    27  	vendor, ok := receiver.vendors[driver]
    28  	if !ok {
    29  		errorx.Panic(fmt.Sprintf("Unsupported driver %s", driver))
    30  	}
    31  	return vendor
    32  }
    33  
    34  type IVendor interface {
    35  	CreateTable(ctx context.Context, db *gorm.DB, t Table) error
    36  	DropTable(ctx context.Context, db *gorm.DB, t Table) error
    37  	ChangeColumn(ctx context.Context, db *gorm.DB, col Column) error
    38  	AddColumn(ctx context.Context, db *gorm.DB, col Column) error
    39  	DropColumn(ctx context.Context, db *gorm.DB, col Column) error
    40  	ToColumnType(goType string, autoincrementing bool) string
    41  
    42  	Insert(ctx context.Context, db *gorm.DB, dml DMLSchema, args ...interface{}) (int64, error)
    43  	Update(ctx context.Context, db *gorm.DB, dml DMLSchema, args ...interface{}) error
    44  	Delete(ctx context.Context, db *gorm.DB, dml DMLSchema, args ...interface{}) error
    45  	SelectById(ctx context.Context, db *gorm.DB, dml DMLSchema, args ...interface{}) (map[string]interface{}, error)
    46  	GetInsertStatement(dml DMLSchema) (statement string, err error)
    47  	GetInsertReturningPkStatement(dml DMLSchema) (statement string, err error)
    48  	GetBatchInsertStatement(dml DMLSchema, rows []interface{}) (statement string, err error)
    49  	GetUpdateStatement(dml DMLSchema) (statement string, err error)
    50  }
    51  
    52  type DMLSchema struct {
    53  	Schema        string
    54  	TablePrefix   string
    55  	TableName     string
    56  	InsertColumns []Column
    57  	UpdateColumns []Column
    58  	Pk            []Column
    59  }
    60  
    61  // Column define a column
    62  type Column struct {
    63  	TablePrefix   string
    64  	Table         string
    65  	Name          string
    66  	OldName       string
    67  	Type          string
    68  	Default       *string
    69  	Pk            bool
    70  	Nullable      bool
    71  	Unsigned      bool
    72  	Autoincrement bool
    73  	Extra         string
    74  	Comment       string
    75  	// 关联表名
    76  	Foreign string
    77  }
    78  
    79  type Index struct {
    80  	Name        string
    81  	Columns     []string
    82  	Cardinality []uint64
    83  	NoneUnique  uint64
    84  }
    85  
    86  // Table defines a table
    87  type Table struct {
    88  	TablePrefix string
    89  	Name        string
    90  	Columns     []Column
    91  	BizColumns  []Column
    92  	Pk          []string
    93  	Joins       []string
    94  	Indexes     []*Index
    95  	// 父表
    96  	Inherited string
    97  }
    98  
    99  func String(tmplname, tmpl string, data interface{}, pf PlaceholderFormat) (string, error) {
   100  	result, err := templateutils.String(tmplname, tmpl, data)
   101  	if err != nil {
   102  		return "", errors.WithStack(err)
   103  	}
   104  	if pf != nil {
   105  		result, err = pf.ReplacePlaceholders(result)
   106  		if err != nil {
   107  			return "", errors.WithStack(err)
   108  		}
   109  	}
   110  	zlogger.Debug().Msg(result)
   111  	return result, nil
   112  }
   113  
   114  func StringBlock(tmplname, tmpl string, block string, data interface{}, pf PlaceholderFormat) (string, error) {
   115  	result, err := templateutils.StringBlock(tmplname, tmpl, block, data)
   116  	if err != nil {
   117  		return "", errors.WithStack(err)
   118  	}
   119  	if pf != nil {
   120  		result, err = pf.ReplacePlaceholders(result)
   121  		if err != nil {
   122  			return "", errors.WithStack(err)
   123  		}
   124  	}
   125  	zlogger.Debug().Msg(result)
   126  	return result, nil
   127  }
   128  
   129  const (
   130  	// Update used for update_at column
   131  	Update = "on update CURRENT_TIMESTAMP"
   132  )
   133  
   134  func Scan(rows *sql.Rows, result *[]map[string]interface{}) {
   135  	fields, _ := rows.Columns()
   136  	for rows.Next() {
   137  		scans := make([]interface{}, len(fields))
   138  		data := make(map[string]interface{})
   139  
   140  		for i := range scans {
   141  			scans[i] = &scans[i]
   142  		}
   143  		rows.Scan(scans...)
   144  		for i, v := range scans {
   145  			data[fields[i]] = v
   146  		}
   147  		*result = append(*result, data)
   148  	}
   149  }