Skip to content
This repository was archived by the owner on Sep 7, 2021. It is now read-only.
This repository is currently being migrated. It's locked while the migration is in progress.

Commit b2d743c

Browse files
authored
Merge branch 'master' into lunny/fix_buffer_iterate
2 parents 9c4cbad + a6300f2 commit b2d743c

File tree

125 files changed

+1135
-28017
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

125 files changed

+1135
-28017
lines changed

.drone.yml

Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
workspace:
2+
base: /go
3+
path: src/github.com/go-xorm/xorm
4+
5+
clone:
6+
git:
7+
image: plugins/git:next
8+
depth: 50
9+
tags: true
10+
11+
services:
12+
mysql:
13+
image: mysql:5.7
14+
environment:
15+
- MYSQL_DATABASE=xorm_test
16+
- MYSQL_ALLOW_EMPTY_PASSWORD=yes
17+
when:
18+
event: [ push, tag, pull_request ]
19+
20+
pgsql:
21+
image: postgres:9.5
22+
environment:
23+
- POSTGRES_USER=postgres
24+
- POSTGRES_DB=xorm_test
25+
when:
26+
event: [ push, tag, pull_request ]
27+
28+
#mssql:
29+
# image: microsoft/mssql-server-linux:2017-CU11
30+
# environment:
31+
# - ACCEPT_EULA=Y
32+
# - SA_PASSWORD=yourStrong(!)Password
33+
# - MSSQL_PID=Developer
34+
# commands:
35+
# - echo 'CREATE DATABASE xorm_test' > create.sql
36+
# - /opt/mssql-tools/bin/sqlcmd -S localhost -U sa -P yourStrong(!)Password -i "create.sql"
37+
38+
matrix:
39+
GO_VERSION:
40+
- 1.8
41+
- 1.9
42+
- 1.10
43+
- 1.11
44+
45+
pipeline:
46+
init_postgres:
47+
image: postgres:9.5
48+
commands:
49+
# wait for postgres service to become available
50+
- |
51+
until psql -U postgres -d xorm_test -h pgsql \
52+
-c "SELECT 1;" >/dev/null 2>&1; do sleep 1; done
53+
# query the database
54+
- |
55+
psql -U postgres -d xorm_test -h pgsql \
56+
-c "create schema xorm;"
57+
58+
build:
59+
image: golang:${GO_VERSION}
60+
commands:
61+
- go get -t -d -v ./...
62+
- go get -u github.com/go-xorm/core
63+
- go get -u github.com/go-xorm/builder
64+
- go build -v
65+
when:
66+
event: [ push, pull_request ]
67+
68+
test-sqlite:
69+
image: golang:${GO_VERSION}
70+
commands:
71+
- go get -u github.com/wadey/gocovmerge
72+
- go test -v -race -db="sqlite3" -conn_str="./test.db" -coverprofile=coverage1-1.txt -covermode=atomic
73+
- go test -v -race -db="sqlite3" -conn_str="./test.db" -cache=true -coverprofile=coverage1-2.txt -covermode=atomic
74+
when:
75+
event: [ push, pull_request ]
76+
77+
test-mysql:
78+
image: golang:${GO_VERSION}
79+
commands:
80+
- go test -v -race -db="mysql" -conn_str="root:@tcp(mysql)/xorm_test" -coverprofile=coverage2-1.txt -covermode=atomic
81+
- go test -v -race -db="mysql" -conn_str="root:@tcp(mysql)/xorm_test" -cache=true -coverprofile=coverage2-2.txt -covermode=atomic
82+
when:
83+
event: [ push, pull_request ]
84+
85+
test-mysql-utf8mb4:
86+
image: golang:${GO_VERSION}
87+
commands:
88+
- go test -v -race -db="mysql" -conn_str="root:@tcp(mysql)/xorm_test?charset=utf8mb4" -coverprofile=coverage2.1-1.txt -covermode=atomic
89+
- go test -v -race -db="mysql" -conn_str="root:@tcp(mysql)/xorm_test?charset=utf8mb4" -cache=true -coverprofile=coverage2.1-2.txt -covermode=atomic
90+
when:
91+
event: [ push, pull_request ]
92+
93+
test-mymysql:
94+
image: golang:${GO_VERSION}
95+
commands:
96+
- go test -v -race -db="mymysql" -conn_str="tcp:mysql:3306*xorm_test/root/" -coverprofile=coverage3-1.txt -covermode=atomic
97+
- go test -v -race -db="mymysql" -conn_str="tcp:mysql:3306*xorm_test/root/" -cache=true -coverprofile=coverage3-2.txt -covermode=atomic
98+
when:
99+
event: [ push, pull_request ]
100+
101+
test-postgres:
102+
image: golang:${GO_VERSION}
103+
commands:
104+
- go test -v -race -db="postgres" -conn_str="postgres://postgres:@pgsql/xorm_test?sslmode=disable" -coverprofile=coverage4-1.txt -covermode=atomic
105+
- go test -v -race -db="postgres" -conn_str="postgres://postgres:@pgsql/xorm_test?sslmode=disable" -cache=true -coverprofile=coverage4-2.txt -covermode=atomic
106+
when:
107+
event: [ push, pull_request ]
108+
109+
test-postgres-schema:
110+
image: golang:${GO_VERSION}
111+
commands:
112+
- go test -v -race -db="postgres" -conn_str="postgres://postgres:@pgsql/xorm_test?sslmode=disable" -schema=xorm -coverprofile=coverage5-1.txt -covermode=atomic
113+
- go test -v -race -db="postgres" -conn_str="postgres://postgres:@pgsql/xorm_test?sslmode=disable" -schema=xorm -cache=true -coverprofile=coverage5-2.txt -covermode=atomic
114+
- gocovmerge coverage1-1.txt coverage1-2.txt coverage2-1.txt coverage2-2.txt coverage2.1-1.txt coverage2.1-2.txt coverage3-1.txt coverage3-2.txt coverage4-1.txt coverage4-2.txt coverage5-1.txt coverage5-2.txt > coverage.txt
115+
when:
116+
event: [ push, pull_request ]
117+
118+
#coverage:
119+
# image: robertstettner/drone-codecov
120+
# secrets: [ codecov_token ]
121+
# files:
122+
# - coverage.txt
123+
# when:
124+
# event: [ push, pull_request ]
125+
# branch: [ master ]

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,5 +28,6 @@ temp_test.go
2828
.vscode
2929
xorm.test
3030
*.sqlite3
31+
test.db.sql
3132

