From b0b9fc253044355d6bc9e842b402a88f6326d398 Mon Sep 17 00:00:00 2001 From: Stephen Afam-Osemene Date: Sat, 9 Nov 2024 21:38:50 +0000 Subject: [PATCH] Make bob.Cache() require an Executor to run any query hooks. --- CHANGELOG.md | 1 + cached.go | 31 ++++++++++++++++++++++++++----- query.go | 8 ++++---- query_test.go | 4 ++++ 4 files changed, 35 insertions(+), 9 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9b762cf..a8600d0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -77,6 +77,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 The same functionality can be achieved by using `modelSlice.Delete()` or creating an `Delete` query using `table.Delete()`. - `BeforeInsertHooks` now only takes a single `ModelSetter` at a time. This is because it is not possible to know before executing the queries exactly how many setters are being used since additional rows can be inserted by applying another setter as a mod. +- `bob.Cache()` now requires an `Executor`. This is used to run any query hooks. ### Removed diff --git a/cached.go b/cached.go index 4479c57..e739103 100644 --- a/cached.go +++ b/cached.go @@ -6,23 +6,43 @@ import ( "io" ) -func Cache(ctx context.Context, q Query) (BaseQuery[*cached], error) { - return CacheN(ctx, q, 1) +func Cache(ctx context.Context, exec Executor, q Query) (BaseQuery[*cached], error) { + return CacheN(ctx, exec, q, 1) } -func CacheN(ctx context.Context, q Query, start int) (BaseQuery[*cached], error) { +func CacheN(ctx context.Context, exec Executor, q Query, start int) (BaseQuery[*cached], error) { + var err error + + if h, ok := q.(HookableQuery); ok { + ctx, err = h.RunHooks(ctx, exec) + if err != nil { + return BaseQuery[*cached]{}, err + } + } + query, args, err := BuildN(ctx, q, start) if err != nil { return BaseQuery[*cached]{}, err } - return BaseQuery[*cached]{ + cached := BaseQuery[*cached]{ + QueryType: q.Type(), Expression: &cached{ query: []byte(query), args: args, start: start, }, - }, nil + } + + if l, ok := q.(Loadable); ok { + cached.Expression.SetLoaders(l.GetLoaders()...) + } + + if m, ok := q.(MapperModder); ok { + cached.Expression.SetMapperMods(m.GetMapperMods()...) + } + + return cached, nil } type WrongStartError struct { @@ -38,6 +58,7 @@ type cached struct { query []byte args []any start int + Load } // WriteSQL implements Expression. diff --git a/query.go b/query.go index 7c2c5d2..eb53114 100644 --- a/query.go +++ b/query.go @@ -136,11 +136,11 @@ func (q BaseQuery[E]) BuildN(ctx context.Context, start int) (string, []any, err } // Convinient function to cache a query -func (q BaseQuery[E]) Cache(ctx context.Context) (BaseQuery[*cached], error) { - return CacheN(ctx, q, 1) +func (q BaseQuery[E]) Cache(ctx context.Context, exec Executor) (BaseQuery[*cached], error) { + return CacheN(ctx, exec, q, 1) } // Convinient function to cache a query from a point -func (q BaseQuery[E]) CacheN(ctx context.Context, start int) (BaseQuery[*cached], error) { - return CacheN(ctx, q, start) +func (q BaseQuery[E]) CacheN(ctx context.Context, exec Executor, start int) (BaseQuery[*cached], error) { + return CacheN(ctx, exec, q, start) } diff --git a/query_test.go b/query_test.go index 1753fde..a04588a 100644 --- a/query_test.go +++ b/query_test.go @@ -5,4 +5,8 @@ var ( _ Loadable = BaseQuery[Expression]{} _ MapperModder = BaseQuery[Expression]{} _ HookableQuery = BaseQuery[Expression]{} + + _ Expression = &cached{} + _ Loadable = &cached{} + _ MapperModder = &cached{} )