From bd4a229bda5e3fb7648042f8ae608116f4b9bc62 Mon Sep 17 00:00:00 2001 From: Yanan Wang Date: Mon, 3 Aug 2026 17:14:59 -0500 Subject: [PATCH] feat: Invoked IText2SqlHook.SqlExecuting in SqlSelectFn and ExecuteQueryFn before deserializing the function args, so hooks can rewrite the SQL statements (e.g. inject trace tags) prior to execution. --- .../BotSharp.Plugin.SqlDriver/Functions/ExecuteQueryFn.cs | 6 +++++- .../BotSharp.Plugin.SqlDriver/Functions/SqlSelectFn.cs | 6 +++++- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/ExecuteQueryFn.cs b/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/ExecuteQueryFn.cs index 92d6baef5..6948e4a75 100644 --- a/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/ExecuteQueryFn.cs +++ b/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/ExecuteQueryFn.cs @@ -22,9 +22,13 @@ public ExecuteQueryFn(IServiceProvider services, public async Task Execute(RoleDialogModel message) { + var dbHook = _services.GetRequiredService(); + // The hook may rewrite message.FunctionArgs (e.g. tag the statements for + // traceability), so it must run before the args are deserialized. + await dbHook.SqlExecuting(message); + var args = JsonSerializer.Deserialize(message.FunctionArgs) ?? new(); //var refinedArgs = await RefineSqlStatement(message, args); - var dbHook = _services.GetRequiredService(); var dbType = dbHook.GetDatabaseType(message); var connectionString = _setting.Connections.FirstOrDefault(x => x.Name.Equals(args.DataSource, StringComparison.OrdinalIgnoreCase))?.ConnectionString; var dbConnectionString = dbHook.GetConnectionString(message, args.DataSource) ?? connectionString ?? throw new Exception("database connection is not found"); diff --git a/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/SqlSelectFn.cs b/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/SqlSelectFn.cs index 5b2a50e11..f8f4a1f27 100644 --- a/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/SqlSelectFn.cs +++ b/src/Plugins/BotSharp.Plugin.SqlDriver/Functions/SqlSelectFn.cs @@ -15,6 +15,11 @@ public SqlSelectFn(IServiceProvider services, public async Task Execute(RoleDialogModel message) { + var dbHook = _services.GetRequiredService(); + // The hook may rewrite message.FunctionArgs (e.g. tag the statement for + // traceability), so it must run before the args are deserialized. + await dbHook.SqlExecuting(message); + var args = JsonSerializer.Deserialize(message.FunctionArgs); if (args.GeneratedWithoutTableDefinition) @@ -24,7 +29,6 @@ public async Task Execute(RoleDialogModel message) } // check if need to instantely - var dbHook = _services.GetRequiredService(); var dbType = dbHook.GetDatabaseType(message); var dbConnectionString = dbHook.GetConnectionString(message) ?? throw new Exception("database connectdion is not found");