Skip to content

Commit

Permalink
Merge pull request #501 from J-Zeitler/map_batch
Browse files Browse the repository at this point in the history
add support for batch insert/exec with maps in addition to structs
  • Loading branch information
jmoiron authored Jan 24, 2021
2 parents 03c8d81 + 429af82 commit 68949f7
Show file tree
Hide file tree
Showing 4 changed files with 41 additions and 2 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -23,3 +23,5 @@ _testmain.go
*.exe
tags
environ

.idea
24 changes: 23 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -182,6 +182,28 @@ func main() {
// as the name -> db mapping, so struct fields are lowercased and the `db` tag
// is taken into consideration.
rows, err = db.NamedQuery(`SELECT * FROM person WHERE first_name=:first_name`, jason)


// batch insert

// batch insert with structs
personStructs := []Person{
{FirstName: "Ardie", LastName: "Savea", Email: "asavea@ab.co.nz"},
{FirstName: "Sonny Bill", LastName: "Williams", Email: "sbw@ab.co.nz"},
{FirstName: "Ngani", LastName: "Laumape", Email: "nlaumape@ab.co.nz"},
}

_, err = db.NamedExec(`INSERT INTO person (first_name, last_name, email)
VALUES (:first_name, :last_name, :email)`, personStructs)

// batch insert with maps
personMaps := []map[string]interface{}{
{"first_name": "Ardie", "last_name": "Savea", "email": "asavea@ab.co.nz"},
{"first_name": "Sonny Bill", "last_name": "Williams", "email": "sbw@ab.co.nz"},
{"first_name": "Ngani", "last_name": "Laumape", "email": "nlaumape@ab.co.nz"},
}

_, err = db.NamedExec(`INSERT INTO person (first_name, last_name, email)
VALUES (:first_name, :last_name, :email)`, personMaps)
}
```

4 changes: 4 additions & 0 deletions named.go
Original file line number Diff line number Diff line change
Expand Up @@ -157,6 +157,10 @@ func bindAnyArgs(names []string, arg interface{}, m *reflectx.Mapper) ([]interfa
// type, given a list of names to pull out of the struct. Used by public
// BindStruct interface.
func bindArgs(names []string, arg interface{}, m *reflectx.Mapper) ([]interface{}, error) {
if maparg, ok := arg.(map[string]interface{}); ok {
return bindMapArgs(names, maparg)
}

arglist := make([]interface{}, 0, len(names))

// grab the indirected value of arg
Expand Down
13 changes: 12 additions & 1 deletion named_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -195,7 +195,7 @@ func TestNamedQueries(t *testing.T) {
t.Errorf("got %s, expected %s", p.Email, people[0].Email)
}

// test batch inserts
// test struct batch inserts
sls := []Person{
{FirstName: "Ardie", LastName: "Savea", Email: "asavea@ab.co.nz"},
{FirstName: "Sonny Bill", LastName: "Williams", Email: "sbw@ab.co.nz"},
Expand All @@ -206,6 +206,17 @@ func TestNamedQueries(t *testing.T) {
_, err = db.NamedExec(insert, sls)
test.Error(err)

// test map batch inserts
slsMap := []map[string]interface{}{
{"first_name": "Ardie", "last_name": "Savea", "email": "asavea@ab.co.nz"},
{"first_name": "Sonny Bill", "last_name": "Williams", "email": "sbw@ab.co.nz"},
{"first_name": "Ngani", "last_name": "Laumape", "email": "nlaumape@ab.co.nz"},
}

_, err = db.NamedExec(`INSERT INTO person (first_name, last_name, email)
VALUES (:first_name, :last_name, :email)`, slsMap)
test.Error(err)

for _, p := range sls {
dest := Person{}
err = db.Get(&dest, db.Rebind("SELECT * FROM person WHERE email=?"), p.Email)
Expand Down

0 comments on commit 68949f7

Please sign in to comment.