From f0962ea1ecbd6163d7d560c2e33e6bbfbd168ec8 Mon Sep 17 00:00:00 2001 From: Hein Date: Tue, 9 Dec 2025 14:37:09 +0200 Subject: [PATCH] Added EnableQueryDebug log --- pkg/common/adapters/database/bun.go | 33 ++++++++++++++++++++++++++++ pkg/common/adapters/database/gorm.go | 16 ++++++++++++++ 2 files changed, 49 insertions(+) diff --git a/pkg/common/adapters/database/bun.go b/pkg/common/adapters/database/bun.go index c27e2bc..0dde367 100644 --- a/pkg/common/adapters/database/bun.go +++ b/pkg/common/adapters/database/bun.go @@ -6,6 +6,7 @@ import ( "fmt" "reflect" "strings" + "time" "github.com/uptrace/bun" @@ -15,6 +16,24 @@ import ( "github.com/bitechdev/ResolveSpec/pkg/reflection" ) +// QueryDebugHook is a Bun query hook that logs all SQL queries including preloads +type QueryDebugHook struct{} + +func (h *QueryDebugHook) BeforeQuery(ctx context.Context, event *bun.QueryEvent) context.Context { + return ctx +} + +func (h *QueryDebugHook) AfterQuery(ctx context.Context, event *bun.QueryEvent) { + query := event.Query + duration := time.Since(event.StartTime) + + if event.Err != nil { + logger.Error("SQL Query Failed [%s]: %s. Error: %v", duration, query, event.Err) + } else { + logger.Debug("SQL Query Success [%s]: %s", duration, query) + } +} + // BunAdapter adapts Bun to work with our Database interface // This demonstrates how the abstraction works with different ORMs type BunAdapter struct { @@ -26,6 +45,20 @@ func NewBunAdapter(db *bun.DB) *BunAdapter { return &BunAdapter{db: db} } +// EnableQueryDebug enables query debugging which logs all SQL queries including preloads +// This is useful for debugging preload queries that may be failing +func (b *BunAdapter) EnableQueryDebug() { + b.db.AddQueryHook(&QueryDebugHook{}) + logger.Info("Bun query debug mode enabled - all SQL queries will be logged") +} + +// DisableQueryDebug removes all query hooks +func (b *BunAdapter) DisableQueryDebug() { + // Create a new DB without hooks + // Note: Bun doesn't have a RemoveQueryHook, so we'd need to track hooks manually + logger.Info("To disable query debug, recreate the BunAdapter without adding the hook") +} + func (b *BunAdapter) NewSelect() common.SelectQuery { return &BunSelectQuery{ query: b.db.NewSelect(), diff --git a/pkg/common/adapters/database/gorm.go b/pkg/common/adapters/database/gorm.go index 1a0f522..60817e1 100644 --- a/pkg/common/adapters/database/gorm.go +++ b/pkg/common/adapters/database/gorm.go @@ -23,6 +23,22 @@ func NewGormAdapter(db *gorm.DB) *GormAdapter { return &GormAdapter{db: db} } +// EnableQueryDebug enables query debugging which logs all SQL queries including preloads +// This is useful for debugging preload queries that may be failing +func (g *GormAdapter) EnableQueryDebug() *GormAdapter { + g.db = g.db.Debug() + logger.Info("GORM query debug mode enabled - all SQL queries will be logged") + return g +} + +// DisableQueryDebug disables query debugging +func (g *GormAdapter) DisableQueryDebug() *GormAdapter { + // GORM's Debug() creates a new session, so we need to get the base DB + // This is a simplified implementation + logger.Info("GORM debug mode - create a new adapter without Debug() to disable") + return g +} + func (g *GormAdapter) NewSelect() common.SelectQuery { return &GormSelectQuery{db: g.db} }