diff --git a/CloudBuilder.Core/DatabaseAccessor/UnitOfWorkAttribute.cs b/CloudBuilder.Core/DatabaseAccessor/UnitOfWorkAttribute.cs index 97e3f08..dde1348 100644 --- a/CloudBuilder.Core/DatabaseAccessor/UnitOfWorkAttribute.cs +++ b/CloudBuilder.Core/DatabaseAccessor/UnitOfWorkAttribute.cs @@ -1,4 +1,6 @@ -using Microsoft.AspNetCore.Mvc.Filters; +using CloudBuilder.Core.Service; +using Microsoft.AspNetCore.Mvc; +using Microsoft.AspNetCore.Mvc.Filters; using Microsoft.EntityFrameworkCore; using System; using System.Collections.Generic; @@ -10,7 +12,8 @@ using System.Transactions; namespace CloudBuilder.Core.DatabaseAccessor { /* - 事务范围不匹配:TransactionScope 管理的是分布式事务,但对于单个数据库连接,通常不需要分布式事务。 + 事务范围:TransactionScopeOption.RequiresNew 管理的是分布式事务, + TransactionScopeOption.Required但对于单个数据库连接,通常不需要分布式事务。 OnActionExecutionAsync 是 ASP.NET Core 中异步的 Action 过滤器执行方法。 // OnActionExecuting: Action 执行前 [开始事务] @@ -19,6 +22,7 @@ namespace CloudBuilder.Core.DatabaseAccessor ↓ // OnActionExecuted: Action 执行后(无论是否异常) [检查异常] + //Controller对象不抛出异常,返回的是异常对象ValidatedException、ServiceErrorException(方便前端信息统一处理) [提交或回滚事务] */ [AttributeUsage(AttributeTargets.Method)] @@ -38,15 +42,59 @@ namespace CloudBuilder.Core.DatabaseAccessor base.OnActionExecuting(context); } + //public override void OnActionExecuting(ActionExecutingContext context) + //{ + // // 正确:单机数据库事务(不是分布式) + // _transactionScope = new TransactionScope( + // TransactionScopeOption.Required, + // new TransactionOptions + // { + // IsolationLevel = IsolationLevel.ReadCommitted + // }, + // TransactionScopeAsyncFlowOption.Enabled); // 必须加这个 + + // base.OnActionExecuting(context); + //} + public override void OnActionExecuted(ActionExecutedContext context) { - if (_transactionScope != null) + if (_transactionScope == null) { - if (context.Exception == null) + base.OnActionExecuted(context); + return; + } + + bool needRollback = false; + + try + { + // ============================================== + // 核心逻辑:判断返回值是不是异常对象 + // ============================================== + if (context.Result is ObjectResult objectResult) + { + var value = objectResult.Value; + + if (value != null) + { + // 只要是这两个异常 → 必须回滚 + if (value is ValidatedException || value is ServiceErrorException) + { + needRollback = true; + } + } + } + + // 如果没有异常,才提交 + if (!needRollback) { //必须要有 SaveChanges() 调用,否则数据只会停留在内存中,不会真正保存到数据库。 _transactionScope.Complete(); } + } + finally + { + // 不 Complete() 就是自动回滚 _transactionScope.Dispose(); } diff --git a/CloudBuilder.Security.Service/SecurityFunctionService.cs b/CloudBuilder.Security.Service/SecurityFunctionService.cs index 748157c..e7f5fe1 100644 --- a/CloudBuilder.Security.Service/SecurityFunctionService.cs +++ b/CloudBuilder.Security.Service/SecurityFunctionService.cs @@ -253,16 +253,18 @@ namespace CloudBuilder.Security.Service if (maps == null || maps.Length == 0) return; - + int maxOrderBy = 0; foreach (SecurityFunctionMapViewEntity map in maps) { SecurityFunctionMapViewEntity[] oldMaps = repositoryMapView.Entities.Where(x => x.ParentFunctionName == map.ParentFunctionName).ToArray(); + if (oldMaps != null && oldMaps.Count() > 0) maxOrderBy = oldMaps.Max(x => x.Orderby); + repositoryMap.InsertNow(new SecurityFunctionMapEntity() { FunctionNameSon = functionName, FunctionNameParent = map.ParentFunctionName, - Orderby = oldMaps == null ? 1 : oldMaps.Max(x => x.Orderby) + 1 + Orderby = oldMaps == null ? 1 : maxOrderBy + 1 }); } diff --git a/CloudBuilder.Web.Entry.sln b/CloudBuilder.Web.Entry.sln index 3686ac4..1ef7ace 100644 --- a/CloudBuilder.Web.Entry.sln +++ b/CloudBuilder.Web.Entry.sln @@ -1,12 +1,14 @@  Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio Version 17 -VisualStudioVersion = 17.14.37111.16 d17.14 +VisualStudioVersion = 17.14.37111.16 MinimumVisualStudioVersion = 10.0.40219.1 Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Web.Entry", "CloudBuilder.Web.Entry\CloudBuilder.Web.Entry.csproj", "{9823D7CF-5DF8-BCAE-391B-C2CFC51C99C2}" EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Security.Service", "CloudBuilder.Security.Service\CloudBuilder.Security.Service.csproj", "{D4371FF5-55AA-F6FB-9D02-FA0486C7F492}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Core", "CloudBuilder.Core\CloudBuilder.Core.csproj", "{AFA9D41C-E8A5-32D3-E81B-2ABA7C37D46C}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -21,6 +23,10 @@ Global {D4371FF5-55AA-F6FB-9D02-FA0486C7F492}.Debug|Any CPU.Build.0 = Debug|Any CPU {D4371FF5-55AA-F6FB-9D02-FA0486C7F492}.Release|Any CPU.ActiveCfg = Release|Any CPU {D4371FF5-55AA-F6FB-9D02-FA0486C7F492}.Release|Any CPU.Build.0 = Release|Any CPU + {AFA9D41C-E8A5-32D3-E81B-2ABA7C37D46C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {AFA9D41C-E8A5-32D3-E81B-2ABA7C37D46C}.Debug|Any CPU.Build.0 = Debug|Any CPU + {AFA9D41C-E8A5-32D3-E81B-2ABA7C37D46C}.Release|Any CPU.ActiveCfg = Release|Any CPU + {AFA9D41C-E8A5-32D3-E81B-2ABA7C37D46C}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/CloudBuilderLauncher.exe.lnk b/CloudBuilderLauncher.exe.lnk new file mode 100644 index 0000000..f0d7394 Binary files /dev/null and b/CloudBuilderLauncher.exe.lnk differ diff --git a/CloudBuilderLauncher.sln b/CloudBuilderLauncher.sln index 6ae4086..ab78675 100644 --- a/CloudBuilderLauncher.sln +++ b/CloudBuilderLauncher.sln @@ -1,18 +1,8 @@  Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio Version 17 -VisualStudioVersion = 17.14.37111.16 d17.14 +VisualStudioVersion = 17.14.37111.16 MinimumVisualStudioVersion = 10.0.40219.1 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Core", "CloudBuilder.Core\CloudBuilder.Core.csproj", "{9FDA9022-7888-7E8B-B5EE-0302AA28EA34}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Security", "CloudBuilder.Security\CloudBuilder.Security.csproj", "{269A5036-BAE9-FD61-1DD5-0EA93B79F0D7}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Request", "CloudBuilder.Request\CloudBuilder.Request.csproj", "{6CB84CF4-7E06-780D-C061-2A8284878458}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Gui", "CloudBuilder.Gui\CloudBuilder.Gui.csproj", "{8EFE6D03-160F-4F1F-8E23-1CDDF98AD064}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilder.Security.Gui", "CloudBuilder.Security.Gui\CloudBuilder.Security.Gui.csproj", "{063D44BC-42F9-0A59-CE39-064C43029990}" -EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CloudBuilderLauncher", "CloudBuilderLauncher\CloudBuilderLauncher.csproj", "{6DA327D6-87FD-9F92-C842-B463A6E95A7F}" EndProject Global @@ -21,26 +11,6 @@ Global Release|Any CPU = Release|Any CPU EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution - {9FDA9022-7888-7E8B-B5EE-0302AA28EA34}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {9FDA9022-7888-7E8B-B5EE-0302AA28EA34}.Debug|Any CPU.Build.0 = Debug|Any CPU - {9FDA9022-7888-7E8B-B5EE-0302AA28EA34}.Release|Any CPU.ActiveCfg = Release|Any CPU - {9FDA9022-7888-7E8B-B5EE-0302AA28EA34}.Release|Any CPU.Build.0 = Release|Any CPU - {269A5036-BAE9-FD61-1DD5-0EA93B79F0D7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {269A5036-BAE9-FD61-1DD5-0EA93B79F0D7}.Debug|Any CPU.Build.0 = Debug|Any CPU - {269A5036-BAE9-FD61-1DD5-0EA93B79F0D7}.Release|Any CPU.ActiveCfg = Release|Any CPU - {269A5036-BAE9-FD61-1DD5-0EA93B79F0D7}.Release|Any CPU.Build.0 = Release|Any CPU - {6CB84CF4-7E06-780D-C061-2A8284878458}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {6CB84CF4-7E06-780D-C061-2A8284878458}.Debug|Any CPU.Build.0 = Debug|Any CPU - {6CB84CF4-7E06-780D-C061-2A8284878458}.Release|Any CPU.ActiveCfg = Release|Any CPU - {6CB84CF4-7E06-780D-C061-2A8284878458}.Release|Any CPU.Build.0 = Release|Any CPU - {8EFE6D03-160F-4F1F-8E23-1CDDF98AD064}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {8EFE6D03-160F-4F1F-8E23-1CDDF98AD064}.Debug|Any CPU.Build.0 = Debug|Any CPU - {8EFE6D03-160F-4F1F-8E23-1CDDF98AD064}.Release|Any CPU.ActiveCfg = Release|Any CPU - {8EFE6D03-160F-4F1F-8E23-1CDDF98AD064}.Release|Any CPU.Build.0 = Release|Any CPU - {063D44BC-42F9-0A59-CE39-064C43029990}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {063D44BC-42F9-0A59-CE39-064C43029990}.Debug|Any CPU.Build.0 = Debug|Any CPU - {063D44BC-42F9-0A59-CE39-064C43029990}.Release|Any CPU.ActiveCfg = Release|Any CPU - {063D44BC-42F9-0A59-CE39-064C43029990}.Release|Any CPU.Build.0 = Release|Any CPU {6DA327D6-87FD-9F92-C842-B463A6E95A7F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {6DA327D6-87FD-9F92-C842-B463A6E95A7F}.Debug|Any CPU.Build.0 = Debug|Any CPU {6DA327D6-87FD-9F92-C842-B463A6E95A7F}.Release|Any CPU.ActiveCfg = Release|Any CPU