add function Having for gdb.Model

This commit is contained in:
John
2020-04-11 10:11:52 +08:00
parent 385a503d31
commit c08739b5a3
5 changed files with 59 additions and 18 deletions

View File

@ -2,22 +2,9 @@ package main
import (
"fmt"
"github.com/gogf/gf/text/gregex"
"github.com/gogf/gf/text/gstr"
)
func main() {
s := `user u LEFT JOIN user_detail ud ON(ud.id=u.id) LEFT JOIN user_stats us ON(us.id=u.id)`
split := " JOIN "
as := "my-as"
if gstr.Contains(s, split) {
// For join table.
array := gstr.Split(s, split)
array[len(array)-1], _ = gregex.ReplaceString(`(.+) ON`, fmt.Sprintf(`$1 AS %s ON`, as), array[len(array)-1])
s = gstr.Join(array, split)
} else {
// For base table.
s = gstr.TrimRight(s) + " AS " + as
}
fmt.Println(s)
a := []interface{}{1}
fmt.Println(a[1])
}

View File

@ -28,6 +28,7 @@ type Model struct {
whereHolder []*whereHolder // Condition strings for where operation.
groupBy string // Used for "group by" statement.
orderBy string // Used for "order by" statement.
having []interface{} // Used for "having..." statement.
start int // Used for "select ... start, limit ..." statement.
limit int // Used for "select ... start, limit ..." statement.
option int // Option for extra operation features.

View File

@ -32,6 +32,17 @@ func (m *Model) Where(where interface{}, args ...interface{}) *Model {
return model
}
// Having sets the having statement for the model.
// The parameters of this function usage are as the same as function Where.
// See Where.
func (m *Model) Having(having interface{}, args ...interface{}) *Model {
model := m.getModel()
model.having = []interface{}{
having, args,
}
return model
}
// WherePri does the same logic as Model.Where except that if the parameter <where>
// is a single condition like int/string/float/slice, it treats the condition as the primary
// key value. That is, if primary key is "id" and given <where> parameter as "123", the

View File

@ -12,6 +12,7 @@ import (
"github.com/gogf/gf/internal/empty"
"github.com/gogf/gf/os/gtime"
"github.com/gogf/gf/text/gstr"
"github.com/gogf/gf/util/gconv"
"time"
)
@ -159,7 +160,9 @@ func (m *Model) formatCondition(limit bool) (conditionWhere string, conditionExt
switch v.operator {
case gWHERE_HOLDER_WHERE:
if conditionWhere == "" {
newWhere, newArgs := formatWhere(m.db, v.where, v.args, m.option&OPTION_OMITEMPTY > 0)
newWhere, newArgs := formatWhere(
m.db, v.where, v.args, m.option&OPTION_OMITEMPTY > 0,
)
if len(newWhere) > 0 {
conditionWhere = newWhere
conditionArgs = newArgs
@ -169,7 +172,9 @@ func (m *Model) formatCondition(limit bool) (conditionWhere string, conditionExt
fallthrough
case gWHERE_HOLDER_AND:
newWhere, newArgs := formatWhere(m.db, v.where, v.args, m.option&OPTION_OMITEMPTY > 0)
newWhere, newArgs := formatWhere(
m.db, v.where, v.args, m.option&OPTION_OMITEMPTY > 0,
)
if len(newWhere) > 0 {
if conditionWhere[0] == '(' {
conditionWhere = fmt.Sprintf(`%s AND (%s)`, conditionWhere, newWhere)
@ -180,7 +185,9 @@ func (m *Model) formatCondition(limit bool) (conditionWhere string, conditionExt
}
case gWHERE_HOLDER_OR:
newWhere, newArgs := formatWhere(m.db, v.where, v.args, m.option&OPTION_OMITEMPTY > 0)
newWhere, newArgs := formatWhere(
m.db, v.where, v.args, m.option&OPTION_OMITEMPTY > 0,
)
if len(newWhere) > 0 {
if conditionWhere[0] == '(' {
conditionWhere = fmt.Sprintf(`%s OR (%s)`, conditionWhere, newWhere)
@ -201,6 +208,15 @@ func (m *Model) formatCondition(limit bool) (conditionWhere string, conditionExt
if m.orderBy != "" {
conditionExtra += " ORDER BY " + m.orderBy
}
if len(m.having) > 0 {
havingStr, havingArgs := formatWhere(
m.db, m.having[0], gconv.Interfaces(m.having[1]), m.option&OPTION_OMITEMPTY > 0,
)
if len(havingStr) > 0 {
conditionExtra += " HAVING " + havingStr
conditionArgs = append(conditionArgs, havingArgs...)
}
}
if m.limit != 0 {
if m.start >= 0 {
conditionExtra += fmt.Sprintf(" LIMIT %d,%d", m.start, m.limit)

View File

@ -2200,3 +2200,29 @@ func Test_Model_Cache(t *testing.T) {
t.Assert(one["passport"], "user_200")
})
}
func Test_Model_Having(t *testing.T) {
table := createInitTable()
defer dropTable(table)
gtest.C(t, func(t *gtest.T) {
all, err := db.Table(table).Where("id > 1").Having("id > 8").All()
t.Assert(err, nil)
t.Assert(len(all), 2)
})
gtest.C(t, func(t *gtest.T) {
all, err := db.Table(table).Where("id > 1").Having("id > ?", 8).All()
t.Assert(err, nil)
t.Assert(len(all), 2)
})
gtest.C(t, func(t *gtest.T) {
all, err := db.Table(table).Where("id > ?", 1).Having("id > ?", 8).All()
t.Assert(err, nil)
t.Assert(len(all), 2)
})
gtest.C(t, func(t *gtest.T) {
all, err := db.Table(table).Where("id > ?", 1).Having("id", 8).All()
t.Assert(err, nil)
t.Assert(len(all), 1)
})
}