Refactor: add StoredProcedureBuilder for SQL calls
Introduce StoredProcedureBuilder to centralize and simplify the construction of SQL stored procedure calls and parameter lists. Refactor DeleteObjectProcedureHandler, InsertObjectProcedureHandler, and UpdateObjectProcedureHandler to use this utility, replacing manual StringBuilder and parameter management. Improves code readability, reduces duplication, and standardizes parameter handling, including output parameters.
This commit is contained in:
@@ -11,7 +11,7 @@ using ReC.Application.Endpoints.Commands;
|
||||
using ReC.Application.Profile.Commands;
|
||||
using ReC.Application.RecActions.Commands;
|
||||
using ReC.Application.Results.Commands;
|
||||
using System.Text;
|
||||
using System.Data;
|
||||
|
||||
namespace ReC.Application.Common.Procedures.InsertProcedure;
|
||||
|
||||
@@ -37,90 +37,62 @@ public class InsertObjectProcedureHandler(IRepository repo, IOptionsMonitor<SqlE
|
||||
{
|
||||
public async Task<long> Handle(InsertObjectProcedure request, CancellationToken cancel)
|
||||
{
|
||||
var sql = new StringBuilder("EXEC [dbo].[PRREC_INSERT_OBJECT]");
|
||||
var parameters = new List<SqlParameter>();
|
||||
var separator = ' ';
|
||||
|
||||
void Add(string name, object? value, System.Data.SqlDbType? dbType = null)
|
||||
{
|
||||
if (value is null) return;
|
||||
sql.AppendLine($"{separator}@{name} = @{name}");
|
||||
separator = ',';
|
||||
if (dbType.HasValue)
|
||||
parameters.Add(new SqlParameter($"@{name}", dbType.Value) { Value = value });
|
||||
else
|
||||
parameters.Add(new SqlParameter($"@{name}", value));
|
||||
}
|
||||
|
||||
Add("pENTITY", request.Entity);
|
||||
Add("pADDED_WHO", request.AddedWho);
|
||||
Add("pADDED_WHEN", DateTime.UtcNow);
|
||||
|
||||
Add("pACTION_PROFILE_ID", request.Action?.ProfileId);
|
||||
Add("pACTION_ACTIVE", request.Action?.Active);
|
||||
Add("pACTION_SEQUENCE", request.Action?.Sequence, System.Data.SqlDbType.TinyInt);
|
||||
Add("pACTION_ENDPOINT_ID", request.Action?.EndpointId);
|
||||
Add("pACTION_ENDPOINT_AUTH_ID", request.Action?.EndpointAuthId);
|
||||
Add("pACTION_ENDPOINT_PARAMS_ID", request.Action?.EndpointParamsId, System.Data.SqlDbType.SmallInt);
|
||||
Add("pACTION_SQL_CONNECTION_ID", request.Action?.SqlConnectionId, System.Data.SqlDbType.SmallInt);
|
||||
Add("pACTION_TYPE_ID", request.Action?.TypeId is not null ? (byte)request.Action.TypeId : null, System.Data.SqlDbType.TinyInt);
|
||||
Add("pACTION_PRE_SQL", request.Action?.PreSql);
|
||||
Add("pACTION_HEADER_SQL", request.Action?.HeaderSql);
|
||||
Add("pACTION_BODY_SQL", request.Action?.BodySql);
|
||||
Add("pACTION_POST_SQL", request.Action?.PostSql);
|
||||
Add("pACTION_ERROR_ACTION_ID", request.Action?.ErrorActionId, System.Data.SqlDbType.TinyInt);
|
||||
|
||||
Add("pENDPOINT_ACTIVE", request.Endpoint?.Active);
|
||||
Add("pENDPOINT_DESCRIPTION", request.Endpoint?.Description);
|
||||
Add("pENDPOINT_URI", request.Endpoint?.Uri);
|
||||
|
||||
Add("pENDPOINT_AUTH_ACTIVE", request.EndpointAuth?.Active);
|
||||
Add("pENDPOINT_AUTH_DESCRIPTION", request.EndpointAuth?.Description);
|
||||
Add("pENDPOINT_AUTH_TYPE_ID", request.EndpointAuth?.TypeId, System.Data.SqlDbType.TinyInt);
|
||||
Add("pENDPOINT_AUTH_API_KEY", request.EndpointAuth?.ApiKey);
|
||||
Add("pENDPOINT_AUTH_API_VALUE", request.EndpointAuth?.ApiValue);
|
||||
Add("pENDPOINT_AUTH_API_KEY_ADD_TO_ID", request.EndpointAuth?.ApiKeyAddToId);
|
||||
Add("pENDPOINT_AUTH_TOKEN", request.EndpointAuth?.Token);
|
||||
Add("pENDPOINT_AUTH_USERNAME", request.EndpointAuth?.Username);
|
||||
Add("pENDPOINT_AUTH_PASSWORD", request.EndpointAuth?.Password);
|
||||
Add("pENDPOINT_AUTH_DOMAIN", request.EndpointAuth?.Domain);
|
||||
Add("pENDPOINT_AUTH_WORKSTATION", request.EndpointAuth?.Workstation);
|
||||
|
||||
Add("pPROFILE_ACTIVE", request.Profile?.Active);
|
||||
Add("pPROFILE_TYPE_ID", request.Profile?.TypeId, System.Data.SqlDbType.TinyInt);
|
||||
Add("pPROFILE_MANDANTOR", request.Profile?.Mandantor);
|
||||
Add("pPROFILE_NAME", request.Profile?.Name);
|
||||
Add("pPROFILE_DESCRIPTION", request.Profile?.Description);
|
||||
Add("pPROFILE_LOG_LEVEL_ID", request.Profile?.LogLevelId, System.Data.SqlDbType.TinyInt);
|
||||
Add("pPROFILE_LANGUAGE_ID", request.Profile?.LanguageId, System.Data.SqlDbType.SmallInt);
|
||||
|
||||
Add("pRESULT_ACTION_ID", request.Result?.ActionId);
|
||||
Add("pRESULT_STATUS_ID", request.Result?.StatusId, System.Data.SqlDbType.SmallInt);
|
||||
Add("pRESULT_TYPE_ID", request.Result?.Type is not null ? (byte)request.Result.Type : null, System.Data.SqlDbType.TinyInt);
|
||||
Add("pRESULT_HEADER", request.Result?.Header);
|
||||
Add("pRESULT_BODY", request.Result?.Body);
|
||||
Add("pRESULT_INFO", request.Result?.Info);
|
||||
Add("pRESULT_ERROR", request.Result?.Error);
|
||||
|
||||
Add("pENDPOINT_PARAMS_ACTIVE", request.EndpointParams?.Active);
|
||||
Add("pENDPOINT_PARAMS_DESCRIPTION", request.EndpointParams?.Description);
|
||||
Add("pENDPOINT_PARAMS_GROUP_ID", request.EndpointParams?.GroupId, System.Data.SqlDbType.SmallInt);
|
||||
Add("pENDPOINT_PARAMS_SEQUENCE", request.EndpointParams?.Sequence, System.Data.SqlDbType.TinyInt);
|
||||
Add("pENDPOINT_PARAMS_KEY", request.EndpointParams?.Key);
|
||||
Add("pENDPOINT_PARAMS_VALUE", request.EndpointParams?.Value);
|
||||
|
||||
// output parameter — always added
|
||||
sql.AppendLine($"{separator}@oGUID = @oGUID OUTPUT");
|
||||
parameters.Add(new SqlParameter
|
||||
{
|
||||
ParameterName = "@oGUID",
|
||||
SqlDbType = System.Data.SqlDbType.BigInt,
|
||||
Direction = System.Data.ParameterDirection.Output
|
||||
});
|
||||
var sp = new StoredProcedureBuilder("EXEC [dbo].[PRREC_INSERT_OBJECT]")
|
||||
.Add("pENTITY", request.Entity)
|
||||
.Add("pADDED_WHO", request.AddedWho)
|
||||
.Add("pADDED_WHEN", DateTime.UtcNow)
|
||||
.Add("pACTION_PROFILE_ID", request.Action?.ProfileId)
|
||||
.Add("pACTION_ACTIVE", request.Action?.Active)
|
||||
.Add("pACTION_SEQUENCE", request.Action?.Sequence, SqlDbType.TinyInt)
|
||||
.Add("pACTION_ENDPOINT_ID", request.Action?.EndpointId)
|
||||
.Add("pACTION_ENDPOINT_AUTH_ID", request.Action?.EndpointAuthId)
|
||||
.Add("pACTION_ENDPOINT_PARAMS_ID", request.Action?.EndpointParamsId, SqlDbType.SmallInt)
|
||||
.Add("pACTION_SQL_CONNECTION_ID", request.Action?.SqlConnectionId, SqlDbType.SmallInt)
|
||||
.Add("pACTION_TYPE_ID", request.Action?.TypeId is not null ? (byte)request.Action.TypeId : null, SqlDbType.TinyInt)
|
||||
.Add("pACTION_PRE_SQL", request.Action?.PreSql)
|
||||
.Add("pACTION_HEADER_SQL", request.Action?.HeaderSql)
|
||||
.Add("pACTION_BODY_SQL", request.Action?.BodySql)
|
||||
.Add("pACTION_POST_SQL", request.Action?.PostSql)
|
||||
.Add("pACTION_ERROR_ACTION_ID", request.Action?.ErrorActionId, SqlDbType.TinyInt)
|
||||
.Add("pENDPOINT_ACTIVE", request.Endpoint?.Active)
|
||||
.Add("pENDPOINT_DESCRIPTION", request.Endpoint?.Description)
|
||||
.Add("pENDPOINT_URI", request.Endpoint?.Uri)
|
||||
.Add("pENDPOINT_AUTH_ACTIVE", request.EndpointAuth?.Active)
|
||||
.Add("pENDPOINT_AUTH_DESCRIPTION", request.EndpointAuth?.Description)
|
||||
.Add("pENDPOINT_AUTH_TYPE_ID", request.EndpointAuth?.TypeId, SqlDbType.TinyInt)
|
||||
.Add("pENDPOINT_AUTH_API_KEY", request.EndpointAuth?.ApiKey)
|
||||
.Add("pENDPOINT_AUTH_API_VALUE", request.EndpointAuth?.ApiValue)
|
||||
.Add("pENDPOINT_AUTH_API_KEY_ADD_TO_ID", request.EndpointAuth?.ApiKeyAddToId)
|
||||
.Add("pENDPOINT_AUTH_TOKEN", request.EndpointAuth?.Token)
|
||||
.Add("pENDPOINT_AUTH_USERNAME", request.EndpointAuth?.Username)
|
||||
.Add("pENDPOINT_AUTH_PASSWORD", request.EndpointAuth?.Password)
|
||||
.Add("pENDPOINT_AUTH_DOMAIN", request.EndpointAuth?.Domain)
|
||||
.Add("pENDPOINT_AUTH_WORKSTATION", request.EndpointAuth?.Workstation)
|
||||
.Add("pPROFILE_ACTIVE", request.Profile?.Active)
|
||||
.Add("pPROFILE_TYPE_ID", request.Profile?.TypeId, SqlDbType.TinyInt)
|
||||
.Add("pPROFILE_MANDANTOR", request.Profile?.Mandantor)
|
||||
.Add("pPROFILE_NAME", request.Profile?.Name)
|
||||
.Add("pPROFILE_DESCRIPTION", request.Profile?.Description)
|
||||
.Add("pPROFILE_LOG_LEVEL_ID", request.Profile?.LogLevelId, SqlDbType.TinyInt)
|
||||
.Add("pPROFILE_LANGUAGE_ID", request.Profile?.LanguageId, SqlDbType.SmallInt)
|
||||
.Add("pRESULT_ACTION_ID", request.Result?.ActionId)
|
||||
.Add("pRESULT_STATUS_ID", request.Result?.StatusId, SqlDbType.SmallInt)
|
||||
.Add("pRESULT_TYPE_ID", request.Result?.Type is not null ? (byte)request.Result.Type : null, SqlDbType.TinyInt)
|
||||
.Add("pRESULT_HEADER", request.Result?.Header)
|
||||
.Add("pRESULT_BODY", request.Result?.Body)
|
||||
.Add("pRESULT_INFO", request.Result?.Info)
|
||||
.Add("pRESULT_ERROR", request.Result?.Error)
|
||||
.Add("pENDPOINT_PARAMS_ACTIVE", request.EndpointParams?.Active)
|
||||
.Add("pENDPOINT_PARAMS_DESCRIPTION", request.EndpointParams?.Description)
|
||||
.Add("pENDPOINT_PARAMS_GROUP_ID", request.EndpointParams?.GroupId, SqlDbType.SmallInt)
|
||||
.Add("pENDPOINT_PARAMS_SEQUENCE", request.EndpointParams?.Sequence, SqlDbType.TinyInt)
|
||||
.Add("pENDPOINT_PARAMS_KEY", request.EndpointParams?.Key)
|
||||
.Add("pENDPOINT_PARAMS_VALUE", request.EndpointParams?.Value)
|
||||
.AddOutput("oGUID", SqlDbType.BigInt);
|
||||
|
||||
try
|
||||
{
|
||||
await repo.ExecuteQueryRawAsync(sql.ToString(), parameters.ToArray(), cancel);
|
||||
await repo.ExecuteQueryRawAsync(sp.BuildSql(), sp.BuildParameters(), cancel);
|
||||
}
|
||||
catch (SqlException ex)
|
||||
{
|
||||
@@ -130,12 +102,12 @@ public class InsertObjectProcedureHandler(IRepository repo, IOptionsMonitor<SqlE
|
||||
throw;
|
||||
}
|
||||
|
||||
var guidParam = parameters.Last();
|
||||
var guidParam = sp.GetParameter("oGUID");
|
||||
|
||||
if (guidParam.Value != DBNull.Value)
|
||||
if (guidParam.Value is long longValue)
|
||||
if (guidParam?.Value != DBNull.Value)
|
||||
if (guidParam!.Value is long longValue)
|
||||
return longValue;
|
||||
else if (long.TryParse(guidParam.Value.ToString(), out var guid))
|
||||
else if (long.TryParse(guidParam.Value?.ToString(), out var guid))
|
||||
return guid;
|
||||
|
||||
throw new InsertObjectFailedException(request, "InsertObject stored procedure did not return a valid identifier.");
|
||||
|
||||
Reference in New Issue
Block a user