Optional where clause #547
-
Hey! I've just discovered bob and I have to say, I'm so impressed. I've tried sqlx, slc and GORM, but bob is the right amount of type-safe (via. generation) an flexibility (via. query builder) ❤️ I'm just wondering if there's an 'idiomatic' way to add an optional WHERE mod? Here's a simplified example, that uses optional criteria via. pointers): type GetAccountOpts struct {
AccountID *accounts.AccountID
Email *string
}
func (s *AccountStore) GetAccount(ctx context.Context, opts GetAccountOpts) (*Account, error) {
return models.Accounts.Query(
db.OptionalWhere(models.SelectWhere.Account.PublicID.EQ, opts.ID),
db.OptionalWhere(models.SelectWhere.Account.Email.EQ, opts.Email),
).One(ctx, s.ex)
} If I was doing it in pure SQL (sqlite), I'd use something like: WHERE
(accounts.id = ?1 OR (?1 IS NULL)) OR ... and my func OptionalWhere[V any](
where func(val V) mods.Where[*dialect.SelectQuery],
value *V,
) mods.Where[*dialect.SelectQuery] {
if value != nil {
return where(*value)
}
return sm.Where(sqlite.RawQuery("NULL is NULL"))
} but I was wondering if there's simply a way to return a no-op WHERE mod so that the resulting query only includes the fields that are actually supplied? |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 3 replies
-
First, I really like that you're using query mods beyond just what is generated by default. In your example, you're pretty close. The thing is... the mod doesn't HAVE TO do anything. Try this: func OptionalWhere[V any](
where func(val V) mods.Where[*dialect.SelectQuery],
value *V,
) bob.Mod[*dialect.SelectQuery] {
if value != nil {
return where(*value)
}
return bob.ModFunc[*dialect.SelectQuery](func(*dialect.SelectQuery) {})
} |
Beta Was this translation helpful? Give feedback.
First, I really like that you're using query mods beyond just what is generated by default.
The power of mods are that you can create your own to do whatever you want.
In your example, you're pretty close. The thing is... the mod doesn't HAVE TO do anything. Try this: