Skip to content

Commit

Permalink
Merge pull request #21 from yoyo-project/task/fk-query-generation
Browse files Browse the repository at this point in the history
Adds support for generating queries on references
  • Loading branch information
dotvezz authored Jul 1, 2021
2 parents 8e238d4 + 8c7fdd7 commit 71c60a5
Show file tree
Hide file tree
Showing 4 changed files with 129 additions and 3 deletions.
102 changes: 102 additions & 0 deletions example/yoyo/repositories/query/person/query.go
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,48 @@ func (q Query) AgeNot(in float64) Query {
}}
}

func (q Query) CityId(in int32) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, CityId(in).n},
Operator: query.And,
}}
}

func (q Query) CityIdGreaterOrEqual(in int32) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, CityIdGreaterOrEqual(in).n},
Operator: query.And,
}}
}

func (q Query) CityIdGreaterThan(in int32) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, CityIdGreaterThan(in).n},
Operator: query.And,
}}
}

func (q Query) CityIdLessOrEqual(in int32) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, CityIdLessOrEqual(in).n},
Operator: query.And,
}}
}

func (q Query) CityIdLessThan(in int32) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, CityIdLessThan(in).n},
Operator: query.And,
}}
}

func (q Query) CityIdNot(in int32) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, CityIdNot(in).n},
Operator: query.And,
}}
}

func (q Query) FavoriteColor(in string) Query {
return Query{query.Node{
Children: &[2]query.Node{q.n, FavoriteColor(in).n},
Expand Down Expand Up @@ -275,6 +317,66 @@ func AgeNot(in float64) Query {
}}
}

func CityId(in int32) Query {
return Query{query.Node{
Condition: query.Condition{
Column: "fk_city_id",
Operator: query.Equals,
Value: in,
},
}}
}

func CityIdGreaterOrEqual(in int32) Query {
return Query{query.Node{
Condition: query.Condition{
Column: "fk_city_id",
Operator: query.GreaterOrEqual,
Value: in,
},
}}
}

func CityIdGreaterThan(in int32) Query {
return Query{query.Node{
Condition: query.Condition{
Column: "fk_city_id",
Operator: query.GreaterThan,
Value: in,
},
}}
}

func CityIdLessOrEqual(in int32) Query {
return Query{query.Node{
Condition: query.Condition{
Column: "fk_city_id",
Operator: query.LessOrEqual,
Value: in,
},
}}
}

func CityIdLessThan(in int32) Query {
return Query{query.Node{
Condition: query.Condition{
Column: "fk_city_id",
Operator: query.LessThan,
Value: in,
},
}}
}

func CityIdNot(in int32) Query {
return Query{query.Node{
Condition: query.Condition{
Column: "fk_city_id",
Operator: query.NotEquals,
Value: in,
},
}}
}

func FavoriteColor(in string) Query {
return Query{query.Node{
Condition: query.Condition{
Expand Down
2 changes: 1 addition & 1 deletion internal/repository/generate.go
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ func InitGeneratorLoader(
return newGenerator(
NewEntityGenerator(packageName, config.Schema),
NewEntityRepositoryGenerator(packageName, adapter, reposPath, findPackagePath),
NewQueryFileGenerator(reposPath, findPackagePath),
NewQueryFileGenerator(reposPath, findPackagePath, config.Schema),
NewRepositoriesGenerator(packageName, reposPath, findPackagePath, config.Schema),
NewQueryNodeGenerator(),
file.CreateWithDirs,
Expand Down
26 changes: 25 additions & 1 deletion internal/repository/generate_query.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import (
"github.com/yoyo-project/yoyo/internal/schema"
)

func NewQueryFileGenerator(reposPath string, findPackagePath Finder) EntityGenerator {
func NewQueryFileGenerator(reposPath string, findPackagePath Finder, db schema.Database) EntityGenerator {
return func(t schema.Table, w io.StringWriter) error {
var methods, functions, imports []string
for _, c := range t.Columns {
Expand All @@ -20,6 +20,30 @@ func NewQueryFileGenerator(reposPath string, findPackagePath Finder) EntityGener
imports = append(imports, is...)
}

for _, r := range t.References {
if r.HasMany {
continue // Skip HasMany references which require a join
}

ft, ok := db.GetTable(r.TableName)
if !ok {
return fmt.Errorf("unable to generate queries for table %s, missing foreign table %s", t.Name, r.TableName)
}

var ms, fs, is []string

for i, n := range r.ColNames(ft) {
c := ft.PKColumns()[i]
// Override the GoName in order to generate correct method/function names
c.GoName = ft.ExportedGoName() + c.ExportedGoName()
ms, fs, is = template.GenerateQueryLogic(n, c)
}

methods = append(methods, ms...)
functions = append(functions, fs...)
imports = append(imports, is...)
}

importPath, err := findPackagePath(reposPath + "/")
if err != nil {
return fmt.Errorf("unable to generate query file: %w", err)
Expand Down
2 changes: 1 addition & 1 deletion internal/schema/schema_reference.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ const (
)

// ColNames returns a list foreign key column names for the given reference. The method assumes that the `fTable` value
//is correct (for example, the "many" side in a one-to-many reference) and not necessarily the target table of the
// is correct (for example, the "many" side in a one-to-many reference) and not necessarily the target table of the
// Reference itself. So make sure the Yoyo-to-RDB reference translation has already happened before calling ColNames.
func (r *Reference) ColNames(ft Table) []string {
var (
Expand Down

0 comments on commit 71c60a5

Please sign in to comment.