3233
.idea/

README.md

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,8 @@ Xorm is a simple and powerful ORM for Go.
3434

3535
* Postgres schema support
3636

37+
* Context Cache support
38+
3739
## Drivers Support
3840

3941
Drivers for Go's sql package which currently support database/sql includes:
@@ -358,6 +360,56 @@ if _, err := session.Exec("delete from userinfo where username = ?", user2.Usern
358360
return session.Commit()
359361
```
360362

363+
* Or you can use `Transaction` to replace above codes.
364+
365+
```Go
366+
res, err := engine.Transaction(func(sess *xorm.Session) (interface{}, error) {
367+
user1 := Userinfo{Username: "xiaoxiao", Departname: "dev", Alias: "lunny", Created: time.Now()}
368+
if _, err := session.Insert(&user1); err != nil {
369+
return nil, err
370+
}
371+
372+
user2 := Userinfo{Username: "yyy"}
373+
if _, err := session.Where("id = ?", 2).Update(&user2); err != nil {
374+
return nil, err
375+
}
376+
377+
if _, err := session.Exec("delete from userinfo where username = ?", user2.Username); err != nil {
378+
return nil, err
379+
}
380+
return nil, nil
381+
})
382+
```
383+
384+
* Context Cache, if enabled, current query result will be cached on session and be used by next same statement on the same session.
385+
386+
```Go
387+
sess := engine.NewSession()
388+
defer sess.Close()
389+
390+
var context = xorm.NewMemoryContextCache()
391+
392+
var c2 ContextGetStruct
393+
has, err := sess.ID(1).ContextCache(context).Get(&c2)
394+
assert.NoError(t, err)
395+
assert.True(t, has)
396+
assert.EqualValues(t, 1, c2.Id)
397+
assert.EqualValues(t, "1", c2.Name)
398+
sql, args := sess.LastSQL()
399+
assert.True(t, len(sql) > 0)
400+
assert.True(t, len(args) > 0)
401+
402+
var c3 ContextGetStruct
403+
has, err = sess.ID(1).ContextCache(context).Get(&c3)
404+
assert.NoError(t, err)
405+
assert.True(t, has)
406+
assert.EqualValues(t, 1, c3.Id)
407+
assert.EqualValues(t, "1", c3.Name)
408+
sql, args = sess.LastSQL()
409+
assert.True(t, len(sql) == 0)
410+
assert.True(t, len(args) == 0)
411+
```
412+
361413
## Contributing
362414

363415
If you want to pull request, please see [CONTRIBUTING](https://github.com/go-xorm/xorm/blob/master/CONTRIBUTING.md). And we also provide [Xorm on Google Groups](https://groups.google.com/forum/#!forum/xorm) to discuss.

README_CN.md

Lines changed: 55 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,8 @@ xorm是一个简单而强大的Go语言ORM库. 通过它可以使数据库操作
3232

3333
* 内置SQL Builder支持
3434

35+
* 上下文缓存支持
36+
3537
## 驱动支持
3638

3739
目前支持的Go数据库驱动和对应的数据库如下:
@@ -360,9 +362,61 @@ if _, err := session.Exec("delete from userinfo where username = ?", user2.Usern
360362
return session.Commit()
361363
```
362364

365+
* 事物的简写方法
366+
367+
```Go
368+
res, err := engine.Transaction(func(session *xorm.Session) (interface{}, error) {
369+
user1 := Userinfo{Username: "xiaoxiao", Departname: "dev", Alias: "lunny", Created: time.Now()}
370+
if _, err := session.Insert(&user1); err != nil {
371+
return nil, err
372+
}
373+
374+
user2 := Userinfo{Username: "yyy"}
375+
if _, err := session.Where("id = ?", 2).Update(&user2); err != nil {
376+
return nil, err
377+
}
378+
379+
if _, err := session.Exec("delete from userinfo where username = ?", user2.Username); err != nil {
380+
return nil, err
381+
}
382+
return nil, nil
383+
})
384+
```
385+
386+
* 上下文缓存,如果启用,那么针对单个对象的查询将会被缓存到系统中,可以被下一个查询使用。
387+
388+
```Go
389+
sess := engine.NewSession()
390+
defer sess.Close()
391+
392+
var context = xorm.NewMemoryContextCache()
393+
394+
var c2 ContextGetStruct
395+
has, err := sess.ID(1).ContextCache(context).Get(&c2)
396+
assert.NoError(t, err)
397+
assert.True(t, has)
398+
assert.EqualValues(t, 1, c2.Id)
399+
assert.EqualValues(t, "1", c2.Name)
400+
sql, args := sess.LastSQL()
401+
assert.True(t, len(sql) > 0)
402+
assert.True(t, len(args) > 0)
403+
404+
var c3 ContextGetStruct
405+
has, err = sess.ID(1).ContextCache(context).Get(&c3)
406+
assert.NoError(t, err)
407+
assert.True(t, has)
408+
assert.EqualValues(t, 1, c3.Id)
409+
assert.EqualValues(t, "1", c3.Name)
410+
sql, args = sess.LastSQL()
411+
assert.True(t, len(sql) == 0)
412+
assert.True(t, len(args) == 0)
413+
```
414+
363415
## 贡献
364416

365-
如果您也想为Xorm贡献您的力量,请查看 [CONTRIBUTING](https://github.com/go-xorm/xorm/blob/master/CONTRIBUTING.md)。您也可以加入QQ群 280360085 技术帮助和讨论。
417+
如果您也想为Xorm贡献您的力量,请查看 [CONTRIBUTING](https://github.com/go-xorm/xorm/blob/master/CONTRIBUTING.md)。您也可以加入QQ群 技术帮助和讨论。
418+
群一:280360085 (已满)
419+
群二:795010183
366420

367421
## Credits
368422

circle.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ database:
2222
test:
2323
override:
2424
# './...' is a relative pattern which means all subdirectories
25-
- go get -u github.com/wadey/gocovmerge;
25+
- go get -u github.com/wadey/gocovmerge
2626
- go test -v -race -db="sqlite3" -conn_str="./test.db" -coverprofile=coverage1-1.txt -covermode=atomic
2727
- go test -v -race -db="sqlite3" -conn_str="./test.db" -cache=true -coverprofile=coverage1-2.txt -covermode=atomic
2828
- go test -v -race -db="mysql" -conn_str="root:@/xorm_test" -coverprofile=coverage2-1.txt -covermode=atomic

context_cache.go

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
// Copyright 2018 The Xorm Authors. All rights reserved.
2+
// Use of this source code is governed by a BSD-style
3+
// license that can be found in the LICENSE file.
4+
5+
package xorm
6+
7+
// ContextCache is the interface that operates the cache data.
8+
type ContextCache interface {
9+
// Put puts value into cache with key.
10+
Put(key string, val interface{})
11+
// Get gets cached value by given key.
12+
Get(key string) interface{}
13+
}
14+
15+
type memoryContextCache map[string]interface{}
16+
17+
// NewMemoryContextCache return memoryContextCache
18+
func NewMemoryContextCache() memoryContextCache {
19+
return make(map[string]interface{})
20+
}
21+
22+
// Put puts value into cache with key.
23+
func (m memoryContextCache) Put(key string, val interface{}) {
24+
m[key] = val
25+
}
26+
27+
// Get gets cached value by given key.
28+
func (m memoryContextCache) Get(key string) interface{} {
29+
return m[key]
30+
}

context_test.go

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,18 +7,19 @@
77
package xorm
88

99
import (
10+
"context"
1011
"testing"
12+
"time"
1113

1214
"github.com/stretchr/testify/assert"
1315
)
1416

1517
func TestPingContext(t *testing.T) {
1618
assert.NoError(t, prepareEngine())
1719

18-
// TODO: Since EngineInterface should be compitable with old Go version, PingContext is not supported.
19-
/*
20-
ctx, _ := context.WithTimeout(context.Background(), 10*time.Second)
21-
err := testEngine.PingContext(ctx)
22-
assert.NoError(t, err)
23-
*/
20+
ctx, canceled := context.WithTimeout(context.Background(), 10*time.Second)
21+
defer canceled()
22+
23+
err := testEngine.(*Engine).PingContext(ctx)
24+
assert.NoError(t, err)
2425
}

dialect_mssql.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -218,7 +218,7 @@ func (db *mssql) SqlType(c *core.Column) string {
218218
res = core.Bit
219219
if strings.EqualFold(c.Default, "true") {
220220
c.Default = "1"
221-
} else {
221+
} else if strings.EqualFold(c.Default, "false") {
222222
c.Default = "0"
223223
}
224224
case core.Serial:

dialect_mysql.go

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -551,9 +551,12 @@ func (db *mysql) CreateTableSql(table *core.Table, tableName, storeEngine, chars
551551

552552
if len(charset) == 0 {
553553
charset = db.URI().Charset
554-
} else if len(charset) > 0 {
554+
}
555+
if len(charset) != 0 {
555556
sql += " DEFAULT CHARSET " + charset
556557
}
558+
559+
557560

558561
if db.rowFormat != "" {
559562
sql += " ROW_FORMAT=" + db.rowFormat

dialect_postgres.go

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -822,7 +822,7 @@ func (db *postgres) SqlType(c *core.Column) string {
822822
case core.NVarchar:
823823
res = core.Varchar
824824
case core.Uuid:
825-
res = core.Uuid
825+
return core.Uuid
826826
case core.Blob, core.TinyBlob, core.MediumBlob, core.LongBlob:
827827
return core.Bytea
828828
case core.Double:
@@ -834,6 +834,10 @@ func (db *postgres) SqlType(c *core.Column) string {
834834
res = t
835835
}
836836

837+
if strings.EqualFold(res, "bool") {
838+
// for bool, we don't need length information
839+
return res
840+
}
837841
hasLen1 := (c.Length > 0)
838842
hasLen2 := (c.Length2 > 0)
839843

@@ -1223,3 +1227,15 @@ func (p *pqDriver) Parse(driverName, dataSourceName string) (*core.Uri, error) {
12231227

12241228
return db, nil
12251229
}
1230+
1231+
type pqDriverPgx struct {
1232+
pqDriver
1233+
}
1234+
1235+
func (pgx *pqDriverPgx) Parse(driverName, dataSourceName string) (*core.Uri, error) {
1236+
// Remove the leading characters for driver to work
1237+
if len(dataSourceName) >= 9 && dataSourceName[0] == 0 {
1238+
dataSourceName = dataSourceName[9:]
1239+
}
1240+
return pgx.pqDriver.Parse(driverName, dataSourceName)
1241+
}

0 commit comments

Comments
 (0)