diff --git a/RulesEngine.UnitTest/BusinessRuleEngineTest.cs b/RulesEngine.UnitTest/BusinessRuleEngineTest.cs index e2c40bac..849b46db 100644 --- a/RulesEngine.UnitTest/BusinessRuleEngineTest.cs +++ b/RulesEngine.UnitTest/BusinessRuleEngineTest.cs @@ -164,7 +164,6 @@ public async Task ExecuteRule_ManyInputs_ReturnsListOfRuleResultTree(string rule dynamic input14 = GetInput2(); dynamic input15 = GetInput3(); - dynamic input16 = GetInput1(); dynamic input17 = GetInput2(); dynamic input18 = GetInput3(); @@ -174,7 +173,6 @@ public async Task ExecuteRule_ManyInputs_ReturnsListOfRuleResultTree(string rule Assert.Contains(result, c => c.IsSuccess); } - [Theory] [InlineData("rules2.json")] public async Task ExecuteRule_CalledMultipleTimes_ReturnsSameResult(string ruleFileName) @@ -198,8 +196,6 @@ public async Task ExecuteRule_CalledMultipleTimes_ReturnsSameResult(string ruleF var expected = result1.Select(c => new { c.Rule.RuleName, c.IsSuccess }); var actual = result2.Select(c => new { c.Rule.RuleName, c.IsSuccess }); Assert.Equal(expected, actual); - - } [Theory] @@ -233,7 +229,6 @@ public async Task ExecuteRule_ExceptionScenario_RulesInvalid(string ruleFileName Assert.False(string.IsNullOrEmpty(result[0].ExceptionMessage) || string.IsNullOrWhiteSpace(result[0].ExceptionMessage)); } - [Fact] public void RulesEngine_New_IncorrectJSON_ThrowsException() { @@ -248,7 +243,6 @@ public void RulesEngine_New_IncorrectJSON_ThrowsException() }); } - [Fact] public void RulesEngine_AddOrUpdate_IncorrectJSON_ThrowsException() { @@ -265,7 +259,6 @@ public void RulesEngine_AddOrUpdate_IncorrectJSON_ThrowsException() }); } - [Theory] [InlineData("rules1.json")] public async Task ExecuteRule_InvalidWorkFlow_ThrowsException(string ruleFileName) @@ -292,7 +285,6 @@ public async Task RemoveWorkflow_RemovesWorkflow(string ruleFileName) await Assert.ThrowsAsync(async () => await re.ExecuteAllRulesAsync("inputWorkflow", new[] { input1, input2, input3 })); } - [Theory] [InlineData("rules1.json")] public async Task ClearWorkflow_RemovesAllWorkflow(string ruleFileName) @@ -507,7 +499,6 @@ public async Task ExecuteRuleWithIgnoreException_CompilationException_DoesNotRet Assert.False(result[1].ExceptionMessage.StartsWith("Exception while parsing expression")); } - [Theory] [InlineData("rules10.json")] public async Task ExecuteRuleWithJsonElement(string ruleFileName) @@ -802,12 +793,9 @@ public async Task RulesEngineWithGlobalParam_RunsSuccessfully(string ruleFileNam Assert.True(result[1].IsSuccess); } - - [Fact] public async Task ExecuteRule_RuntimeError_ShouldReturnAsErrorMessage() { - var workflow = new Workflow { WorkflowName = "TestWorkflow", Rules = new[] { @@ -830,11 +818,43 @@ public async Task ExecuteRule_RuntimeError_ShouldReturnAsErrorMessage() Assert.All(result, rule => Assert.StartsWith("Error while executing rule :", rule.ExceptionMessage)); } + [Fact] + public async Task ExecuteRule_RuntimeErrorInPreviousRun_ShouldReturnEmptyErrorMessage() + { + var workflow = new Workflow + { + WorkflowName = "TestWorkflow", + Rules = new[] { + new Rule { + RuleName = "ruleWithRuntimeError", + Expression = "input1.Country.ToLower() == \"india\"" + } + } + }; + + var re = new RulesEngine(new[] { workflow }, null); + var input = new RuleTestClass + { + Country = null + }; + + var result = await re.ExecuteAllRulesAsync("TestWorkflow", input); + + Assert.NotNull(result); + Assert.All(result, rule => Assert.False(rule.IsSuccess)); + Assert.All(result, rule => Assert.StartsWith("Error while executing rule :", rule.ExceptionMessage)); + + input.Country = "india"; + result = await re.ExecuteAllRulesAsync("TestWorkflow", input); + + Assert.NotNull(result); + Assert.All(result, rule => Assert.True(rule.IsSuccess)); + Assert.All(result, rule => Assert.Empty(rule.ExceptionMessage)); + } [Fact] public async Task ExecuteRule_RuntimeError_ThrowsException() { - var workflow = new Workflow { WorkflowName = "TestWorkflow", Rules = new[] { @@ -853,13 +873,11 @@ public async Task ExecuteRule_RuntimeError_ThrowsException() }; _ = await Assert.ThrowsAsync(async () => await re.ExecuteAllRulesAsync("TestWorkflow", [input])); - } [Fact] public async Task ExecuteRule_RuntimeError_IgnoreException_DoesNotReturnException() { - var workflow = new Workflow { WorkflowName = "TestWorkflow", Rules = new[] { @@ -884,7 +902,6 @@ public async Task ExecuteRule_RuntimeError_IgnoreException_DoesNotReturnExceptio Assert.All(result, rule => Assert.Empty(rule.ExceptionMessage)); } - [Fact] public async Task RemoveWorkFlow_ShouldRemoveAllCompiledCache() { @@ -983,7 +1000,6 @@ public async Task ExecuteRule_WithNullInput_ShouldNotThrowException() List result3 = await re.ExecuteAllRulesAsync("Test", new[] { input1 }); Assert.True(result3.All(c => c.IsSuccess)); - } [Fact] @@ -1011,7 +1027,6 @@ public async Task ExecuteRule_SpecialCharInWorkflowName_RunsSuccessfully() List result3 = await re.ExecuteAllRulesAsync("Exámple", new[] { input1 }); Assert.True(result3.All(c => c.IsSuccess)); - } [Fact] @@ -1038,10 +1053,6 @@ public void ContainsWorkFlowName_ShouldReturn() Assert.False(re.ContainsWorkflow(NotExistedWorkflowName)); } - - - - [Theory] [InlineData(typeof(RulesEngine), typeof(IRulesEngine))] public void Class_PublicMethods_ArePartOfInterface(Type classType, Type interfaceType) @@ -1050,15 +1061,11 @@ public void Class_PublicMethods_ArePartOfInterface(Type classType, Type interfac BindingFlags.Public | BindingFlags.Instance); - var interfaceMethods = interfaceType.GetMethods(); - Assert.Equal(interfaceMethods.Count(), classMethods.Count()); } - - private RulesEngine CreateRulesEngine(Workflow workflow) { var json = JsonConvert.SerializeObject(workflow); @@ -1155,8 +1162,6 @@ public bool CheckExists(string str) return false; } - } - } } \ No newline at end of file diff --git a/RulesEngine/HelperFunctions/Helpers.cs b/RulesEngine/HelperFunctions/Helpers.cs index a126edae..22176b19 100644 --- a/RulesEngine/HelperFunctions/Helpers.cs +++ b/RulesEngine/HelperFunctions/Helpers.cs @@ -18,9 +18,10 @@ internal static class Helpers internal static RuleFunc ToResultTree(ReSettings reSettings, Rule rule, IEnumerable childRuleResults, Func isSuccessFunc, string exceptionMessage = "") { return (inputs) => { - var isSuccess = false; var inputsDict = new Dictionary(); + string finalMessage = exceptionMessage; + try { inputsDict = inputs.ToDictionary(c => c.Name, c => c.Value); @@ -28,7 +29,7 @@ internal static RuleFunc ToResultTree(ReSettings reSettings, Rul } catch (Exception ex) { - exceptionMessage = GetExceptionMessage($"Error while executing rule : {rule?.RuleName} - {ex.Message}", reSettings); + finalMessage = GetExceptionMessage($"Error while executing rule : {rule?.RuleName} - {ex.Message}", reSettings); HandleRuleException(new RuleException(exceptionMessage,ex), rule, reSettings); isSuccess = false; } @@ -38,7 +39,7 @@ internal static RuleFunc ToResultTree(ReSettings reSettings, Rul Inputs = inputsDict, IsSuccess = isSuccess, ChildResults = childRuleResults, - ExceptionMessage = exceptionMessage + ExceptionMessage = finalMessage }; }; }