using System.Collections.Generic; using System.Text; using Erp.SqlQueryManager.Domain.Shared; using Volo.Abp.DependencyInjection; namespace Erp.SqlQueryManager.Domain.Services; public class SqlTemplateProvider : ISqlTemplateProvider, ITransientDependency { public string GetStoredProcedureTemplate(string procedureName, string schemaName = "dbo") { return $@"-- ============================================= -- Author: -- Create date: -- Description: -- ============================================= CREATE OR ALTER PROCEDURE [{schemaName}].[{procedureName}] -- Add parameters here @Parameter1 INT = NULL, @Parameter2 NVARCHAR(100) = NULL AS BEGIN -- SET NOCOUNT ON added to prevent extra result sets from -- interfering with SELECT statements. SET NOCOUNT ON; -- Insert statements for procedure here SELECT @Parameter1 AS Parameter1, @Parameter2 AS Parameter2 -- Example error handling BEGIN TRY -- Your logic here END TRY BEGIN CATCH -- Error handling DECLARE @ErrorMessage NVARCHAR(4000) = ERROR_MESSAGE(); DECLARE @ErrorSeverity INT = ERROR_SEVERITY(); DECLARE @ErrorState INT = ERROR_STATE(); RAISERROR(@ErrorMessage, @ErrorSeverity, @ErrorState); END CATCH END GO"; } public string GetViewTemplate(string viewName, string schemaName = "dbo", bool withSchemaBinding = false) { var schemaBindingClause = withSchemaBinding ? " WITH SCHEMABINDING" : ""; return $@"-- ============================================= -- Author: -- Create date: -- Description: -- ============================================= CREATE OR ALTER VIEW [{schemaName}].[{viewName}]{schemaBindingClause} AS -- Define your SELECT statement here SELECT Column1, Column2, Column3 FROM TableName WHERE -- Add your conditions 1 = 1 GO"; } public string GetFunctionTemplate(string functionName, SqlFunctionType functionType, string schemaName = "dbo") { return functionType switch { SqlFunctionType.ScalarFunction => GetScalarFunctionTemplate(functionName, schemaName), SqlFunctionType.TableValuedFunction => GetTableValuedFunctionTemplate(functionName, schemaName), SqlFunctionType.InlineTableValuedFunction => GetInlineTableValuedFunctionTemplate(functionName, schemaName), _ => GetScalarFunctionTemplate(functionName, schemaName) }; } private string GetScalarFunctionTemplate(string functionName, string schemaName) { return $@"-- ============================================= -- Author: -- Create date: -- Description: Scalar function that returns a single value -- ============================================= CREATE OR ALTER FUNCTION [{schemaName}].[{functionName}] ( -- Add parameters here @Parameter1 INT, @Parameter2 NVARCHAR(100) ) RETURNS INT AS BEGIN -- Declare the return variable here DECLARE @Result INT; -- Add your logic here SELECT @Result = COUNT(*) FROM YourTable WHERE Column1 = @Parameter1; -- Return the result RETURN @Result; END GO"; } private string GetTableValuedFunctionTemplate(string functionName, string schemaName) { return $@"-- ============================================= -- Author: -- Create date: -- Description: Multi-statement table-valued function -- ============================================= CREATE OR ALTER FUNCTION [{schemaName}].[{functionName}] ( -- Add parameters here @Parameter1 INT, @Parameter2 NVARCHAR(100) ) RETURNS @ResultTable TABLE ( -- Define the structure of the result table Id INT, Name NVARCHAR(100), Value DECIMAL(18,2) ) AS BEGIN -- Fill the table variable with data INSERT INTO @ResultTable (Id, Name, Value) SELECT Id, Name, Value FROM YourTable WHERE Column1 = @Parameter1; -- Return RETURN; END GO"; } private string GetInlineTableValuedFunctionTemplate(string functionName, string schemaName) { return $@"-- ============================================= -- Author: -- Create date: -- Description: Inline table-valued function -- ============================================= CREATE OR ALTER FUNCTION [{schemaName}].[{functionName}] ( -- Add parameters here @Parameter1 INT, @Parameter2 NVARCHAR(100) ) RETURNS TABLE AS RETURN ( -- Add your SELECT statement here SELECT Id, Name, Value, CreatedDate FROM YourTable WHERE Column1 = @Parameter1 AND Column2 LIKE '%' + @Parameter2 + '%' ) GO"; } public string GetQueryTemplate(string queryType) { return queryType?.ToUpperInvariant() switch { "SELECT" => GetSelectTemplate(), "INSERT" => GetInsertTemplate(), "UPDATE" => GetUpdateTemplate(), "DELETE" => GetDeleteTemplate(), "JOIN" => GetJoinTemplate(), "CTE" => GetCteTemplate(), "PIVOT" => GetPivotTemplate(), "TRANSACTION" => GetTransactionTemplate(), _ => GetSelectTemplate() }; } private string GetSelectTemplate() { return @"-- Basic SELECT query SELECT Column1, Column2, Column3 FROM TableName WHERE -- Add your conditions Column1 = 'value' AND IsActive = 1 ORDER BY Column1 ASC;"; } private string GetInsertTemplate() { return @"-- INSERT statement INSERT INTO TableName ( Column1, Column2, Column3, CreatedDate ) VALUES ( 'Value1', 'Value2', 123, GETDATE() ); -- Or with SELECT INSERT INTO TableName (Column1, Column2) SELECT Column1, Column2 FROM SourceTable WHERE Condition = 1;"; } private string GetUpdateTemplate() { return @"-- UPDATE statement UPDATE TableName SET Column1 = 'NewValue', Column2 = 'NewValue2', UpdatedDate = GETDATE() WHERE Id = 123 AND IsActive = 1;"; } private string GetDeleteTemplate() { return @"-- DELETE statement DELETE FROM TableName WHERE Id = 123 AND IsActive = 0; -- Soft delete pattern UPDATE TableName SET IsDeleted = 1, DeletedDate = GETDATE(), DeletedBy = 'UserName' WHERE Id = 123;"; } private string GetJoinTemplate() { return @"-- JOIN query example SELECT t1.Column1, t1.Column2, t2.Column3, t3.Column4 FROM Table1 t1 INNER JOIN Table2 t2 ON t1.Id = t2.Table1Id LEFT JOIN Table3 t3 ON t2.Id = t3.Table2Id WHERE t1.IsActive = 1 AND t2.Status = 'Active' ORDER BY t1.Column1;"; } private string GetCteTemplate() { return @"-- Common Table Expression (CTE) example WITH CTE_Name AS ( SELECT Column1, Column2, COUNT(*) as RecordCount FROM TableName WHERE IsActive = 1 GROUP BY Column1, Column2 ) SELECT * FROM CTE_Name WHERE RecordCount > 5 ORDER BY RecordCount DESC;"; } private string GetPivotTemplate() { return @"-- PIVOT example SELECT * FROM ( SELECT Category, Year, Amount FROM Sales ) AS SourceTable PIVOT ( SUM(Amount) FOR Year IN ([2021], [2022], [2023], [2024]) ) AS PivotTable ORDER BY Category;"; } private string GetTransactionTemplate() { return @"-- Transaction example BEGIN TRANSACTION; BEGIN TRY -- Your SQL statements here UPDATE Table1 SET Column1 = 'Value' WHERE Id = 1; INSERT INTO Table2 (Column1, Column2) VALUES ('Value1', 'Value2'); DELETE FROM Table3 WHERE Id = 123; -- Commit if all successful COMMIT TRANSACTION; END TRY BEGIN CATCH -- Rollback on error ROLLBACK TRANSACTION; -- Return error information SELECT ERROR_NUMBER() AS ErrorNumber, ERROR_SEVERITY() AS ErrorSeverity, ERROR_STATE() AS ErrorState, ERROR_PROCEDURE() AS ErrorProcedure, ERROR_LINE() AS ErrorLine, ERROR_MESSAGE() AS ErrorMessage; END CATCH;"; } public List GetAvailableQueryTemplates() { return new List { new() { Type = "SELECT", Name = "Basic Select", Description = "Simple SELECT query with WHERE and ORDER BY" }, new() { Type = "INSERT", Name = "Insert Data", Description = "INSERT statement with VALUES or SELECT" }, new() { Type = "UPDATE", Name = "Update Data", Description = "UPDATE statement with conditions" }, new() { Type = "DELETE", Name = "Delete Data", Description = "DELETE statement with soft delete example" }, new() { Type = "JOIN", Name = "Join Tables", Description = "Query with INNER and LEFT JOINs" }, new() { Type = "CTE", Name = "Common Table Expression", Description = "CTE (WITH clause) example" }, new() { Type = "PIVOT", Name = "Pivot Table", Description = "PIVOT query for data transformation" }, new() { Type = "TRANSACTION", Name = "Transaction", Description = "Transaction with error handling" } }; } }