Merge pull request #4214 from flycash/rft/dbOption

Optimize orm by using BDOption rather than hints
This commit is contained in:
Ming Deng 2020-09-09 00:06:44 +08:00 committed by GitHub
commit 6612bc4c2a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 63 additions and 102 deletions

View File

@ -20,8 +20,6 @@ import (
"time"
"github.com/astaxie/beego/pkg/client/orm"
"github.com/astaxie/beego/pkg/client/orm/hints"
"github.com/astaxie/beego/pkg/infrastructure/utils"
)
// DriverType database driver constant int.
@ -86,13 +84,13 @@ func AddAliasWthDB(aliasName, driverName string, db *sql.DB) error {
// RegisterDataBase Setting the database connect params. Use the database driver self dataSource args.
func RegisterDataBase(aliasName, driverName, dataSource string, params ...int) error {
opts := make([]utils.KV, 0, 2)
opts := make([]orm.DBOption, 0, 2)
if len(params) > 0 {
opts = append(opts, hints.MaxIdleConnections(params[0]))
opts = append(opts, orm.MaxIdleConnections(params[0]))
}
if len(params) > 1 {
opts = append(opts, hints.MaxOpenConnections(params[1]))
opts = append(opts, orm.MaxOpenConnections(params[1]))
}
return orm.RegisterDataBase(aliasName, driverName, dataSource, opts...)
}

View File

@ -21,9 +21,6 @@ import (
"sync"
"time"
"github.com/astaxie/beego/pkg/client/orm/hints"
"github.com/astaxie/beego/pkg/infrastructure/utils"
lru "github.com/hashicorp/golang-lru"
)
@ -278,6 +275,7 @@ type alias struct {
MaxIdleConns int
MaxOpenConns int
ConnMaxLifetime time.Duration
StmtCacheSize int
DB *DB
DbBaser dbBaser
TZ *time.Location
@ -340,7 +338,7 @@ func detectTZ(al *alias) {
}
}
func addAliasWthDB(aliasName, driverName string, db *sql.DB, params ...utils.KV) (*alias, error) {
func addAliasWthDB(aliasName, driverName string, db *sql.DB, params ...DBOption) (*alias, error) {
existErr := fmt.Errorf("DataBase alias name `%s` already registered, cannot reuse", aliasName)
if _, ok := dataBaseCache.get(aliasName); ok {
return nil, existErr
@ -358,32 +356,35 @@ func addAliasWthDB(aliasName, driverName string, db *sql.DB, params ...utils.KV)
return al, nil
}
func newAliasWithDb(aliasName, driverName string, db *sql.DB, params ...utils.KV) (*alias, error) {
kvs := utils.NewKVs(params...)
func newAliasWithDb(aliasName, driverName string, db *sql.DB, params ...DBOption) (*alias, error) {
al := &alias{}
al.DB = &DB{
RWMutex: new(sync.RWMutex),
DB: db,
}
for _, p := range params {
p(al)
}
var stmtCache *lru.Cache
var stmtCacheSize int
maxStmtCacheSize := kvs.GetValueOr(hints.KeyMaxStmtCacheSize, 0).(int)
if maxStmtCacheSize > 0 {
_stmtCache, errC := newStmtDecoratorLruWithEvict(maxStmtCacheSize)
if al.StmtCacheSize > 0 {
_stmtCache, errC := newStmtDecoratorLruWithEvict(al.StmtCacheSize)
if errC != nil {
return nil, errC
} else {
stmtCache = _stmtCache
stmtCacheSize = maxStmtCacheSize
stmtCacheSize = al.StmtCacheSize
}
}
al := new(alias)
al.Name = aliasName
al.DriverName = driverName
al.DB = &DB{
RWMutex: new(sync.RWMutex),
DB: db,
stmtDecorators: stmtCache,
stmtDecoratorsLimit: stmtCacheSize,
}
al.DB.stmtDecorators = stmtCache
al.DB.stmtDecoratorsLimit = stmtCacheSize
if dr, ok := drivers[driverName]; ok {
al.DbBaser = dbBasers[dr]
@ -399,14 +400,6 @@ func newAliasWithDb(aliasName, driverName string, db *sql.DB, params ...utils.KV
detectTZ(al)
kvs.IfContains(hints.KeyMaxIdleConnections, func(value interface{}) {
al.SetMaxIdleConns(value.(int))
}).IfContains(hints.KeyMaxOpenConnections, func(value interface{}) {
al.SetMaxOpenConns(value.(int))
}).IfContains(hints.KeyConnMaxLifetime, func(value interface{}) {
al.SetConnMaxLifetime(value.(time.Duration))
})
return al, nil
}
@ -442,13 +435,13 @@ func (al *alias) SetConnMaxLifetime(lifeTime time.Duration) {
}
// AddAliasWthDB add a aliasName for the drivename
func AddAliasWthDB(aliasName, driverName string, db *sql.DB, params ...utils.KV) error {
func AddAliasWthDB(aliasName, driverName string, db *sql.DB, params ...DBOption) error {
_, err := addAliasWthDB(aliasName, driverName, db, params...)
return err
}
// RegisterDataBase Setting the database connect params. Use the database driver self dataSource args.
func RegisterDataBase(aliasName, driverName, dataSource string, params ...utils.KV) error {
func RegisterDataBase(aliasName, driverName, dataSource string, params ...DBOption) error {
var (
err error
db *sql.DB
@ -561,3 +554,33 @@ func newStmtDecoratorLruWithEvict(cacheSize int) (*lru.Cache, error) {
}
return cache, nil
}
type DBOption func(al *alias)
// MaxIdleConnections return a hint about MaxIdleConnections
func MaxIdleConnections(maxIdleConn int) DBOption {
return func(al *alias) {
al.SetMaxIdleConns(maxIdleConn)
}
}
// MaxOpenConnections return a hint about MaxOpenConnections
func MaxOpenConnections(maxOpenConn int) DBOption {
return func(al *alias) {
al.SetMaxOpenConns(maxOpenConn)
}
}
// ConnMaxLifetime return a hint about ConnMaxLifetime
func ConnMaxLifetime(v time.Duration) DBOption {
return func(al *alias) {
al.SetConnMaxLifetime(v)
}
}
// MaxStmtCacheSize return a hint about MaxStmtCacheSize
func MaxStmtCacheSize(v int) DBOption {
return func(al *alias) {
al.StmtCacheSize = v
}
}

View File

@ -18,16 +18,14 @@ import (
"testing"
"time"
"github.com/astaxie/beego/pkg/client/orm/hints"
"github.com/stretchr/testify/assert"
)
func TestRegisterDataBase(t *testing.T) {
err := RegisterDataBase("test-params", DBARGS.Driver, DBARGS.Source,
hints.MaxIdleConnections(20),
hints.MaxOpenConnections(300),
hints.ConnMaxLifetime(time.Minute))
MaxIdleConnections(20),
MaxOpenConnections(300),
ConnMaxLifetime(time.Minute))
assert.Nil(t, err)
al := getDbAlias("test-params")
@ -39,7 +37,7 @@ func TestRegisterDataBase(t *testing.T) {
func TestRegisterDataBase_MaxStmtCacheSizeNegative1(t *testing.T) {
aliasName := "TestRegisterDataBase_MaxStmtCacheSizeNegative1"
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, hints.MaxStmtCacheSize(-1))
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, MaxStmtCacheSize(-1))
assert.Nil(t, err)
al := getDbAlias(aliasName)
@ -49,7 +47,7 @@ func TestRegisterDataBase_MaxStmtCacheSizeNegative1(t *testing.T) {
func TestRegisterDataBase_MaxStmtCacheSize0(t *testing.T) {
aliasName := "TestRegisterDataBase_MaxStmtCacheSize0"
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, hints.MaxStmtCacheSize(0))
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, MaxStmtCacheSize(0))
assert.Nil(t, err)
al := getDbAlias(aliasName)
@ -59,7 +57,7 @@ func TestRegisterDataBase_MaxStmtCacheSize0(t *testing.T) {
func TestRegisterDataBase_MaxStmtCacheSize1(t *testing.T) {
aliasName := "TestRegisterDataBase_MaxStmtCacheSize1"
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, hints.MaxStmtCacheSize(1))
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, MaxStmtCacheSize(1))
assert.Nil(t, err)
al := getDbAlias(aliasName)
@ -69,7 +67,7 @@ func TestRegisterDataBase_MaxStmtCacheSize1(t *testing.T) {
func TestRegisterDataBase_MaxStmtCacheSize841(t *testing.T) {
aliasName := "TestRegisterDataBase_MaxStmtCacheSize841"
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, hints.MaxStmtCacheSize(841))
err := RegisterDataBase(aliasName, DBARGS.Driver, DBARGS.Source, MaxStmtCacheSize(841))
assert.Nil(t, err)
al := getDbAlias(aliasName)

View File

@ -15,20 +15,12 @@
package hints
import (
"time"
"github.com/astaxie/beego/pkg/infrastructure/utils"
)
const (
//db level
KeyMaxIdleConnections = iota
KeyMaxOpenConnections
KeyConnMaxLifetime
KeyMaxStmtCacheSize
//query level
KeyForceIndex
KeyForceIndex = iota
KeyUseIndex
KeyIgnoreIndex
KeyForUpdate
@ -57,26 +49,6 @@ func (s *Hint) GetValue() interface{} {
var _ utils.KV = new(Hint)
// MaxIdleConnections return a hint about MaxIdleConnections
func MaxIdleConnections(v int) *Hint {
return NewHint(KeyMaxIdleConnections, v)
}
// MaxOpenConnections return a hint about MaxOpenConnections
func MaxOpenConnections(v int) *Hint {
return NewHint(KeyMaxOpenConnections, v)
}
// ConnMaxLifetime return a hint about ConnMaxLifetime
func ConnMaxLifetime(v time.Duration) *Hint {
return NewHint(KeyConnMaxLifetime, v)
}
// MaxStmtCacheSize return a hint about MaxStmtCacheSize
func MaxStmtCacheSize(v int) *Hint {
return NewHint(KeyMaxStmtCacheSize, v)
}
// ForceIndex return a hint about ForceIndex
func ForceIndex(indexes ...string) *Hint {
return NewHint(KeyForceIndex, indexes)

View File

@ -48,34 +48,6 @@ func TestNewHint_float(t *testing.T) {
assert.Equal(t, hint.GetValue(), value)
}
func TestMaxOpenConnections(t *testing.T) {
i := 887423
hint := MaxOpenConnections(i)
assert.Equal(t, hint.GetValue(), i)
assert.Equal(t, hint.GetKey(), KeyMaxOpenConnections)
}
func TestConnMaxLifetime(t *testing.T) {
i := time.Hour
hint := ConnMaxLifetime(i)
assert.Equal(t, hint.GetValue(), i)
assert.Equal(t, hint.GetKey(), KeyConnMaxLifetime)
}
func TestMaxIdleConnections(t *testing.T) {
i := 42316
hint := MaxIdleConnections(i)
assert.Equal(t, hint.GetValue(), i)
assert.Equal(t, hint.GetKey(), KeyMaxIdleConnections)
}
func TestMaxStmtCacheSize(t *testing.T) {
i := 94157
hint := MaxStmtCacheSize(i)
assert.Equal(t, hint.GetValue(), i)
assert.Equal(t, hint.GetKey(), KeyMaxStmtCacheSize)
}
func TestForceIndex(t *testing.T) {
s := []string{`f_index1`, `f_index2`, `f_index3`}
hint := ForceIndex(s...)

View File

@ -22,8 +22,6 @@ import (
"strings"
"time"
"github.com/astaxie/beego/pkg/client/orm/hints"
_ "github.com/go-sql-driver/mysql"
_ "github.com/lib/pq"
_ "github.com/mattn/go-sqlite3"
@ -529,7 +527,7 @@ func init() {
os.Exit(2)
}
err := RegisterDataBase("default", DBARGS.Driver, DBARGS.Source, hints.MaxIdleConnections(20))
err := RegisterDataBase("default", DBARGS.Driver, DBARGS.Source, MaxIdleConnections(20))
if err != nil {
panic(fmt.Sprintf("can not register database: %v", err))

View File

@ -601,7 +601,7 @@ func NewOrmUsingDB(aliasName string) Ormer {
}
// NewOrmWithDB create a new ormer object with specify *sql.DB for query
func NewOrmWithDB(driverName, aliasName string, db *sql.DB, params ...utils.KV) (Ormer, error) {
func NewOrmWithDB(driverName, aliasName string, db *sql.DB, params ...DBOption) (Ormer, error) {
al, err := newAliasWithDb(aliasName, driverName, db, params...)
if err != nil {
return nil, err