using System; using System.Collections.Generic; using System.Linq; using System.Reflection; using YLErp.DBModels; using YLErp.Modules.RiskEngine.Dto; namespace YLErp.Modules.RiskEngine { [TestClass] public class RiskRuleApplicationStatusDecoupleContractTest { private static readonly string[] AvailabilityPropertyNames = { "AssociatedRuleCount", "EffectiveRuleCount", "CanEnable", "CanDisable", "EnableButtonTooltip", "DisableButtonTooltip" }; [TestMethod] public void DisableRuleResult_UsesDecoupledContract() { AssertProperty("RuleId", typeof(long)); AssertProperty("AffectedActiveAppCount", typeof(int)); Assert.IsNull(typeof(DisableRuleResult).GetProperty("CascadedApplicationIds")); } [TestMethod] public void DeleteRuleResult_ReportsAffectedApplications() { AssertProperty("RuleId", typeof(long)); AssertProperty("AffectedActiveAppCount", typeof(int)); AssertProperty("CausedNoAvailableRuleAppIds", typeof(List)); } [TestMethod] public void ApplicationDtos_ExposeAvailabilityFields() { AssertAvailabilityProperties(); AssertAvailabilityProperties(); } [TestMethod] public void BatchOperationResult_ExposesDecoupledApplicationImpactFields() { AssertProperty("AffectedApplicationIds", typeof(List)); AssertProperty("CausedNoAvailableRuleApplicationIds", typeof(List)); AssertProperty("AffectedApplicationIds", typeof(List)); AssertProperty("CausedNoAvailableRuleApplicationIds", typeof(List)); } [TestMethod] public void VariableDeleteReferenceMessage_ListsDistinctSortedRuleIds() { var method = typeof(RiskRuleService).GetMethod( "BuildVariableDeleteReferenceMessage", BindingFlags.NonPublic | BindingFlags.Static); Assert.IsNotNull(method); var rules = new List { new glms_risk_rule { id = 12 }, new glms_risk_rule { id = 10 }, new glms_risk_rule { id = 12 } }; var message = (string)method.Invoke(null, new object[] { rules }); Assert.AreEqual("该变量被 2 个规则引用(规则ID:10、12),无法删除", message); } private static void AssertAvailabilityProperties() { foreach (var propertyName in AvailabilityPropertyNames) { var expectedType = propertyName.EndsWith("Tooltip", StringComparison.Ordinal) ? typeof(string) : propertyName.StartsWith("Can", StringComparison.Ordinal) ? typeof(bool) : typeof(int); AssertProperty(propertyName, expectedType); } } private static void AssertProperty(string propertyName, Type expectedType) { var property = typeof(T).GetProperty(propertyName); Assert.IsNotNull(property, $"{typeof(T).Name}.{propertyName} should exist."); Assert.AreEqual(expectedType, property.PropertyType, $"{typeof(T).Name}.{propertyName} type mismatch."); } } }