From 24b9dab04cb80c442f5229526a95504174a909f6 Mon Sep 17 00:00:00 2001 From: ricodp Date: Sun, 15 Aug 2021 16:36:11 +0800 Subject: [PATCH 1/2] allow transcation to look for timeout setting in app.config, if not present, revert to previous/default behaviour --- source/AliaSQL.Core/AliaSQL.Core.csproj | 4 +++ .../Services/IApplicationSettings.cs | 9 +++++ .../Services/Impl/ApplicationSettings.cs | 25 ++++++++++++++ .../Services/Impl/QueryExecutor.cs | 2 +- .../Services/Impl/TransactionProvider.cs | 34 +++++++++++++++++++ 5 files changed, 73 insertions(+), 1 deletion(-) create mode 100644 source/AliaSQL.Core/Services/IApplicationSettings.cs create mode 100644 source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs create mode 100644 source/AliaSQL.Core/Services/Impl/TransactionProvider.cs diff --git a/source/AliaSQL.Core/AliaSQL.Core.csproj b/source/AliaSQL.Core/AliaSQL.Core.csproj index 62b59d8..5b20688 100644 --- a/source/AliaSQL.Core/AliaSQL.Core.csproj +++ b/source/AliaSQL.Core/AliaSQL.Core.csproj @@ -58,6 +58,7 @@ + @@ -69,7 +70,10 @@ + + + diff --git a/source/AliaSQL.Core/Services/IApplicationSettings.cs b/source/AliaSQL.Core/Services/IApplicationSettings.cs new file mode 100644 index 0000000..1c3763e --- /dev/null +++ b/source/AliaSQL.Core/Services/IApplicationSettings.cs @@ -0,0 +1,9 @@ +using System; + +namespace AliaSQL.Core.Services +{ + internal interface IApplicationSettings + { + TimeSpan? Timeout(); + } +} \ No newline at end of file diff --git a/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs b/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs new file mode 100644 index 0000000..e6d0eac --- /dev/null +++ b/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs @@ -0,0 +1,25 @@ +using System; +using System.Configuration; + +namespace AliaSQL.Core.Services.Impl +{ + internal class ApplicationSettings : IApplicationSettings + { + public TimeSpan? Timeout() + { + var timeoutValue = ConfigurationManager.AppSettings["timeout"]; + + if (string.IsNullOrEmpty(timeoutValue)) + { + return null; + } + + if (!TimeSpan.TryParse(timeoutValue, out var time)) + { + return null; + } + + return time; + } + } +} diff --git a/source/AliaSQL.Core/Services/Impl/QueryExecutor.cs b/source/AliaSQL.Core/Services/Impl/QueryExecutor.cs index f03a9cb..b7e84c2 100644 --- a/source/AliaSQL.Core/Services/Impl/QueryExecutor.cs +++ b/source/AliaSQL.Core/Services/Impl/QueryExecutor.cs @@ -72,7 +72,7 @@ public void ExecuteNonQuery(ConnectionSettings settings, string sql, bool includ public void ExecuteNonQueryTransactional(ConnectionSettings settings, string sql) { //do all this in a single transaction - using (var scope = new TransactionScope()) + using (var scope = new TransactionProvider().CreateTransactionScope()) { string connectionString = _connectionStringGenerator.GetConnectionString(settings, true); using (var connection = new SqlConnection(connectionString)) diff --git a/source/AliaSQL.Core/Services/Impl/TransactionProvider.cs b/source/AliaSQL.Core/Services/Impl/TransactionProvider.cs new file mode 100644 index 0000000..b851cb4 --- /dev/null +++ b/source/AliaSQL.Core/Services/Impl/TransactionProvider.cs @@ -0,0 +1,34 @@ +using System.Reflection; +using System.Transactions; + +namespace AliaSQL.Core.Services.Impl +{ + internal class TransactionProvider + { + private readonly IApplicationSettings _applicationSettings; + + public TransactionProvider() + { + _applicationSettings = new ApplicationSettings(); + } + + private void SetTransactionManagerField(string fieldName, object value) + { + typeof(TransactionManager).GetField(fieldName, BindingFlags.NonPublic | BindingFlags.Static)?.SetValue(null, value); + } + + public TransactionScope CreateTransactionScope() + { + var timeout = _applicationSettings.Timeout(); + + if (timeout == null) + { + return new TransactionScope(); + } + + SetTransactionManagerField("_cachedMaxTimeout", true); + SetTransactionManagerField("_maximumTimeout", timeout.GetValueOrDefault()); + return new TransactionScope(TransactionScopeOption.RequiresNew, timeout.GetValueOrDefault()); + } + } +} From bdd8ee1dd33701ab2ad7c1f6c3b19c299b069ce0 Mon Sep 17 00:00:00 2001 From: ricodp Date: Mon, 16 Aug 2021 08:20:25 +0800 Subject: [PATCH 2/2] rename app key --- source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs b/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs index e6d0eac..bcf1271 100644 --- a/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs +++ b/source/AliaSQL.Core/Services/Impl/ApplicationSettings.cs @@ -7,7 +7,7 @@ internal class ApplicationSettings : IApplicationSettings { public TimeSpan? Timeout() { - var timeoutValue = ConfigurationManager.AppSettings["timeout"]; + var timeoutValue = ConfigurationManager.AppSettings["aliasql.transaction.timeout"]; if (string.IsNullOrEmpty(timeoutValue)) {