added condition query builder support via github.com/go-xorm/builder
This commit is contained in:
parent
5ae5bc982a
commit
01c5ff6337
|
@ -51,10 +51,15 @@ Drivers for Go's sql package which currently support database/sql includes:
|
||||||
|
|
||||||
* Oracle: [github.com/mattn/go-oci8](https://github.com/mattn/go-oci8) (experiment)
|
* Oracle: [github.com/mattn/go-oci8](https://github.com/mattn/go-oci8) (experiment)
|
||||||
|
|
||||||
* ql: [github.com/cznic/ql](https://github.com/cznic/ql) (experiment)
|
|
||||||
|
|
||||||
# Changelog
|
# Changelog
|
||||||
|
|
||||||
|
* **v0.6.0**
|
||||||
|
* remove support for ql
|
||||||
|
* add query condition builder support via [github.com/go-xorm/builder](https://github.com/go-xorm/builder), so Where, And, Or
|
||||||
|
methods can use `builder.Cond` as parameter
|
||||||
|
* add Sum, SumInt, SumInt64 and NotIn methods
|
||||||
|
* some bugs fixed
|
||||||
|
|
||||||
* **v0.5.0**
|
* **v0.5.0**
|
||||||
* logging interface changed
|
* logging interface changed
|
||||||
* some bugs fixed
|
* some bugs fixed
|
||||||
|
|
|
@ -52,10 +52,15 @@ xorm是一个简单而强大的Go语言ORM库. 通过它可以使数据库操作
|
||||||
|
|
||||||
* Oracle: [github.com/mattn/go-oci8](https://github.com/mattn/go-oci8) (试验性支持)
|
* Oracle: [github.com/mattn/go-oci8](https://github.com/mattn/go-oci8) (试验性支持)
|
||||||
|
|
||||||
* ql: [github.com/cznic/ql](https://github.com/cznic/ql) (试验性支持)
|
|
||||||
|
|
||||||
## 更新日志
|
## 更新日志
|
||||||
|
|
||||||
|
* **v0.6.0**
|
||||||
|
* 去除对 ql 的支持
|
||||||
|
* 新增条件查询分析器 [github.com/go-xorm/builder](https://github.com/go-xorm/builder), 从因此 `Where, And, Or` 函数
|
||||||
|
将可以用 `builder.Cond` 作为条件组合
|
||||||
|
* 新增 Sum, SumInt, SumInt64 和 NotIn 函数
|
||||||
|
* Bug修正
|
||||||
|
|
||||||
* **v0.5.0**
|
* **v0.5.0**
|
||||||
* logging接口进行不兼容改变
|
* logging接口进行不兼容改变
|
||||||
* Bug修正
|
* Bug修正
|
||||||
|
|
|
@ -641,10 +641,10 @@ func (engine *Engine) Cascade(trueOrFalse ...bool) *Session {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Where method provide a condition query
|
// Where method provide a condition query
|
||||||
func (engine *Engine) Where(querystring string, args ...interface{}) *Session {
|
func (engine *Engine) Where(query interface{}, args ...interface{}) *Session {
|
||||||
session := engine.NewSession()
|
session := engine.NewSession()
|
||||||
session.IsAutoClose = true
|
session.IsAutoClose = true
|
||||||
return session.Where(querystring, args...)
|
return session.Where(query, args...)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Id will be depracated, please use ID instead
|
// Id will be depracated, please use ID instead
|
||||||
|
|
207
session.go
207
session.go
|
@ -16,6 +16,7 @@ import (
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
|
"github.com/go-xorm/builder"
|
||||||
"github.com/go-xorm/core"
|
"github.com/go-xorm/core"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -112,7 +113,7 @@ func (session *Session) Prepare() *Session {
|
||||||
return session
|
return session
|
||||||
}
|
}
|
||||||
|
|
||||||
// Sql will be deprecated, please use SQL instead.
|
// Sql !DEPRECIATED! will be deprecated, please use SQL instead.
|
||||||
func (session *Session) Sql(querystring string, args ...interface{}) *Session {
|
func (session *Session) Sql(querystring string, args ...interface{}) *Session {
|
||||||
session.Statement.Sql(querystring, args...)
|
session.Statement.Sql(querystring, args...)
|
||||||
return session
|
return session
|
||||||
|
@ -126,20 +127,20 @@ func (session *Session) SQL(querystring string, args ...interface{}) *Session {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Where provides custom query condition.
|
// Where provides custom query condition.
|
||||||
func (session *Session) Where(querystring string, args ...interface{}) *Session {
|
func (session *Session) Where(query interface{}, args ...interface{}) *Session {
|
||||||
session.Statement.Where(querystring, args...)
|
session.Statement.Where(query, args...)
|
||||||
return session
|
return session
|
||||||
}
|
}
|
||||||
|
|
||||||
// And provides custom query condition.
|
// And provides custom query condition.
|
||||||
func (session *Session) And(querystring string, args ...interface{}) *Session {
|
func (session *Session) And(query interface{}, args ...interface{}) *Session {
|
||||||
session.Statement.And(querystring, args...)
|
session.Statement.And(query, args...)
|
||||||
return session
|
return session
|
||||||
}
|
}
|
||||||
|
|
||||||
// Or provides custom query condition.
|
// Or provides custom query condition.
|
||||||
func (session *Session) Or(querystring string, args ...interface{}) *Session {
|
func (session *Session) Or(query interface{}, args ...interface{}) *Session {
|
||||||
session.Statement.Or(querystring, args...)
|
session.Statement.Or(query, args...)
|
||||||
return session
|
return session
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -189,6 +190,12 @@ func (session *Session) In(column string, args ...interface{}) *Session {
|
||||||
return session
|
return session
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// NotIn provides a query string like "id in (1, 2, 3)"
|
||||||
|
func (session *Session) NotIn(column string, args ...interface{}) *Session {
|
||||||
|
session.Statement.NotIn(column, args...)
|
||||||
|
return session
|
||||||
|
}
|
||||||
|
|
||||||
// Incr provides a query string like "count = count + 1"
|
// Incr provides a query string like "count = count + 1"
|
||||||
func (session *Session) Incr(column string, arg ...interface{}) *Session {
|
func (session *Session) Incr(column string, arg ...interface{}) *Session {
|
||||||
session.Statement.Incr(column, arg...)
|
session.Statement.Incr(column, arg...)
|
||||||
|
@ -892,15 +899,14 @@ func (session *Session) cacheFind(t reflect.Type, sqlStr string, rowsSlicePtr in
|
||||||
ff = append(ff, ie[0])
|
ff = append(ff, ie[0])
|
||||||
}
|
}
|
||||||
|
|
||||||
newSession.In(table.PrimaryKeys[0], ff...)
|
newSession.In("`"+table.PrimaryKeys[0]+"`", ff...)
|
||||||
} else {
|
} else {
|
||||||
var kn = make([]string, 0)
|
|
||||||
for _, name := range table.PrimaryKeys {
|
|
||||||
kn = append(kn, name+" = ?")
|
|
||||||
}
|
|
||||||
condi := "(" + strings.Join(kn, " AND ") + ")"
|
|
||||||
for _, ie := range ides {
|
for _, ie := range ides {
|
||||||
newSession.Or(condi, ie...)
|
cond := builder.NewCond()
|
||||||
|
for i, name := range table.PrimaryKeys {
|
||||||
|
cond = cond.And(builder.Eq{"`" + name + "`": ie[i]})
|
||||||
|
}
|
||||||
|
newSession.Or(cond)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1240,10 +1246,13 @@ func (session *Session) Find(rowsSlicePtr interface{}, condiBean ...interface{})
|
||||||
var table = session.Statement.RefTable
|
var table = session.Statement.RefTable
|
||||||
|
|
||||||
var addedTableName = (len(session.Statement.JoinStr) > 0)
|
var addedTableName = (len(session.Statement.JoinStr) > 0)
|
||||||
|
var autoCond builder.Cond
|
||||||
if !session.Statement.noAutoCondition && len(condiBean) > 0 {
|
if !session.Statement.noAutoCondition && len(condiBean) > 0 {
|
||||||
colNames, args := session.Statement.buildConditions(table, condiBean[0], true, true, false, true, addedTableName)
|
var err error
|
||||||
session.Statement.ConditionStr = strings.Join(colNames, " AND ")
|
autoCond, err = session.Statement.buildConds(table, condiBean[0], true, true, false, true, addedTableName)
|
||||||
session.Statement.BeanArgs = args
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// !oinume! Add "<col> IS NULL" to WHERE whatever condiBean is given.
|
// !oinume! Add "<col> IS NULL" to WHERE whatever condiBean is given.
|
||||||
// See https://github.com/go-xorm/xorm/issues/179
|
// See https://github.com/go-xorm/xorm/issues/179
|
||||||
|
@ -1256,8 +1265,7 @@ func (session *Session) Find(rowsSlicePtr interface{}, condiBean ...interface{})
|
||||||
}
|
}
|
||||||
colName = session.Engine.Quote(nm) + "." + colName
|
colName = session.Engine.Quote(nm) + "." + colName
|
||||||
}
|
}
|
||||||
session.Statement.ConditionStr = fmt.Sprintf("(%v IS NULL OR %v = '0001-01-01 00:00:00')",
|
autoCond = builder.IsNull{colName}.Or(builder.Eq{colName: "0001-01-01 00:00:00"})
|
||||||
colName, colName)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1291,12 +1299,10 @@ func (session *Session) Find(rowsSlicePtr interface{}, condiBean ...interface{})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
session.Statement.attachInSql()
|
condSQL, condArgs, _ := builder.ToSQL(session.Statement.cond.And(autoCond))
|
||||||
session.Statement.Params = append(append(append(session.Statement.joinArgs, session.Statement.Params...),
|
|
||||||
session.Statement.BeanArgs...), session.Statement.inParams...)
|
|
||||||
|
|
||||||
sqlStr = session.Statement.genSelectSQL(columnStr)
|
args = append(session.Statement.joinArgs, condArgs...)
|
||||||
args = session.Statement.Params
|
sqlStr = session.Statement.genSelectSQL(columnStr, condSQL)
|
||||||
// for mssql and use limit
|
// for mssql and use limit
|
||||||
qs := strings.Count(sqlStr, "?")
|
qs := strings.Count(sqlStr, "?")
|
||||||
if len(args)*2 == qs {
|
if len(args)*2 == qs {
|
||||||
|
@ -3567,97 +3573,68 @@ func (session *Session) Update(bean interface{}, condiBean ...interface{}) (int6
|
||||||
colNames = append(colNames, session.Engine.Quote(v.colName)+" = "+v.expr)
|
colNames = append(colNames, session.Engine.Quote(v.colName)+" = "+v.expr)
|
||||||
}
|
}
|
||||||
|
|
||||||
var condiColNames []string
|
session.Statement.processIdParam()
|
||||||
var condiArgs []interface{}
|
|
||||||
|
|
||||||
|
var autoCond builder.Cond
|
||||||
if !session.Statement.noAutoCondition && len(condiBean) > 0 {
|
if !session.Statement.noAutoCondition && len(condiBean) > 0 {
|
||||||
condiColNames, condiArgs = session.Statement.buildConditions(session.Statement.RefTable, condiBean[0], true, true, false, true, false)
|
var err error
|
||||||
|
autoCond, err = session.Statement.buildConds(session.Statement.RefTable, condiBean[0], true, true, false, true, false)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var condition = ""
|
|
||||||
session.Statement.processIdParam()
|
|
||||||
st := session.Statement
|
st := session.Statement
|
||||||
defer session.resetStatement()
|
defer session.resetStatement()
|
||||||
if st.WhereStr != "" {
|
|
||||||
condition = fmt.Sprintf("%v", st.WhereStr)
|
|
||||||
}
|
|
||||||
|
|
||||||
if condition == "" {
|
var sqlStr string
|
||||||
if len(condiColNames) > 0 {
|
var condArgs []interface{}
|
||||||
condition = fmt.Sprintf("%v", strings.Join(condiColNames, " "+session.Engine.Dialect().AndStr()+" "))
|
var condSQL string
|
||||||
}
|
cond := session.Statement.cond.And(autoCond)
|
||||||
} else {
|
|
||||||
if len(condiColNames) > 0 {
|
|
||||||
condition = fmt.Sprintf("(%v) %v (%v)", condition,
|
|
||||||
session.Engine.Dialect().AndStr(), strings.Join(condiColNames, " "+session.Engine.Dialect().AndStr()+" "))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
var sqlStr, inSQL string
|
|
||||||
var inArgs []interface{}
|
|
||||||
doIncVer := false
|
doIncVer := false
|
||||||
var verValue *reflect.Value
|
var verValue *reflect.Value
|
||||||
if table != nil && table.Version != "" && session.Statement.checkVersion {
|
if table != nil && table.Version != "" && session.Statement.checkVersion {
|
||||||
if condition != "" {
|
verValue, err = table.VersionColumn().ValueOf(bean)
|
||||||
condition = fmt.Sprintf("WHERE (%v) %v %v = ?", condition, session.Engine.Dialect().AndStr(),
|
if err != nil {
|
||||||
session.Engine.Quote(table.Version))
|
return 0, err
|
||||||
} else {
|
|
||||||
condition = fmt.Sprintf("WHERE %v = ?", session.Engine.Quote(table.Version))
|
|
||||||
}
|
|
||||||
inSQL, inArgs = session.Statement.genInSql()
|
|
||||||
if len(inSQL) > 0 {
|
|
||||||
if condition != "" {
|
|
||||||
condition += " " + session.Engine.Dialect().AndStr() + " " + inSQL
|
|
||||||
} else {
|
|
||||||
condition = "WHERE " + inSQL
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cond = cond.And(builder.Eq{session.Engine.Quote(table.Version): verValue.Interface()})
|
||||||
|
condSQL, condArgs, _ = builder.ToSQL(cond)
|
||||||
|
|
||||||
|
if len(condSQL) > 0 {
|
||||||
|
condSQL = "WHERE " + condSQL
|
||||||
}
|
}
|
||||||
|
|
||||||
if st.LimitN > 0 {
|
if st.LimitN > 0 {
|
||||||
condition = condition + fmt.Sprintf(" LIMIT %d", st.LimitN)
|
condSQL = condSQL + fmt.Sprintf(" LIMIT %d", st.LimitN)
|
||||||
}
|
}
|
||||||
|
|
||||||
sqlStr = fmt.Sprintf("UPDATE %v SET %v, %v %v",
|
sqlStr = fmt.Sprintf("UPDATE %v SET %v, %v %v",
|
||||||
session.Engine.Quote(session.Statement.TableName()),
|
session.Engine.Quote(session.Statement.TableName()),
|
||||||
strings.Join(colNames, ", "),
|
strings.Join(colNames, ", "),
|
||||||
session.Engine.Quote(table.Version)+" = "+session.Engine.Quote(table.Version)+" + 1",
|
session.Engine.Quote(table.Version)+" = "+session.Engine.Quote(table.Version)+" + 1",
|
||||||
condition)
|
condSQL)
|
||||||
|
|
||||||
verValue, err = table.VersionColumn().ValueOf(bean)
|
|
||||||
if err != nil {
|
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
|
|
||||||
condiArgs = append(condiArgs, verValue.Interface())
|
|
||||||
doIncVer = true
|
doIncVer = true
|
||||||
} else {
|
} else {
|
||||||
if condition != "" {
|
condSQL, condArgs, _ = builder.ToSQL(cond)
|
||||||
condition = "WHERE " + condition
|
if len(condSQL) > 0 {
|
||||||
}
|
condSQL = "WHERE " + condSQL
|
||||||
inSQL, inArgs = session.Statement.genInSql()
|
|
||||||
if len(inSQL) > 0 {
|
|
||||||
if condition != "" {
|
|
||||||
condition += " " + session.Engine.Dialect().AndStr() + " " + inSQL
|
|
||||||
} else {
|
|
||||||
condition = "WHERE " + inSQL
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if st.LimitN > 0 {
|
if st.LimitN > 0 {
|
||||||
condition = condition + fmt.Sprintf(" LIMIT %d", st.LimitN)
|
condSQL = condSQL + fmt.Sprintf(" LIMIT %d", st.LimitN)
|
||||||
}
|
}
|
||||||
|
|
||||||
sqlStr = fmt.Sprintf("UPDATE %v SET %v %v",
|
sqlStr = fmt.Sprintf("UPDATE %v SET %v %v",
|
||||||
session.Engine.Quote(session.Statement.TableName()),
|
session.Engine.Quote(session.Statement.TableName()),
|
||||||
strings.Join(colNames, ", "),
|
strings.Join(colNames, ", "),
|
||||||
condition)
|
condSQL)
|
||||||
}
|
}
|
||||||
|
|
||||||
args = append(args, st.Params...)
|
res, err := session.exec(sqlStr, append(args, condArgs...)...)
|
||||||
args = append(args, inArgs...)
|
|
||||||
args = append(args, condiArgs...)
|
|
||||||
|
|
||||||
res, err := session.exec(sqlStr, args...)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
} else if doIncVer {
|
} else if doIncVer {
|
||||||
|
@ -3791,41 +3768,27 @@ func (session *Session) Delete(bean interface{}) (int64, error) {
|
||||||
}
|
}
|
||||||
// --
|
// --
|
||||||
|
|
||||||
var colNames []string
|
var autoCond builder.Cond
|
||||||
var args []interface{}
|
|
||||||
|
|
||||||
if !session.Statement.noAutoCondition {
|
if !session.Statement.noAutoCondition {
|
||||||
colNames, args = session.Statement.buildConditions(table, bean, true, true, false, true, false)
|
var err error
|
||||||
|
autoCond, err = session.Statement.buildConds(table, bean, true, true, false, true, false)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
}
|
}
|
||||||
var condition = ""
|
|
||||||
var andStr = session.Engine.dialect.AndStr()
|
|
||||||
|
|
||||||
session.Statement.processIdParam()
|
session.Statement.processIdParam()
|
||||||
if session.Statement.WhereStr != "" {
|
|
||||||
condition = session.Statement.WhereStr
|
condSQL, condArgs, _ := builder.ToSQL(session.Statement.cond.And(autoCond))
|
||||||
if len(colNames) > 0 {
|
if len(condSQL) == 0 && session.Statement.LimitN == 0 {
|
||||||
condition += " " + andStr + " " + strings.Join(colNames, " "+andStr+" ")
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
condition = strings.Join(colNames, " "+andStr+" ")
|
|
||||||
}
|
|
||||||
inSQL, inArgs := session.Statement.genInSql()
|
|
||||||
if len(inSQL) > 0 {
|
|
||||||
if len(condition) > 0 {
|
|
||||||
condition += " " + andStr + " "
|
|
||||||
}
|
|
||||||
condition += inSQL
|
|
||||||
args = append(args, inArgs...)
|
|
||||||
}
|
|
||||||
if len(condition) == 0 && session.Statement.LimitN == 0 {
|
|
||||||
return 0, ErrNeedDeletedCond
|
return 0, ErrNeedDeletedCond
|
||||||
}
|
}
|
||||||
|
|
||||||
var deleteSQL, realSQL string
|
var deleteSQL, realSQL string
|
||||||
var tableName = session.Engine.Quote(session.Statement.TableName())
|
var tableName = session.Engine.Quote(session.Statement.TableName())
|
||||||
|
|
||||||
if len(condition) > 0 {
|
if len(condSQL) > 0 {
|
||||||
deleteSQL = fmt.Sprintf("DELETE FROM %v WHERE %v", tableName, condition)
|
deleteSQL = fmt.Sprintf("DELETE FROM %v WHERE %v", tableName, condSQL)
|
||||||
} else {
|
} else {
|
||||||
deleteSQL = fmt.Sprintf("DELETE FROM %v", tableName)
|
deleteSQL = fmt.Sprintf("DELETE FROM %v", tableName)
|
||||||
}
|
}
|
||||||
|
@ -3842,14 +3805,14 @@ func (session *Session) Delete(bean interface{}) (int64, error) {
|
||||||
switch session.Engine.dialect.DBType() {
|
switch session.Engine.dialect.DBType() {
|
||||||
case core.POSTGRES:
|
case core.POSTGRES:
|
||||||
inSQL := fmt.Sprintf("ctid IN (SELECT ctid FROM %s%s)", tableName, orderSQL)
|
inSQL := fmt.Sprintf("ctid IN (SELECT ctid FROM %s%s)", tableName, orderSQL)
|
||||||
if len(condition) > 0 {
|
if len(condSQL) > 0 {
|
||||||
deleteSQL += " AND " + inSQL
|
deleteSQL += " AND " + inSQL
|
||||||
} else {
|
} else {
|
||||||
deleteSQL += " WHERE " + inSQL
|
deleteSQL += " WHERE " + inSQL
|
||||||
}
|
}
|
||||||
case core.SQLITE:
|
case core.SQLITE:
|
||||||
inSQL := fmt.Sprintf("rowid IN (SELECT rowid FROM %s%s)", tableName, orderSQL)
|
inSQL := fmt.Sprintf("rowid IN (SELECT rowid FROM %s%s)", tableName, orderSQL)
|
||||||
if len(condition) > 0 {
|
if len(condSQL) > 0 {
|
||||||
deleteSQL += " AND " + inSQL
|
deleteSQL += " AND " + inSQL
|
||||||
} else {
|
} else {
|
||||||
deleteSQL += " WHERE " + inSQL
|
deleteSQL += " WHERE " + inSQL
|
||||||
|
@ -3862,34 +3825,34 @@ func (session *Session) Delete(bean interface{}) (int64, error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
argsForCache := make([]interface{}, 0, len(args)*2)
|
argsForCache := make([]interface{}, 0, len(condArgs)*2)
|
||||||
if session.Statement.unscoped || table.DeletedColumn() == nil { // tag "deleted" is disabled
|
if session.Statement.unscoped || table.DeletedColumn() == nil { // tag "deleted" is disabled
|
||||||
realSQL = deleteSQL
|
realSQL = deleteSQL
|
||||||
copy(argsForCache, args)
|
copy(argsForCache, condArgs)
|
||||||
argsForCache = append(session.Statement.Params, argsForCache...)
|
argsForCache = append(condArgs, argsForCache...)
|
||||||
} else {
|
} else {
|
||||||
// !oinume! sqlStrForCache and argsForCache is needed to behave as executing "DELETE FROM ..." for cache.
|
// !oinume! sqlStrForCache and argsForCache is needed to behave as executing "DELETE FROM ..." for cache.
|
||||||
copy(argsForCache, args)
|
copy(argsForCache, condArgs)
|
||||||
argsForCache = append(session.Statement.Params, argsForCache...)
|
argsForCache = append(condArgs, argsForCache...)
|
||||||
|
|
||||||
deletedColumn := table.DeletedColumn()
|
deletedColumn := table.DeletedColumn()
|
||||||
realSQL = fmt.Sprintf("UPDATE %v SET %v = ? WHERE %v",
|
realSQL = fmt.Sprintf("UPDATE %v SET %v = ? WHERE %v",
|
||||||
session.Engine.Quote(session.Statement.TableName()),
|
session.Engine.Quote(session.Statement.TableName()),
|
||||||
session.Engine.Quote(deletedColumn.Name),
|
session.Engine.Quote(deletedColumn.Name),
|
||||||
condition)
|
condSQL)
|
||||||
|
|
||||||
if len(orderSQL) > 0 {
|
if len(orderSQL) > 0 {
|
||||||
switch session.Engine.dialect.DBType() {
|
switch session.Engine.dialect.DBType() {
|
||||||
case core.POSTGRES:
|
case core.POSTGRES:
|
||||||
inSQL := fmt.Sprintf("ctid IN (SELECT ctid FROM %s%s)", tableName, orderSQL)
|
inSQL := fmt.Sprintf("ctid IN (SELECT ctid FROM %s%s)", tableName, orderSQL)
|
||||||
if len(condition) > 0 {
|
if len(condSQL) > 0 {
|
||||||
realSQL += " AND " + inSQL
|
realSQL += " AND " + inSQL
|
||||||
} else {
|
} else {
|
||||||
realSQL += " WHERE " + inSQL
|
realSQL += " WHERE " + inSQL
|
||||||
}
|
}
|
||||||
case core.SQLITE:
|
case core.SQLITE:
|
||||||
inSQL := fmt.Sprintf("rowid IN (SELECT rowid FROM %s%s)", tableName, orderSQL)
|
inSQL := fmt.Sprintf("rowid IN (SELECT rowid FROM %s%s)", tableName, orderSQL)
|
||||||
if len(condition) > 0 {
|
if len(condSQL) > 0 {
|
||||||
realSQL += " AND " + inSQL
|
realSQL += " AND " + inSQL
|
||||||
} else {
|
} else {
|
||||||
realSQL += " WHERE " + inSQL
|
realSQL += " WHERE " + inSQL
|
||||||
|
@ -3903,12 +3866,12 @@ func (session *Session) Delete(bean interface{}) (int64, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// !oinume! Insert NowTime to the head of session.Statement.Params
|
// !oinume! Insert NowTime to the head of session.Statement.Params
|
||||||
session.Statement.Params = append(session.Statement.Params, "")
|
condArgs = append(condArgs, "")
|
||||||
paramsLen := len(session.Statement.Params)
|
paramsLen := len(condArgs)
|
||||||
copy(session.Statement.Params[1:paramsLen], session.Statement.Params[0:paramsLen-1])
|
copy(condArgs[1:paramsLen], condArgs[0:paramsLen-1])
|
||||||
|
|
||||||
val, t := session.Engine.NowTime2(deletedColumn.SQLType.Name)
|
val, t := session.Engine.NowTime2(deletedColumn.SQLType.Name)
|
||||||
session.Statement.Params[0] = val
|
condArgs[0] = val
|
||||||
|
|
||||||
var colName = deletedColumn.Name
|
var colName = deletedColumn.Name
|
||||||
session.afterClosures = append(session.afterClosures, func(bean interface{}) {
|
session.afterClosures = append(session.afterClosures, func(bean interface{}) {
|
||||||
|
@ -3917,13 +3880,11 @@ func (session *Session) Delete(bean interface{}) (int64, error) {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
args = append(session.Statement.Params, args...)
|
|
||||||
|
|
||||||
if cacher := session.Engine.getCacher2(session.Statement.RefTable); cacher != nil && session.Statement.UseCache {
|
if cacher := session.Engine.getCacher2(session.Statement.RefTable); cacher != nil && session.Statement.UseCache {
|
||||||
session.cacheDelete(deleteSQL, argsForCache...)
|
session.cacheDelete(deleteSQL, argsForCache...)
|
||||||
}
|
}
|
||||||
|
|
||||||
res, err := session.exec(realSQL, args...)
|
res, err := session.exec(realSQL, condArgs...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
295
statement.go
295
statement.go
|
@ -14,14 +14,10 @@ import (
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
|
"github.com/go-xorm/builder"
|
||||||
"github.com/go-xorm/core"
|
"github.com/go-xorm/core"
|
||||||
)
|
)
|
||||||
|
|
||||||
type inParam struct {
|
|
||||||
colName string
|
|
||||||
args []interface{}
|
|
||||||
}
|
|
||||||
|
|
||||||
type incrParam struct {
|
type incrParam struct {
|
||||||
colName string
|
colName string
|
||||||
arg interface{}
|
arg interface{}
|
||||||
|
@ -43,10 +39,7 @@ type Statement struct {
|
||||||
Engine *Engine
|
Engine *Engine
|
||||||
Start int
|
Start int
|
||||||
LimitN int
|
LimitN int
|
||||||
WhereStr string
|
|
||||||
IdParam *core.PK
|
IdParam *core.PK
|
||||||
Params []interface{}
|
|
||||||
inParams []interface{}
|
|
||||||
OrderStr string
|
OrderStr string
|
||||||
JoinStr string
|
JoinStr string
|
||||||
joinArgs []interface{}
|
joinArgs []interface{}
|
||||||
|
@ -57,7 +50,6 @@ type Statement struct {
|
||||||
columnMap map[string]bool
|
columnMap map[string]bool
|
||||||
useAllCols bool
|
useAllCols bool
|
||||||
OmitStr string
|
OmitStr string
|
||||||
ConditionStr string
|
|
||||||
AltTableName string
|
AltTableName string
|
||||||
tableName string
|
tableName string
|
||||||
RawSQL string
|
RawSQL string
|
||||||
|
@ -66,7 +58,6 @@ type Statement struct {
|
||||||
UseAutoJoin bool
|
UseAutoJoin bool
|
||||||
StoreEngine string
|
StoreEngine string
|
||||||
Charset string
|
Charset string
|
||||||
BeanArgs []interface{}
|
|
||||||
UseCache bool
|
UseCache bool
|
||||||
UseAutoTime bool
|
UseAutoTime bool
|
||||||
noAutoCondition bool
|
noAutoCondition bool
|
||||||
|
@ -78,10 +69,10 @@ type Statement struct {
|
||||||
unscoped bool
|
unscoped bool
|
||||||
mustColumnMap map[string]bool
|
mustColumnMap map[string]bool
|
||||||
nullableMap map[string]bool
|
nullableMap map[string]bool
|
||||||
inColumns map[string]*inParam
|
|
||||||
incrColumns map[string]incrParam
|
incrColumns map[string]incrParam
|
||||||
decrColumns map[string]decrParam
|
decrColumns map[string]decrParam
|
||||||
exprColumns map[string]exprParam
|
exprColumns map[string]exprParam
|
||||||
|
cond builder.Cond
|
||||||
}
|
}
|
||||||
|
|
||||||
// Init reset all the statment's fields
|
// Init reset all the statment's fields
|
||||||
|
@ -89,9 +80,6 @@ func (statement *Statement) Init() {
|
||||||
statement.RefTable = nil
|
statement.RefTable = nil
|
||||||
statement.Start = 0
|
statement.Start = 0
|
||||||
statement.LimitN = 0
|
statement.LimitN = 0
|
||||||
statement.WhereStr = ""
|
|
||||||
statement.Params = make([]interface{}, 0)
|
|
||||||
statement.inParams = make([]interface{}, 0)
|
|
||||||
statement.OrderStr = ""
|
statement.OrderStr = ""
|
||||||
statement.UseCascade = true
|
statement.UseCascade = true
|
||||||
statement.JoinStr = ""
|
statement.JoinStr = ""
|
||||||
|
@ -101,13 +89,11 @@ func (statement *Statement) Init() {
|
||||||
statement.ColumnStr = ""
|
statement.ColumnStr = ""
|
||||||
statement.OmitStr = ""
|
statement.OmitStr = ""
|
||||||
statement.columnMap = make(map[string]bool)
|
statement.columnMap = make(map[string]bool)
|
||||||
statement.ConditionStr = ""
|
|
||||||
statement.AltTableName = ""
|
statement.AltTableName = ""
|
||||||
statement.tableName = ""
|
statement.tableName = ""
|
||||||
statement.IdParam = nil
|
statement.IdParam = nil
|
||||||
statement.RawSQL = ""
|
statement.RawSQL = ""
|
||||||
statement.RawParams = make([]interface{}, 0)
|
statement.RawParams = make([]interface{}, 0)
|
||||||
statement.BeanArgs = make([]interface{}, 0)
|
|
||||||
statement.UseCache = true
|
statement.UseCache = true
|
||||||
statement.UseAutoTime = true
|
statement.UseAutoTime = true
|
||||||
statement.noAutoCondition = false
|
statement.noAutoCondition = false
|
||||||
|
@ -121,10 +107,10 @@ func (statement *Statement) Init() {
|
||||||
statement.nullableMap = make(map[string]bool)
|
statement.nullableMap = make(map[string]bool)
|
||||||
statement.checkVersion = true
|
statement.checkVersion = true
|
||||||
statement.unscoped = false
|
statement.unscoped = false
|
||||||
statement.inColumns = make(map[string]*inParam)
|
|
||||||
statement.incrColumns = make(map[string]incrParam)
|
statement.incrColumns = make(map[string]incrParam)
|
||||||
statement.decrColumns = make(map[string]decrParam)
|
statement.decrColumns = make(map[string]decrParam)
|
||||||
statement.exprColumns = make(map[string]exprParam)
|
statement.exprColumns = make(map[string]exprParam)
|
||||||
|
statement.cond = builder.NewCond()
|
||||||
}
|
}
|
||||||
|
|
||||||
// NoAutoCondition if you do not want convert bean's field as query condition, then use this function
|
// NoAutoCondition if you do not want convert bean's field as query condition, then use this function
|
||||||
|
@ -136,6 +122,12 @@ func (statement *Statement) NoAutoCondition(no ...bool) *Statement {
|
||||||
return statement
|
return statement
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Alias set the table alias
|
||||||
|
func (statement *Statement) Alias(alias string) *Statement {
|
||||||
|
statement.TableAlias = alias
|
||||||
|
return statement
|
||||||
|
}
|
||||||
|
|
||||||
// Sql add the raw sql statement
|
// Sql add the raw sql statement
|
||||||
func (statement *Statement) Sql(querystring string, args ...interface{}) *Statement {
|
func (statement *Statement) Sql(querystring string, args ...interface{}) *Statement {
|
||||||
statement.RawSQL = querystring
|
statement.RawSQL = querystring
|
||||||
|
@ -143,52 +135,71 @@ func (statement *Statement) Sql(querystring string, args ...interface{}) *Statem
|
||||||
return statement
|
return statement
|
||||||
}
|
}
|
||||||
|
|
||||||
// Alias set the table alias
|
|
||||||
func (statement *Statement) Alias(alias string) *Statement {
|
|
||||||
statement.TableAlias = alias
|
|
||||||
return statement
|
|
||||||
}
|
|
||||||
|
|
||||||
// Where add Where statment
|
// Where add Where statment
|
||||||
func (statement *Statement) Where(querystring string, args ...interface{}) *Statement {
|
func (statement *Statement) Where(query interface{}, args ...interface{}) *Statement {
|
||||||
// The second where will be triggered as And
|
return statement.And(query, args...)
|
||||||
if len(statement.WhereStr) > 0 {
|
|
||||||
return statement.And(querystring, args...)
|
|
||||||
}
|
|
||||||
|
|
||||||
if !strings.Contains(querystring, statement.Engine.dialect.EqStr()) {
|
|
||||||
querystring = strings.Replace(querystring, "=", statement.Engine.dialect.EqStr(), -1)
|
|
||||||
}
|
|
||||||
statement.WhereStr = querystring
|
|
||||||
statement.Params = args
|
|
||||||
return statement
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// And add Where & and statment
|
// And add Where & and statment
|
||||||
func (statement *Statement) And(querystring string, args ...interface{}) *Statement {
|
func (statement *Statement) And(query interface{}, args ...interface{}) *Statement {
|
||||||
if len(statement.WhereStr) > 0 {
|
switch query.(type) {
|
||||||
var buf bytes.Buffer
|
case string:
|
||||||
fmt.Fprintf(&buf, "(%v) %s (%v)", statement.WhereStr,
|
cond := builder.Expr(query.(string), args...)
|
||||||
statement.Engine.dialect.AndStr(), querystring)
|
statement.cond = statement.cond.And(cond)
|
||||||
statement.WhereStr = buf.String()
|
case builder.Cond:
|
||||||
} else {
|
cond := query.(builder.Cond)
|
||||||
statement.WhereStr = querystring
|
statement.cond = statement.cond.And(cond)
|
||||||
|
for _, v := range args {
|
||||||
|
if vv, ok := v.(builder.Cond); ok {
|
||||||
|
statement.cond = statement.cond.And(vv)
|
||||||
}
|
}
|
||||||
statement.Params = append(statement.Params, args...)
|
}
|
||||||
|
default:
|
||||||
|
// TODO: not support condition type
|
||||||
|
}
|
||||||
|
|
||||||
return statement
|
return statement
|
||||||
}
|
}
|
||||||
|
|
||||||
// Or add Where & Or statment
|
// Or add Where & Or statment
|
||||||
func (statement *Statement) Or(querystring string, args ...interface{}) *Statement {
|
func (statement *Statement) Or(query interface{}, args ...interface{}) *Statement {
|
||||||
if len(statement.WhereStr) > 0 {
|
switch query.(type) {
|
||||||
var buf bytes.Buffer
|
case string:
|
||||||
fmt.Fprintf(&buf, "(%v) %s (%v)", statement.WhereStr,
|
cond := builder.Expr(query.(string), args...)
|
||||||
statement.Engine.dialect.OrStr(), querystring)
|
statement.cond = statement.cond.Or(cond)
|
||||||
statement.WhereStr = buf.String()
|
case builder.Cond:
|
||||||
} else {
|
cond := query.(builder.Cond)
|
||||||
statement.WhereStr = querystring
|
statement.cond = statement.cond.Or(cond)
|
||||||
|
for _, v := range args {
|
||||||
|
if vv, ok := v.(builder.Cond); ok {
|
||||||
|
statement.cond = statement.cond.Or(vv)
|
||||||
}
|
}
|
||||||
statement.Params = append(statement.Params, args...)
|
}
|
||||||
|
default:
|
||||||
|
// TODO: not support condition type
|
||||||
|
}
|
||||||
|
return statement
|
||||||
|
}
|
||||||
|
|
||||||
|
// In generate "Where column IN (?) " statment
|
||||||
|
func (statement *Statement) In(column string, args ...interface{}) *Statement {
|
||||||
|
if len(args) == 0 {
|
||||||
|
return statement
|
||||||
|
}
|
||||||
|
|
||||||
|
in := builder.In(column, args...)
|
||||||
|
statement.cond = statement.cond.And(in)
|
||||||
|
return statement
|
||||||
|
}
|
||||||
|
|
||||||
|
// NotIn generate "Where column IN (?) " statment
|
||||||
|
func (statement *Statement) NotIn(column string, args ...interface{}) *Statement {
|
||||||
|
if len(args) == 0 {
|
||||||
|
return statement
|
||||||
|
}
|
||||||
|
|
||||||
|
in := builder.NotIn(column, args...)
|
||||||
|
statement.cond = statement.cond.And(in)
|
||||||
return statement
|
return statement
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -459,13 +470,11 @@ func (statement *Statement) colName(col *core.Column, tableName string) string {
|
||||||
return statement.Engine.Quote(col.Name)
|
return statement.Engine.Quote(col.Name)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Auto generating conditions according a struct
|
func buildConds(engine *Engine, table *core.Table, bean interface{},
|
||||||
func buildConditions(engine *Engine, table *core.Table, bean interface{},
|
|
||||||
includeVersion bool, includeUpdated bool, includeNil bool,
|
includeVersion bool, includeUpdated bool, includeNil bool,
|
||||||
includeAutoIncr bool, allUseBool bool, useAllCols bool, unscoped bool,
|
includeAutoIncr bool, allUseBool bool, useAllCols bool, unscoped bool,
|
||||||
mustColumnMap map[string]bool, tableName, aliasName string, addedTableName bool) ([]string, []interface{}) {
|
mustColumnMap map[string]bool, tableName, aliasName string, addedTableName bool) (builder.Cond, error) {
|
||||||
var colNames []string
|
var conds []builder.Cond
|
||||||
var args = make([]interface{}, 0)
|
|
||||||
for _, col := range table.Columns() {
|
for _, col := range table.Columns() {
|
||||||
if !includeVersion && col.IsVersion {
|
if !includeVersion && col.IsVersion {
|
||||||
continue
|
continue
|
||||||
|
@ -502,8 +511,7 @@ func buildConditions(engine *Engine, table *core.Table, bean interface{},
|
||||||
}
|
}
|
||||||
|
|
||||||
if col.IsDeleted && !unscoped { // tag "deleted" is enabled
|
if col.IsDeleted && !unscoped { // tag "deleted" is enabled
|
||||||
colNames = append(colNames, fmt.Sprintf("(%v IS NULL OR %v = '0001-01-01 00:00:00')",
|
conds = append(conds, builder.IsNull{colName}.Or(builder.Eq{colName: "0001-01-01 00:00:00"}))
|
||||||
colName, colName))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fieldValue := *fieldValuePtr
|
fieldValue := *fieldValuePtr
|
||||||
|
@ -524,8 +532,7 @@ func buildConditions(engine *Engine, table *core.Table, bean interface{},
|
||||||
if fieldType.Kind() == reflect.Ptr {
|
if fieldType.Kind() == reflect.Ptr {
|
||||||
if fieldValue.IsNil() {
|
if fieldValue.IsNil() {
|
||||||
if includeNil {
|
if includeNil {
|
||||||
args = append(args, nil)
|
conds = append(conds, builder.Eq{colName: nil})
|
||||||
colNames = append(colNames, fmt.Sprintf("%v %s ?", colName, engine.dialect.EqStr()))
|
|
||||||
}
|
}
|
||||||
continue
|
continue
|
||||||
} else if !fieldValue.IsValid() {
|
} else if !fieldValue.IsValid() {
|
||||||
|
@ -668,17 +675,10 @@ func buildConditions(engine *Engine, table *core.Table, bean interface{},
|
||||||
val = fieldValue.Interface()
|
val = fieldValue.Interface()
|
||||||
}
|
}
|
||||||
|
|
||||||
args = append(args, val)
|
conds = append(conds, builder.Eq{colName: val})
|
||||||
var condi string
|
|
||||||
if col.IsPrimaryKey && engine.dialect.DBType() == "ql" {
|
|
||||||
condi = "id() == ?"
|
|
||||||
} else {
|
|
||||||
condi = fmt.Sprintf("%v %s ?", colName, engine.dialect.EqStr())
|
|
||||||
}
|
|
||||||
colNames = append(colNames, condi)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return colNames, args
|
return builder.And(conds...), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// TableName return current tableName
|
// TableName return current tableName
|
||||||
|
@ -762,70 +762,6 @@ func (statement *Statement) getExpr() map[string]exprParam {
|
||||||
return statement.exprColumns
|
return statement.exprColumns
|
||||||
}
|
}
|
||||||
|
|
||||||
// In generate "Where column IN (?) " statment
|
|
||||||
func (statement *Statement) In(column string, args ...interface{}) *Statement {
|
|
||||||
length := len(args)
|
|
||||||
if length == 0 {
|
|
||||||
return statement
|
|
||||||
}
|
|
||||||
|
|
||||||
k := strings.ToLower(column)
|
|
||||||
var newargs []interface{}
|
|
||||||
if length == 1 &&
|
|
||||||
reflect.TypeOf(args[0]).Kind() == reflect.Slice {
|
|
||||||
newargs = make([]interface{}, 0)
|
|
||||||
v := reflect.ValueOf(args[0])
|
|
||||||
for i := 0; i < v.Len(); i++ {
|
|
||||||
newargs = append(newargs, v.Index(i).Interface())
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
newargs = args
|
|
||||||
}
|
|
||||||
|
|
||||||
if _, ok := statement.inColumns[k]; ok {
|
|
||||||
statement.inColumns[k].args = append(statement.inColumns[k].args, newargs...)
|
|
||||||
} else {
|
|
||||||
statement.inColumns[k] = &inParam{column, newargs}
|
|
||||||
}
|
|
||||||
return statement
|
|
||||||
}
|
|
||||||
|
|
||||||
func (statement *Statement) genInSql() (string, []interface{}) {
|
|
||||||
if len(statement.inColumns) == 0 {
|
|
||||||
return "", []interface{}{}
|
|
||||||
}
|
|
||||||
|
|
||||||
inStrs := make([]string, len(statement.inColumns), len(statement.inColumns))
|
|
||||||
args := make([]interface{}, 0, len(statement.inColumns))
|
|
||||||
var buf bytes.Buffer
|
|
||||||
var i int
|
|
||||||
for _, params := range statement.inColumns {
|
|
||||||
buf.Reset()
|
|
||||||
fmt.Fprintf(&buf, "(%v IN (%v))",
|
|
||||||
statement.Engine.quoteColumn(params.colName),
|
|
||||||
strings.Join(makeArray("?", len(params.args)), ","))
|
|
||||||
inStrs[i] = buf.String()
|
|
||||||
i++
|
|
||||||
args = append(args, params.args...)
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(statement.inColumns) == 1 {
|
|
||||||
return inStrs[0], args
|
|
||||||
}
|
|
||||||
return fmt.Sprintf("(%v)", strings.Join(inStrs, " "+statement.Engine.dialect.AndStr()+" ")), args
|
|
||||||
}
|
|
||||||
|
|
||||||
func (statement *Statement) attachInSql() {
|
|
||||||
inSql, inArgs := statement.genInSql()
|
|
||||||
if len(inSql) > 0 {
|
|
||||||
if len(statement.ConditionStr) > 0 {
|
|
||||||
statement.ConditionStr += " " + statement.Engine.dialect.AndStr() + " "
|
|
||||||
}
|
|
||||||
statement.ConditionStr += inSql
|
|
||||||
statement.inParams = inArgs
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (statement *Statement) col2NewColsWithQuote(columns ...string) []string {
|
func (statement *Statement) col2NewColsWithQuote(columns ...string) []string {
|
||||||
newColumns := make([]string, 0)
|
newColumns := make([]string, 0)
|
||||||
for _, col := range columns {
|
for _, col := range columns {
|
||||||
|
@ -1134,12 +1070,16 @@ func (statement *Statement) genGetSql(bean interface{}) (string, []interface{})
|
||||||
var table = statement.RefTable
|
var table = statement.RefTable
|
||||||
var addedTableName = (len(statement.JoinStr) > 0)
|
var addedTableName = (len(statement.JoinStr) > 0)
|
||||||
|
|
||||||
|
var autoCond builder.Cond
|
||||||
if !statement.noAutoCondition {
|
if !statement.noAutoCondition {
|
||||||
colNames, args := statement.buildConditions(table, bean, true, true, false, true, addedTableName)
|
var err error
|
||||||
|
autoCond, err = statement.buildConds(table, bean, true, true, false, true, addedTableName)
|
||||||
statement.ConditionStr = strings.Join(colNames, " "+statement.Engine.dialect.AndStr()+" ")
|
if err != nil {
|
||||||
statement.BeanArgs = args
|
panic(err)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
statement.processIdParam()
|
||||||
|
|
||||||
var columnStr = statement.ColumnStr
|
var columnStr = statement.ColumnStr
|
||||||
if len(statement.selectStr) > 0 {
|
if len(statement.selectStr) > 0 {
|
||||||
|
@ -1165,9 +1105,9 @@ func (statement *Statement) genGetSql(bean interface{}) (string, []interface{})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
statement.attachInSql() // !admpub! fix bug:Iterate func missing "... IN (...)"
|
inSQL, inArgs, _ := builder.ToSQL(statement.cond.And(autoCond))
|
||||||
return statement.genSelectSQL(columnStr), append(append(append(statement.joinArgs, statement.Params...),
|
|
||||||
statement.BeanArgs...), statement.inParams...)
|
return statement.genSelectSQL(columnStr, inSQL), append(statement.joinArgs, inArgs...)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Statement) genAddColumnStr(col *core.Column) (string, []interface{}) {
|
func (s *Statement) genAddColumnStr(col *core.Column) (string, []interface{}) {
|
||||||
|
@ -1177,55 +1117,53 @@ func (s *Statement) genAddColumnStr(col *core.Column) (string, []interface{}) {
|
||||||
return sql, []interface{}{}
|
return sql, []interface{}{}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (statement *Statement) buildConditions(table *core.Table, bean interface{}, includeVersion bool, includeUpdated bool, includeNil bool, includeAutoIncr bool, addedTableName bool) ([]string, []interface{}) {
|
func (statement *Statement) buildConds(table *core.Table, bean interface{}, includeVersion bool, includeUpdated bool, includeNil bool, includeAutoIncr bool, addedTableName bool) (builder.Cond, error) {
|
||||||
return buildConditions(statement.Engine, table, bean, includeVersion, includeUpdated, includeNil, includeAutoIncr, statement.allUseBool, statement.useAllCols,
|
return buildConds(statement.Engine, table, bean, includeVersion, includeUpdated, includeNil, includeAutoIncr, statement.allUseBool, statement.useAllCols,
|
||||||
statement.unscoped, statement.mustColumnMap, statement.TableName(), statement.TableAlias, addedTableName)
|
statement.unscoped, statement.mustColumnMap, statement.TableName(), statement.TableAlias, addedTableName)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (statement *Statement) genCountSql(bean interface{}) (string, []interface{}) {
|
func (statement *Statement) genCountSql(bean interface{}) (string, []interface{}) {
|
||||||
statement.setRefValue(rValue(bean))
|
statement.setRefValue(rValue(bean))
|
||||||
|
|
||||||
var addedTableName = (len(statement.JoinStr) > 0)
|
var autoCond builder.Cond
|
||||||
|
|
||||||
if !statement.noAutoCondition {
|
if !statement.noAutoCondition {
|
||||||
colNames, args := statement.buildConditions(statement.RefTable, bean, true, true, false, true, addedTableName)
|
var err error
|
||||||
|
var addedTableName = (len(statement.JoinStr) > 0)
|
||||||
statement.ConditionStr = strings.Join(colNames, " "+statement.Engine.Dialect().AndStr()+" ")
|
autoCond, err = statement.buildConds(statement.RefTable, bean, true, true, false, true, addedTableName)
|
||||||
statement.BeanArgs = args
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// count(index fieldname) > count(0) > count(*)
|
// count(index fieldname) > count(0) > count(*)
|
||||||
var id = "*"
|
condSQL, condArgs, _ := builder.ToSQL(statement.cond.And(autoCond))
|
||||||
if statement.Engine.Dialect().DBType() == "ql" {
|
|
||||||
id = ""
|
return statement.genSelectSQL("count(*)", condSQL), append(statement.joinArgs, condArgs...)
|
||||||
}
|
|
||||||
statement.attachInSql()
|
|
||||||
return statement.genSelectSQL(fmt.Sprintf("count(%v)", id)), append(append(append(statement.joinArgs, statement.Params...),
|
|
||||||
statement.BeanArgs...), statement.inParams...)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (statement *Statement) genSumSql(bean interface{}, columns ...string) (string, []interface{}) {
|
func (statement *Statement) genSumSql(bean interface{}, columns ...string) (string, []interface{}) {
|
||||||
statement.setRefValue(rValue(bean))
|
statement.setRefValue(rValue(bean))
|
||||||
|
|
||||||
var addedTableName = (len(statement.JoinStr) > 0)
|
var addedTableName = (len(statement.JoinStr) > 0)
|
||||||
|
var autoCond builder.Cond
|
||||||
if !statement.noAutoCondition {
|
if !statement.noAutoCondition {
|
||||||
colNames, args := statement.buildConditions(statement.RefTable, bean, true, true, false, true, addedTableName)
|
var err error
|
||||||
|
autoCond, err = statement.buildConds(statement.RefTable, bean, true, true, false, true, addedTableName)
|
||||||
statement.ConditionStr = strings.Join(colNames, " "+statement.Engine.Dialect().AndStr()+" ")
|
if err != nil {
|
||||||
statement.BeanArgs = args
|
panic(err)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
statement.attachInSql()
|
condSQL, condArgs, _ := builder.ToSQL(statement.cond.And(autoCond))
|
||||||
|
|
||||||
var sumStrs = make([]string, 0, len(columns))
|
var sumStrs = make([]string, 0, len(columns))
|
||||||
for _, colName := range columns {
|
for _, colName := range columns {
|
||||||
sumStrs = append(sumStrs, fmt.Sprintf("COALESCE(sum(%s),0)", colName))
|
sumStrs = append(sumStrs, fmt.Sprintf("COALESCE(sum(%s),0)", colName))
|
||||||
}
|
}
|
||||||
return statement.genSelectSQL(strings.Join(sumStrs, ", ")), append(append(append(statement.joinArgs, statement.Params...),
|
return statement.genSelectSQL(strings.Join(sumStrs, ", "), condSQL), append(statement.joinArgs, condArgs...)
|
||||||
statement.BeanArgs...), statement.inParams...)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (statement *Statement) genSelectSQL(columnStr string) (a string) {
|
func (statement *Statement) genSelectSQL(columnStr, condSQL string) (a string) {
|
||||||
var distinct string
|
var distinct string
|
||||||
if statement.IsDistinct {
|
if statement.IsDistinct {
|
||||||
distinct = "DISTINCT "
|
distinct = "DISTINCT "
|
||||||
|
@ -1239,17 +1177,8 @@ func (statement *Statement) genSelectSQL(columnStr string) (a string) {
|
||||||
statement.processIdParam()
|
statement.processIdParam()
|
||||||
|
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if len(statement.WhereStr) > 0 {
|
if len(condSQL) > 0 {
|
||||||
if len(statement.ConditionStr) > 0 {
|
fmt.Fprintf(&buf, " WHERE %v", condSQL)
|
||||||
fmt.Fprintf(&buf, " WHERE (%v)", statement.WhereStr)
|
|
||||||
} else {
|
|
||||||
fmt.Fprintf(&buf, " WHERE %v", statement.WhereStr)
|
|
||||||
}
|
|
||||||
if statement.ConditionStr != "" {
|
|
||||||
fmt.Fprintf(&buf, " %s (%v)", dialect.AndStr(), statement.ConditionStr)
|
|
||||||
}
|
|
||||||
} else if len(statement.ConditionStr) > 0 {
|
|
||||||
fmt.Fprintf(&buf, " WHERE %v", statement.ConditionStr)
|
|
||||||
}
|
}
|
||||||
var whereStr = buf.String()
|
var whereStr = buf.String()
|
||||||
|
|
||||||
|
@ -1334,20 +1263,12 @@ func (statement *Statement) genSelectSQL(columnStr string) (a string) {
|
||||||
|
|
||||||
func (statement *Statement) processIdParam() {
|
func (statement *Statement) processIdParam() {
|
||||||
if statement.IdParam != nil {
|
if statement.IdParam != nil {
|
||||||
if statement.Engine.dialect.DBType() != "ql" {
|
|
||||||
for i, col := range statement.RefTable.PKColumns() {
|
for i, col := range statement.RefTable.PKColumns() {
|
||||||
var colName = statement.colName(col, statement.TableName())
|
var colName = statement.colName(col, statement.TableName())
|
||||||
if i < len(*(statement.IdParam)) {
|
if i < len(*(statement.IdParam)) {
|
||||||
statement.And(fmt.Sprintf("%v %s ?", colName,
|
statement.cond = statement.cond.And(builder.Eq{colName: (*(statement.IdParam))[i]})
|
||||||
statement.Engine.dialect.EqStr()), (*(statement.IdParam))[i])
|
|
||||||
} else {
|
} else {
|
||||||
statement.And(fmt.Sprintf("%v %s ?", colName,
|
statement.cond = statement.cond.And(builder.Eq{colName: ""})
|
||||||
statement.Engine.dialect.EqStr()), "")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if len(*(statement.IdParam)) <= 1 {
|
|
||||||
statement.And("id() == ?", (*(statement.IdParam))[0])
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue