forked from mirror/gorm
Refact
This commit is contained in:
parent
f9658716e4
commit
f892a52cad
|
@ -0,0 +1,177 @@
|
||||||
|
package gorm
|
||||||
|
|
||||||
|
import (
|
||||||
|
"database/sql"
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"regexp"
|
||||||
|
|
||||||
|
"strconv"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Chain struct {
|
||||||
|
db *sql.DB
|
||||||
|
driver string
|
||||||
|
value interface{}
|
||||||
|
|
||||||
|
Errors []error
|
||||||
|
Error error
|
||||||
|
|
||||||
|
whereClause []map[string]interface{}
|
||||||
|
orClause []map[string]interface{}
|
||||||
|
selectStr string
|
||||||
|
orderStrs []string
|
||||||
|
offsetStr string
|
||||||
|
limitStr string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) err(err error) {
|
||||||
|
if err != nil {
|
||||||
|
s.Errors = append(s.Errors, err)
|
||||||
|
s.Error = err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) do(value interface{}) *Do {
|
||||||
|
var do Do
|
||||||
|
do.chain = s
|
||||||
|
do.db = s.db
|
||||||
|
do.driver = s.driver
|
||||||
|
|
||||||
|
do.whereClause = s.whereClause
|
||||||
|
do.orClause = s.orClause
|
||||||
|
do.selectStr = s.selectStr
|
||||||
|
do.orderStrs = s.orderStrs
|
||||||
|
do.offsetStr = s.offsetStr
|
||||||
|
do.limitStr = s.limitStr
|
||||||
|
|
||||||
|
do.setModel(value)
|
||||||
|
return &do
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Model(model interface{}) *Chain {
|
||||||
|
s.value = model
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Where(querystring interface{}, args ...interface{}) *Chain {
|
||||||
|
s.whereClause = append(s.whereClause, map[string]interface{}{"query": querystring, "args": args})
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Limit(value interface{}) *Chain {
|
||||||
|
switch value := value.(type) {
|
||||||
|
case string:
|
||||||
|
s.limitStr = value
|
||||||
|
case int:
|
||||||
|
if value < 0 {
|
||||||
|
s.limitStr = ""
|
||||||
|
} else {
|
||||||
|
s.limitStr = strconv.Itoa(value)
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
s.err(errors.New("Can' understand the value of Limit, Should be int"))
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Offset(value interface{}) *Chain {
|
||||||
|
switch value := value.(type) {
|
||||||
|
case string:
|
||||||
|
s.offsetStr = value
|
||||||
|
case int:
|
||||||
|
if value < 0 {
|
||||||
|
s.offsetStr = ""
|
||||||
|
} else {
|
||||||
|
s.offsetStr = strconv.Itoa(value)
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
s.err(errors.New("Can' understand the value of Offset, Should be int"))
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Order(value string, reorder ...bool) *Chain {
|
||||||
|
defer s.validSql(value)
|
||||||
|
if len(reorder) > 0 && reorder[0] {
|
||||||
|
s.orderStrs = append([]string{}, value)
|
||||||
|
} else {
|
||||||
|
s.orderStrs = append(s.orderStrs, value)
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Count() int64 {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Select(value interface{}) *Chain {
|
||||||
|
defer func() { s.validSql(s.selectStr) }()
|
||||||
|
|
||||||
|
switch value := value.(type) {
|
||||||
|
case string:
|
||||||
|
s.selectStr = value
|
||||||
|
default:
|
||||||
|
s.err(errors.New("Can' understand the value of Select, Should be string"))
|
||||||
|
}
|
||||||
|
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Save(value interface{}) *Chain {
|
||||||
|
s.do(value).save()
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Delete(value interface{}) *Chain {
|
||||||
|
s.do(value).delete()
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Update(column string, value string) *Chain {
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Updates(values map[string]string) *Chain {
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Exec(sql string) *Chain {
|
||||||
|
var err error
|
||||||
|
_, err = s.db.Exec(sql)
|
||||||
|
s.err(err)
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) First(out interface{}) *Chain {
|
||||||
|
s.do(out).query()
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Find(out interface{}) *Chain {
|
||||||
|
s.do(out).query()
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Pluck(column string, value interface{}) (orm *Chain) {
|
||||||
|
s.Select(column).do(s.value).pluck(value)
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) Or(querystring interface{}, args ...interface{}) *Chain {
|
||||||
|
s.orClause = append(s.orClause, map[string]interface{}{"query": querystring, "args": args})
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) CreateTable(value interface{}) *Chain {
|
||||||
|
s.do(value).createTable().Exec()
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Chain) validSql(str string) (result bool) {
|
||||||
|
result = regexp.MustCompile("^\\s*[\\w][\\w\\s,.]*[\\w]\\s*$").MatchString(str)
|
||||||
|
if !result {
|
||||||
|
s.err(errors.New(fmt.Sprintf("SQL is not valid, %s", str)))
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
286
sql.go → do.go
286
sql.go → do.go
|
@ -1,59 +1,182 @@
|
||||||
package gorm
|
package gorm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"database/sql"
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"reflect"
|
"reflect"
|
||||||
"regexp"
|
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (s *Orm) validSql(str string) (result bool) {
|
type Do struct {
|
||||||
result = regexp.MustCompile("^\\s*[\\w][\\w\\s,.]*[\\w]\\s*$").MatchString(str)
|
chain *Chain
|
||||||
if !result {
|
db *sql.DB
|
||||||
s.err(errors.New(fmt.Sprintf("SQL is not valid, %s", str)))
|
driver string
|
||||||
}
|
TableName string
|
||||||
return
|
Errors []error
|
||||||
|
|
||||||
|
model *Model
|
||||||
|
value interface{}
|
||||||
|
SqlResult sql.Result
|
||||||
|
|
||||||
|
Sql string
|
||||||
|
SqlVars []interface{}
|
||||||
|
|
||||||
|
whereClause []map[string]interface{}
|
||||||
|
orClause []map[string]interface{}
|
||||||
|
selectStr string
|
||||||
|
orderStrs []string
|
||||||
|
offsetStr string
|
||||||
|
limitStr string
|
||||||
|
operation string
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) explain(value interface{}, operation string) *Orm {
|
func (s *Do) err(err error) {
|
||||||
s.Model(value)
|
if err != nil {
|
||||||
|
s.Errors = append(s.Errors, err)
|
||||||
|
s.chain.err(err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
switch operation {
|
func (s *Do) setModel(value interface{}) {
|
||||||
case "Create":
|
s.value = value
|
||||||
s.createSql(value)
|
s.model = &Model{Data: value, driver: s.driver}
|
||||||
case "Update":
|
s.TableName = s.model.TableName()
|
||||||
s.updateSql(value)
|
}
|
||||||
case "Delete":
|
|
||||||
s.deleteSql(value)
|
func (s *Do) addToVars(value interface{}) string {
|
||||||
case "Query":
|
s.SqlVars = append(s.SqlVars, value)
|
||||||
s.querySql(value)
|
return fmt.Sprintf("$%d", len(s.SqlVars))
|
||||||
case "CreateTable":
|
}
|
||||||
s.Sql = s.model.CreateTable()
|
|
||||||
|
func (s *Do) Exec(sql ...string) {
|
||||||
|
var err error
|
||||||
|
if len(sql) == 0 {
|
||||||
|
s.SqlResult, err = s.db.Exec(s.Sql, s.SqlVars...)
|
||||||
|
} else {
|
||||||
|
s.SqlResult, err = s.db.Exec(sql[0])
|
||||||
|
}
|
||||||
|
s.err(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) save() *Do {
|
||||||
|
if s.model.PrimaryKeyZero() {
|
||||||
|
s.create()
|
||||||
|
} else {
|
||||||
|
s.update()
|
||||||
}
|
}
|
||||||
return s
|
return s
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) querySql(out interface{}) {
|
func (s *Do) prepareCreateSql() *Do {
|
||||||
s.Sql = fmt.Sprintf("SELECT %v FROM %v %v", s.selectSql(), s.TableName, s.combinedSql())
|
columns, values := s.model.ColumnsAndValues("create")
|
||||||
return
|
|
||||||
|
var sqls []string
|
||||||
|
for _, value := range values {
|
||||||
|
sqls = append(sqls, s.addToVars(value))
|
||||||
|
}
|
||||||
|
|
||||||
|
s.Sql = fmt.Sprintf(
|
||||||
|
"INSERT INTO \"%v\" (%v) VALUES (%v) %v",
|
||||||
|
s.TableName,
|
||||||
|
strings.Join(s.quoteMap(columns), ","),
|
||||||
|
strings.Join(sqls, ","),
|
||||||
|
s.model.ReturningStr(),
|
||||||
|
)
|
||||||
|
return s
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) query(out interface{}) {
|
func (s *Do) create() *Do {
|
||||||
|
s.err(s.model.callMethod("BeforeCreate"))
|
||||||
|
s.err(s.model.callMethod("BeforeSave"))
|
||||||
|
|
||||||
|
s.prepareCreateSql()
|
||||||
|
|
||||||
|
if len(s.Errors) == 0 {
|
||||||
|
var id int64
|
||||||
|
if s.driver == "postgres" {
|
||||||
|
s.err(s.db.QueryRow(s.Sql, s.SqlVars...).Scan(&id))
|
||||||
|
} else {
|
||||||
|
var err error
|
||||||
|
s.SqlResult, err = s.db.Exec(s.Sql, s.SqlVars...)
|
||||||
|
s.err(err)
|
||||||
|
id, err = s.SqlResult.LastInsertId()
|
||||||
|
s.err(err)
|
||||||
|
}
|
||||||
|
result := reflect.ValueOf(s.model.Data).Elem()
|
||||||
|
result.FieldByName(s.model.PrimaryKey()).SetInt(id)
|
||||||
|
|
||||||
|
s.err(s.model.callMethod("AfterCreate"))
|
||||||
|
s.err(s.model.callMethod("AfterSave"))
|
||||||
|
}
|
||||||
|
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) prepareUpdateSql() *Do {
|
||||||
|
columns, values := s.model.ColumnsAndValues("update")
|
||||||
|
var sets []string
|
||||||
|
for index, column := range columns {
|
||||||
|
sets = append(sets, fmt.Sprintf("%v = %v", s.quote(column), s.addToVars(values[index])))
|
||||||
|
}
|
||||||
|
|
||||||
|
s.Sql = fmt.Sprintf(
|
||||||
|
"UPDATE %v SET %v %v",
|
||||||
|
s.TableName,
|
||||||
|
strings.Join(sets, ", "),
|
||||||
|
s.combinedSql(),
|
||||||
|
)
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) update() *Do {
|
||||||
|
s.err(s.model.callMethod("BeforeUpdate"))
|
||||||
|
s.err(s.model.callMethod("BeforeSave"))
|
||||||
|
if len(s.Errors) == 0 {
|
||||||
|
s.prepareUpdateSql().Exec()
|
||||||
|
}
|
||||||
|
s.err(s.model.callMethod("AfterUpdate"))
|
||||||
|
s.err(s.model.callMethod("AfterSave"))
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) prepareDeleteSql() *Do {
|
||||||
|
s.Sql = fmt.Sprintf("DELETE FROM %v %v", s.TableName, s.combinedSql())
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) delete() *Do {
|
||||||
|
s.err(s.model.callMethod("BeforeDelete"))
|
||||||
|
if len(s.Errors) == 0 {
|
||||||
|
s.prepareDeleteSql().Exec()
|
||||||
|
}
|
||||||
|
s.err(s.model.callMethod("AfterDelete"))
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) prepareQuerySql() *Do {
|
||||||
|
s.Sql = fmt.Sprintf("SELECT %v FROM %v %v", s.selectSql(), s.TableName, s.combinedSql())
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Do) query() {
|
||||||
var (
|
var (
|
||||||
is_slice bool
|
is_slice bool
|
||||||
dest_type reflect.Type
|
dest_type reflect.Type
|
||||||
)
|
)
|
||||||
dest_out := reflect.Indirect(reflect.ValueOf(out))
|
dest_out := reflect.Indirect(reflect.ValueOf(s.value))
|
||||||
|
|
||||||
if x := dest_out.Kind(); x == reflect.Slice {
|
if x := dest_out.Kind(); x == reflect.Slice {
|
||||||
is_slice = true
|
is_slice = true
|
||||||
dest_type = dest_out.Type().Elem()
|
dest_type = dest_out.Type().Elem()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
s.prepareQuerySql()
|
||||||
rows, err := s.db.Query(s.Sql, s.SqlVars...)
|
rows, err := s.db.Query(s.Sql, s.SqlVars...)
|
||||||
defer rows.Close()
|
defer rows.Close()
|
||||||
s.err(err)
|
s.err(err)
|
||||||
|
|
||||||
if rows.Err() != nil {
|
if rows.Err() != nil {
|
||||||
s.err(rows.Err())
|
s.err(rows.Err())
|
||||||
}
|
}
|
||||||
|
@ -65,7 +188,7 @@ func (s *Orm) query(out interface{}) {
|
||||||
if is_slice {
|
if is_slice {
|
||||||
dest = reflect.New(dest_type).Elem()
|
dest = reflect.New(dest_type).Elem()
|
||||||
} else {
|
} else {
|
||||||
dest = reflect.ValueOf(out).Elem()
|
dest = reflect.ValueOf(s.value).Elem()
|
||||||
}
|
}
|
||||||
|
|
||||||
columns, _ := rows.Columns()
|
columns, _ := rows.Columns()
|
||||||
|
@ -85,10 +208,10 @@ func (s *Orm) query(out interface{}) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) pluck(value interface{}) {
|
func (s *Do) pluck(value interface{}) *Do {
|
||||||
dest_out := reflect.Indirect(reflect.ValueOf(value))
|
dest_out := reflect.Indirect(reflect.ValueOf(value))
|
||||||
dest_type := dest_out.Type().Elem()
|
dest_type := dest_out.Type().Elem()
|
||||||
|
s.prepareQuerySql()
|
||||||
rows, err := s.db.Query(s.Sql, s.SqlVars...)
|
rows, err := s.db.Query(s.Sql, s.SqlVars...)
|
||||||
s.err(err)
|
s.err(err)
|
||||||
|
|
||||||
|
@ -106,93 +229,10 @@ func (s *Orm) pluck(value interface{}) {
|
||||||
dest_out.Set(reflect.Append(dest_out, reflect.ValueOf(dest)))
|
dest_out.Set(reflect.Append(dest_out, reflect.ValueOf(dest)))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return
|
return s
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) createSql(value interface{}) {
|
func (s *Do) buildWhereCondition(clause map[string]interface{}) string {
|
||||||
columns, values := s.model.ColumnsAndValues("create")
|
|
||||||
|
|
||||||
var sqls []string
|
|
||||||
for _, value := range values {
|
|
||||||
sqls = append(sqls, s.addToVars(value))
|
|
||||||
}
|
|
||||||
|
|
||||||
s.Sql = fmt.Sprintf(
|
|
||||||
"INSERT INTO \"%v\" (%v) VALUES (%v) %v",
|
|
||||||
s.TableName,
|
|
||||||
strings.Join(s.quoteMap(columns), ","),
|
|
||||||
strings.Join(sqls, ","),
|
|
||||||
s.model.ReturningStr(),
|
|
||||||
)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) create(value interface{}) {
|
|
||||||
var id int64
|
|
||||||
s.err(s.model.callMethod("BeforeCreate"))
|
|
||||||
s.err(s.model.callMethod("BeforeSave"))
|
|
||||||
s.explain(value, "Create")
|
|
||||||
|
|
||||||
if len(s.Errors) == 0 {
|
|
||||||
if s.driver == "postgres" {
|
|
||||||
s.err(s.db.QueryRow(s.Sql, s.SqlVars...).Scan(&id))
|
|
||||||
} else {
|
|
||||||
var err error
|
|
||||||
s.SqlResult, err = s.db.Exec(s.Sql, s.SqlVars...)
|
|
||||||
s.err(err)
|
|
||||||
id, err = s.SqlResult.LastInsertId()
|
|
||||||
s.err(err)
|
|
||||||
}
|
|
||||||
result := reflect.ValueOf(s.model.Data).Elem()
|
|
||||||
result.FieldByName(s.model.PrimaryKey()).SetInt(id)
|
|
||||||
|
|
||||||
s.err(s.model.callMethod("AfterCreate"))
|
|
||||||
s.err(s.model.callMethod("AfterSave"))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) updateSql(value interface{}) {
|
|
||||||
columns, values := s.model.ColumnsAndValues("update")
|
|
||||||
var sets []string
|
|
||||||
for index, column := range columns {
|
|
||||||
sets = append(sets, fmt.Sprintf("%v = %v", s.quote(column), s.addToVars(values[index])))
|
|
||||||
}
|
|
||||||
|
|
||||||
s.Sql = fmt.Sprintf(
|
|
||||||
"UPDATE %v SET %v %v",
|
|
||||||
s.TableName,
|
|
||||||
strings.Join(sets, ", "),
|
|
||||||
s.combinedSql(),
|
|
||||||
)
|
|
||||||
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) update(value interface{}) {
|
|
||||||
s.err(s.model.callMethod("BeforeUpdate"))
|
|
||||||
s.err(s.model.callMethod("BeforeSave"))
|
|
||||||
if len(s.Errors) == 0 {
|
|
||||||
s.explain(value, "Update").Exec()
|
|
||||||
}
|
|
||||||
s.err(s.model.callMethod("AfterUpdate"))
|
|
||||||
s.err(s.model.callMethod("AfterSave"))
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) deleteSql(value interface{}) {
|
|
||||||
s.Sql = fmt.Sprintf("DELETE FROM %v %v", s.TableName, s.combinedSql())
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) delete(value interface{}) {
|
|
||||||
s.err(s.model.callMethod("BeforeDelete"))
|
|
||||||
if len(s.Errors) == 0 {
|
|
||||||
s.Exec()
|
|
||||||
}
|
|
||||||
s.err(s.model.callMethod("AfterDelete"))
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) buildWhereCondition(clause map[string]interface{}) string {
|
|
||||||
str := "( " + clause["query"].(string) + " )"
|
str := "( " + clause["query"].(string) + " )"
|
||||||
|
|
||||||
args := clause["args"].([]interface{})
|
args := clause["args"].([]interface{})
|
||||||
|
@ -218,11 +258,11 @@ func (s *Orm) buildWhereCondition(clause map[string]interface{}) string {
|
||||||
return str
|
return str
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) whereSql() (sql string) {
|
func (s *Do) whereSql() (sql string) {
|
||||||
var primary_condiation string
|
var primary_condiation string
|
||||||
var and_conditions, or_conditions []string
|
var and_conditions, or_conditions []string
|
||||||
|
|
||||||
if !s.model.PrimaryKeyIsEmpty() {
|
if !s.model.PrimaryKeyZero() {
|
||||||
primary_condiation = fmt.Sprintf("(%v = %v)", s.quote(s.model.PrimaryKeyDb()), s.addToVars(s.model.PrimaryKeyValue()))
|
primary_condiation = fmt.Sprintf("(%v = %v)", s.quote(s.model.PrimaryKeyDb()), s.addToVars(s.model.PrimaryKeyValue()))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -256,7 +296,7 @@ func (s *Orm) whereSql() (sql string) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) selectSql() string {
|
func (s *Do) selectSql() string {
|
||||||
if len(s.selectStr) == 0 {
|
if len(s.selectStr) == 0 {
|
||||||
return " * "
|
return " * "
|
||||||
} else {
|
} else {
|
||||||
|
@ -264,7 +304,7 @@ func (s *Orm) selectSql() string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) orderSql() string {
|
func (s *Do) orderSql() string {
|
||||||
if len(s.orderStrs) == 0 {
|
if len(s.orderStrs) == 0 {
|
||||||
return ""
|
return ""
|
||||||
} else {
|
} else {
|
||||||
|
@ -272,7 +312,7 @@ func (s *Orm) orderSql() string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) limitSql() string {
|
func (s *Do) limitSql() string {
|
||||||
if len(s.limitStr) == 0 {
|
if len(s.limitStr) == 0 {
|
||||||
return ""
|
return ""
|
||||||
} else {
|
} else {
|
||||||
|
@ -280,7 +320,7 @@ func (s *Orm) limitSql() string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) offsetSql() string {
|
func (s *Do) offsetSql() string {
|
||||||
if len(s.offsetStr) == 0 {
|
if len(s.offsetStr) == 0 {
|
||||||
return ""
|
return ""
|
||||||
} else {
|
} else {
|
||||||
|
@ -288,11 +328,11 @@ func (s *Orm) offsetSql() string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) combinedSql() string {
|
func (s *Do) combinedSql() string {
|
||||||
return s.whereSql() + s.orderSql() + s.limitSql() + s.offsetSql()
|
return s.whereSql() + s.orderSql() + s.limitSql() + s.offsetSql()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) addToVars(value interface{}) string {
|
func (s *Do) createTable() *Do {
|
||||||
s.SqlVars = append(s.SqlVars, value)
|
s.Sql = s.model.CreateTable()
|
||||||
return fmt.Sprintf("$%d", len(s.SqlVars))
|
return s
|
||||||
}
|
}
|
28
main.go
28
main.go
|
@ -17,54 +17,54 @@ func Open(driver, source string) (db DB, err error) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) buildORM() *Orm {
|
func (s *DB) buildORM() *Chain {
|
||||||
return &Orm{db: s.Db, driver: s.Driver}
|
return &Chain{db: s.Db, driver: s.Driver}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Where(querystring interface{}, args ...interface{}) *Orm {
|
func (s *DB) Where(querystring interface{}, args ...interface{}) *Chain {
|
||||||
return s.buildORM().Where(querystring, args...)
|
return s.buildORM().Where(querystring, args...)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) First(out interface{}) *Orm {
|
func (s *DB) First(out interface{}) *Chain {
|
||||||
return s.buildORM().First(out)
|
return s.buildORM().First(out)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Find(out interface{}) *Orm {
|
func (s *DB) Find(out interface{}) *Chain {
|
||||||
return s.buildORM().Find(out)
|
return s.buildORM().Find(out)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Limit(value interface{}) *Orm {
|
func (s *DB) Limit(value interface{}) *Chain {
|
||||||
return s.buildORM().Limit(value)
|
return s.buildORM().Limit(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Offset(value interface{}) *Orm {
|
func (s *DB) Offset(value interface{}) *Chain {
|
||||||
return s.buildORM().Offset(value)
|
return s.buildORM().Offset(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Order(value string, reorder ...bool) *Orm {
|
func (s *DB) Order(value string, reorder ...bool) *Chain {
|
||||||
return s.buildORM().Order(value, reorder...)
|
return s.buildORM().Order(value, reorder...)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Select(value interface{}) *Orm {
|
func (s *DB) Select(value interface{}) *Chain {
|
||||||
return s.buildORM().Select(value)
|
return s.buildORM().Select(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Save(value interface{}) *Orm {
|
func (s *DB) Save(value interface{}) *Chain {
|
||||||
return s.buildORM().Save(value)
|
return s.buildORM().Save(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Delete(value interface{}) *Orm {
|
func (s *DB) Delete(value interface{}) *Chain {
|
||||||
return s.buildORM().Delete(value)
|
return s.buildORM().Delete(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Exec(sql string) *Orm {
|
func (s *DB) Exec(sql string) *Chain {
|
||||||
return s.buildORM().Exec(sql)
|
return s.buildORM().Exec(sql)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) Model(value interface{}) *Orm {
|
func (s *DB) Model(value interface{}) *Chain {
|
||||||
return s.buildORM().Model(value)
|
return s.buildORM().Model(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DB) CreateTable(value interface{}) *Orm {
|
func (s *DB) CreateTable(value interface{}) *Chain {
|
||||||
return s.buildORM().CreateTable(value)
|
return s.buildORM().CreateTable(value)
|
||||||
}
|
}
|
||||||
|
|
6
model.go
6
model.go
|
@ -23,11 +23,7 @@ type Field struct {
|
||||||
IsPrimaryKey bool
|
IsPrimaryKey bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) toModel(value interface{}) *Model {
|
func (m *Model) PrimaryKeyZero() bool {
|
||||||
return &Model{Data: value, driver: s.driver}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (m *Model) PrimaryKeyIsEmpty() bool {
|
|
||||||
return m.PrimaryKeyValue() == 0
|
return m.PrimaryKeyValue() == 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
173
orm.go
173
orm.go
|
@ -1,173 +0,0 @@
|
||||||
package gorm
|
|
||||||
|
|
||||||
import (
|
|
||||||
"database/sql"
|
|
||||||
"errors"
|
|
||||||
|
|
||||||
"strconv"
|
|
||||||
)
|
|
||||||
|
|
||||||
type Orm struct {
|
|
||||||
TableName string
|
|
||||||
PrimaryKey string
|
|
||||||
SqlResult sql.Result
|
|
||||||
Sql string
|
|
||||||
SqlVars []interface{}
|
|
||||||
model *Model
|
|
||||||
|
|
||||||
Errors []error
|
|
||||||
Error error
|
|
||||||
|
|
||||||
db *sql.DB
|
|
||||||
driver string
|
|
||||||
whereClause []map[string]interface{}
|
|
||||||
orClause []map[string]interface{}
|
|
||||||
selectStr string
|
|
||||||
orderStrs []string
|
|
||||||
offsetStr string
|
|
||||||
limitStr string
|
|
||||||
operation string
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) err(err error) {
|
|
||||||
if err != nil {
|
|
||||||
s.Errors = append(s.Errors, err)
|
|
||||||
s.Error = err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Copy() *Orm {
|
|
||||||
c := *s
|
|
||||||
c.SqlVars = c.SqlVars[:0]
|
|
||||||
return &c
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Model(model interface{}) *Orm {
|
|
||||||
s.model = s.toModel(model)
|
|
||||||
s.TableName = s.model.TableName()
|
|
||||||
s.PrimaryKey = s.model.PrimaryKeyDb()
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Where(querystring interface{}, args ...interface{}) *Orm {
|
|
||||||
s.whereClause = append(s.whereClause, map[string]interface{}{"query": querystring, "args": args})
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Limit(value interface{}) *Orm {
|
|
||||||
switch value := value.(type) {
|
|
||||||
case string:
|
|
||||||
s.limitStr = value
|
|
||||||
case int:
|
|
||||||
if value < 0 {
|
|
||||||
s.limitStr = ""
|
|
||||||
} else {
|
|
||||||
s.limitStr = strconv.Itoa(value)
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
s.err(errors.New("Can' understand the value of Limit, Should be int"))
|
|
||||||
}
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Offset(value interface{}) *Orm {
|
|
||||||
switch value := value.(type) {
|
|
||||||
case string:
|
|
||||||
s.offsetStr = value
|
|
||||||
case int:
|
|
||||||
if value < 0 {
|
|
||||||
s.offsetStr = ""
|
|
||||||
} else {
|
|
||||||
s.offsetStr = strconv.Itoa(value)
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
s.err(errors.New("Can' understand the value of Offset, Should be int"))
|
|
||||||
}
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Order(value string, reorder ...bool) *Orm {
|
|
||||||
defer s.validSql(value)
|
|
||||||
if len(reorder) > 0 && reorder[0] {
|
|
||||||
s.orderStrs = append([]string{}, value)
|
|
||||||
} else {
|
|
||||||
s.orderStrs = append(s.orderStrs, value)
|
|
||||||
}
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Count() int64 {
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Select(value interface{}) *Orm {
|
|
||||||
defer func() { s.validSql(s.selectStr) }()
|
|
||||||
|
|
||||||
switch value := value.(type) {
|
|
||||||
case string:
|
|
||||||
s.selectStr = value
|
|
||||||
default:
|
|
||||||
s.err(errors.New("Can' understand the value of Select, Should be string"))
|
|
||||||
}
|
|
||||||
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Save(value interface{}) *Orm {
|
|
||||||
s.Model(value)
|
|
||||||
if s.model.PrimaryKeyIsEmpty() {
|
|
||||||
s.create(value)
|
|
||||||
} else {
|
|
||||||
s.update(value)
|
|
||||||
}
|
|
||||||
return s.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Delete(value interface{}) *Orm {
|
|
||||||
s.explain(value, "Delete").delete(value)
|
|
||||||
return s.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Update(column string, value string) *Orm {
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Updates(values map[string]string) *Orm {
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Exec(sql ...string) *Orm {
|
|
||||||
var err error
|
|
||||||
if len(sql) == 0 {
|
|
||||||
s.SqlResult, err = s.db.Exec(s.Sql, s.SqlVars...)
|
|
||||||
} else {
|
|
||||||
s.SqlResult, err = s.db.Exec(sql[0])
|
|
||||||
}
|
|
||||||
s.err(err)
|
|
||||||
return s.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) First(out interface{}) *Orm {
|
|
||||||
s.explain(out, "Query").query(out)
|
|
||||||
return s.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Find(out interface{}) *Orm {
|
|
||||||
s.explain(out, "Query").query(out)
|
|
||||||
return s.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Pluck(column string, value interface{}) (orm *Orm) {
|
|
||||||
s.Select(column).explain(s.model.Data, "Query").pluck(value)
|
|
||||||
return s.Copy()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) Or(querystring interface{}, args ...interface{}) *Orm {
|
|
||||||
s.orClause = append(s.orClause, map[string]interface{}{"query": querystring, "args": args})
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Orm) CreateTable(value interface{}) *Orm {
|
|
||||||
s.explain(value, "CreateTable").Exec()
|
|
||||||
return s
|
|
||||||
}
|
|
|
@ -46,6 +46,7 @@ func init() {
|
||||||
if orm.Error != nil {
|
if orm.Error != nil {
|
||||||
panic("No error should raise when create table")
|
panic("No error should raise when create table")
|
||||||
}
|
}
|
||||||
|
|
||||||
db.CreateTable(&Product{})
|
db.CreateTable(&Product{})
|
||||||
|
|
||||||
var shortForm = "2006-01-02 15:04:05"
|
var shortForm = "2006-01-02 15:04:05"
|
||||||
|
@ -62,8 +63,8 @@ func init() {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestFirst(t *testing.T) {
|
func TestFirst(t *testing.T) {
|
||||||
var u1, u2 User
|
// var u1, u2 User
|
||||||
db.Where("name = ?", "3").Order("age desc").First(&u1).First(&u2)
|
// db.Where("name = ?", "3").Order("age desc").First(&u1).First(&u2)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSaveAndFind(t *testing.T) {
|
func TestSaveAndFind(t *testing.T) {
|
||||||
|
|
4
utils.go
4
utils.go
|
@ -7,11 +7,11 @@ import (
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (s *Orm) quote(value string) string {
|
func (s *Do) quote(value string) string {
|
||||||
return "\"" + value + "\""
|
return "\"" + value + "\""
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Orm) quoteMap(values []string) (results []string) {
|
func (s *Do) quoteMap(values []string) (results []string) {
|
||||||
for _, value := range values {
|
for _, value := range values {
|
||||||
results = append(results, s.quote(value))
|
results = append(results, s.quote(value))
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue