From 1e1445a3410edd02dc15c1fb39ae0ae72336ee79 Mon Sep 17 00:00:00 2001 From: Nao Yonashiro Date: Sun, 30 Jul 2023 23:37:01 +0900 Subject: [PATCH 1/2] fix(codegen/golang): fix sqlc.embed to work with pq.Array wrap close #2458 --- internal/codegen/golang/field.go | 2 +- internal/codegen/golang/imports.go | 5 +++++ internal/codegen/golang/query.go | 6 +++++- internal/codegen/golang/result.go | 6 +++--- 4 files changed, 14 insertions(+), 5 deletions(-) diff --git a/internal/codegen/golang/field.go b/internal/codegen/golang/field.go index 94dfc81d7b..75dddca9da 100644 --- a/internal/codegen/golang/field.go +++ b/internal/codegen/golang/field.go @@ -17,7 +17,7 @@ type Field struct { Comment string Column *plugin.Column // EmbedFields contains the embedded fields that require scanning. - EmbedFields []string + EmbedFields []Field } func (gf Field) Tag() string { diff --git a/internal/codegen/golang/imports.go b/internal/codegen/golang/imports.go index cc747cc3d6..0301662c8f 100644 --- a/internal/codegen/golang/imports.go +++ b/internal/codegen/golang/imports.go @@ -334,6 +334,11 @@ func (i *importer) queryImports(filename string) fileImports { if strings.HasPrefix(f.Type, "[]") && f.Type != "[]byte" { return true } + for _, embed := range f.EmbedFields { + if strings.HasPrefix(embed.Type, "[]") && embed.Type != "[]byte" { + return true + } + } } } else { if strings.HasPrefix(q.Ret.Type(), "[]") && q.Ret.Type() != "[]byte" { diff --git a/internal/codegen/golang/query.go b/internal/codegen/golang/query.go index e6bef868df..c43c92eeff 100644 --- a/internal/codegen/golang/query.go +++ b/internal/codegen/golang/query.go @@ -168,7 +168,11 @@ func (v QueryValue) Scan() string { // append any embedded fields if len(f.EmbedFields) > 0 { for _, embed := range f.EmbedFields { - out = append(out, "&"+v.Name+"."+f.Name+"."+embed) + if strings.HasPrefix(embed.Type, "[]") && embed.Type != "[]byte" && !v.SQLDriver.IsPGX() { + out = append(out, "pq.Array(&"+v.Name+"."+f.Name+"."+embed.Name+")") + } else { + out = append(out, "&"+v.Name+"."+f.Name+"."+embed.Name) + } } continue } diff --git a/internal/codegen/golang/result.go b/internal/codegen/golang/result.go index 5955e7ef1c..8e1c2714f7 100644 --- a/internal/codegen/golang/result.go +++ b/internal/codegen/golang/result.go @@ -117,7 +117,7 @@ type goColumn struct { type goEmbed struct { modelType string modelName string - fields []string + fields []Field } // look through all the structs and attempt to find a matching one to embed @@ -138,9 +138,9 @@ func newGoEmbed(embed *plugin.Identifier, structs []Struct, defaultSchema string continue } - fields := make([]string, len(s.Fields)) + fields := make([]Field, len(s.Fields)) for i, f := range s.Fields { - fields[i] = f.Name + fields[i] = f } return &goEmbed{ From ea7073cea8f814afbcc46c1ec7ece4e2dc1f4e94 Mon Sep 17 00:00:00 2001 From: Nao Yonashiro Date: Sun, 30 Jul 2023 23:41:46 +0900 Subject: [PATCH 2/2] test: add endtoend --- .../testdata/sqlc_embed/postgresql/stdlib/go/models.go | 1 + .../testdata/sqlc_embed/postgresql/stdlib/go/query.sql.go | 5 ++++- .../endtoend/testdata/sqlc_embed/postgresql/stdlib/query.sql | 3 ++- 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/models.go b/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/models.go index 4ae3cf19d1..b871742fc5 100644 --- a/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/models.go +++ b/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/models.go @@ -16,6 +16,7 @@ type BazUser struct { type Post struct { ID int32 UserID int32 + Likes []int32 } type User struct { diff --git a/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/query.sql.go b/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/query.sql.go index b996d7977a..e35214671e 100644 --- a/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/query.sql.go +++ b/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/go/query.sql.go @@ -8,6 +8,8 @@ package querytest import ( "context" "database/sql" + + "github.com/lib/pq" ) const duplicate = `-- name: Duplicate :one @@ -34,7 +36,7 @@ func (q *Queries) Duplicate(ctx context.Context) (DuplicateRow, error) { } const join = `-- name: Join :one -SELECT users.id, users.name, users.age, posts.id, posts.user_id FROM posts +SELECT users.id, users.name, users.age, posts.id, posts.user_id, posts.likes FROM posts INNER JOIN users ON posts.user_id = users.id ` @@ -52,6 +54,7 @@ func (q *Queries) Join(ctx context.Context) (JoinRow, error) { &i.User.Age, &i.Post.ID, &i.Post.UserID, + pq.Array(&i.Post.Likes), ) return i, err } diff --git a/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/query.sql b/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/query.sql index 314f697384..b4c2405ba5 100644 --- a/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/query.sql +++ b/internal/endtoend/testdata/sqlc_embed/postgresql/stdlib/query.sql @@ -8,7 +8,8 @@ CREATE TABLE users ( CREATE TABLE posts ( id integer NOT NULL PRIMARY KEY, - user_id integer NOT NULL + user_id integer NOT NULL, + likes integer[] NOT NULL ); CREATE TABLE baz.users (