/// <summary>
        /// This code gets called on the first time this Object type is constructed
        /// </summary>
        void AddSharedBusinessRules()
        {
            lock (_LockObject) {
                if (!SharedValidationRules.RulesExistFor(this.GetType()))
                {
                    ValidationRulesManager          mgrValidation      = SharedValidationRules.GetManager(this.GetType());
                    CharacterFormattingRulesManager mgrCharacterCasing = SharedCharacterFormattingRules.GetManager(this.GetType());

                    foreach (var propInfo in PclReflection.GetPropertiesInfo(this))
                    {
                        foreach (var atr in propInfo.GetCustomAttributes <BaseValidatorAttribute>(false))
                        {
                            mgrValidation.AddRule(atr.Create(propInfo.Name), propInfo.Name);
                        }

                        foreach (var atr in propInfo.GetCustomAttributes <CharacterFormattingAttribute>(false))
                        {
                            mgrCharacterCasing.AddRule(propInfo.Name, atr.CharacterCasing, atr.RemoveSpace);
                        }
                    }

                    AddSharedBusinessValidationRules(mgrValidation);
                    AddSharedCharacterCasingFormattingRules(mgrCharacterCasing);
                }
            }
        }
Пример #2
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the postal code rule for the specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="StateAbbreviationRuleDescriptor" />.</param>
        /// <returns><c>True</c> does the target property specified in the ruleDescriptor meet the postal code rule for the specified property; otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentException">wrong rule passed to ruleDescriptor</exception>
        /// <exception cref="NotSupportedException">Postal code validation rule can only be applied to String properties</exception>
        public static Boolean PostalCodeRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            var args = ruleDescriptor as PostCodeRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to PostalCodeRule: {ruleDescriptor.GetType()}");
            }

            if (args.ValidateForUnitedStatesOnly == ValidateUnitedStatesOnly.Yes)
            {
                var pi = PclReflection.GetPropertyInfo(target, "Country");
                if (pi == null)
                {
                    return(true);
                }
                if (Convert.ToString(pi.GetValue(target, null)) != "United States")
                {
                    return(true);
                }
            }

            var objPi = PclReflection.GetPropertyInfo(target, args.PropertyName);

            if (objPi.PropertyType != typeof(String))
            {
                throw new NotSupportedException("Postal code validation rule can only be applied to String properties");
            }

            var postalCode = Convert.ToString(objPi.GetValue(target, null)).Trim();

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (String.IsNullOrEmpty(postalCode))
                {
                    ruleDescriptor.BrokenRuleDescription = $"Postal code was null or empty but is a required field: {RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)}";
                    return(false);
                }
            }
            else
            {
                if (String.IsNullOrEmpty(postalCode))
                {
                    return(true);
                }
            }

            const String pattern = "^\\d{5}(-\\d{4})?$";
            var          brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required Zip Code pattern";

            if (Regex.IsMatch(postalCode, pattern, RegexOptions.IgnoreCase))
            {
                return(true);
            }
            ruleDescriptor.BrokenRuleDescription = brokenRuleDescription;
            return(false);
        }
Пример #3
0
        /// <summary>
        /// Builds up a string containing each property and value in the class. The string displays the property name, property friendly name and property value.
        /// </summary>
        /// <typeparam name="T">Class Type</typeparam>
        /// <param name="instance">Instance of the class</param>
        /// <param name="delimiter">What delimiter do you want between each property? Defaults to comma; can pass others like Environment.NewLine, etc.</param>
        /// <param name="sortByPropertyName">If set to <c>SortByPropertyName.Yes</c> then output will be sorted by AuditAttribute.AuditSequence and then property name; otherwise no additional sorting is performed and properties; will be left in ordinal order.</param>
        /// <returns>A string containing each property name, friendly name and value, separated by the delimiter and optionally sorted by property name.</returns>
        public static String ClassToString <T>(T instance, String delimiter = GlobalConstants.DefaultDelimiter, SortByPropertyName sortByPropertyName = SortByPropertyName.Yes)
        {
            var sb   = new StringBuilder(4096);
            var list = new List <SortablePropertyBasket>();

            foreach (var propInfo in PclReflection.GetPropertiesInfo(instance))
            {
                var auditAttributes    = propInfo.GetCustomAttributes <AuditAttribute>(false);
                var auditAttributeList = new List <AuditAttribute>(auditAttributes);

                AuditAttribute auditAttribute = null;

                if (auditAttributeList.Count == 1)
                {
                    auditAttribute = auditAttributeList[0];
                }

                var auditSequence = 1;

                if (auditAttribute != null)
                {
                    auditSequence = auditAttribute.AuditSequence;
                }
                if (propInfo.Name != "Item" && propInfo.Name != "ValidationErrors")
                {
                    list.Add(propInfo.GetValue(instance, null) != null ? new SortablePropertyBasket(auditSequence, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), propInfo.GetValue(instance, null).ToString()) : new SortablePropertyBasket(auditSequence, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), Null));
                }
            }

            if (list.Count > 0)
            {
                if (sortByPropertyName == SortByPropertyName.Yes)
                {
                    list.Sort();
                }

                foreach (var propertyBasket in list)
                {
                    sb.Append(propertyBasket);
                    sb.Append(delimiter);
                }

                if (sb.Length > delimiter.Length)
                {
                    sb.Length -= delimiter.Length;
                }
            }
            else
            {
                sb.Append("Class has no properties");
            }

            return(sb.ToString());
        }
Пример #4
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the state abbreviation rule for the specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="StateAbbreviationRuleDescriptor" />.</param>
        /// <returns><c>True</c> does the target property specified in the ruleDescriptor meets the state abbreviation rule for the specified property; otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentException">wrong rule passed to ruleDescriptor</exception>
        /// <exception cref="NotSupportedException">State abbreviation validation rule can only be applied to String properties</exception>
        public static Boolean StateAbbreviationRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            var args = ruleDescriptor as StateAbbreviationRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to StateAbbreviationRule {ruleDescriptor.GetType()}");
            }

            if (args.ValidateForUnitedStatesOnly == ValidateUnitedStatesOnly.Yes)
            {
                var pi = PclReflection.GetPropertyInfo(target, "Country");
                if (pi == null)
                {
                    return(true);
                }
                if (Convert.ToString(pi.GetValue(target, null)) != "United States")
                {
                    return(true);
                }
            }
            var objPi = PclReflection.GetPropertyInfo(target, args.PropertyName);

            if (objPi.PropertyType != typeof(String))
            {
                throw new NotSupportedException("State abbreviation validation rule can only be applied to String properties");
            }

            var state = Convert.ToString(objPi.GetValue(target, null));

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (String.IsNullOrEmpty(state))
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} was null or empty but is a required field";
                    return(false);
                }
            }
            else
            {
                if (String.IsNullOrEmpty(state))
                {
                    return(true);
                }
            }

            if (StateAbbreviationValidator.CreateInstance().IsValid(state))
            {
                return(true);
            }
            args.BrokenRuleDescription = $"The entered value {state} is not a valid state abbreviation";
            return(false);
        }
Пример #5
0
        /// <summary>
        /// Builds up a string containing each property and value in the class decorated with the AuditAttribute. The string displays the property name, property friendly name and property value.
        /// </summary>
        /// <typeparam name="T">Class Type</typeparam>
        /// <param name="instance">Instance of the class</param>
        /// <param name="defaultValue">If no class properties are decorated with the <see cref="AuditAttribute"/> then a single entry will be added to the dictionary that is named 'DefaultValue' and will have the value of defaultValue.</param>
        /// <param name="delimiter">What delimiter do you want between each property? Defaults to comma; can pass others like Environment.NewLine, etc.</param>
        /// <param name="includeAllProperties">if set to <c>true</c> [include all attributes].</param>
        /// <returns>A string containing each property name, friendly name and value, separated by the delimiter and sorted by AuditAttribute.AuditSequence and then property name.</returns>
        public static String AuditToString <T>(T instance, String defaultValue, String delimiter = GlobalConstants.DefaultDelimiter, Boolean includeAllProperties = false)
        {
            var sb   = new StringBuilder(2048);
            var list = new List <SortablePropertyBasket>();
            var nonAttributedPropertyIndex = 0;

            foreach (var propInfo in PclReflection.GetPropertiesInfo(instance))
            {
                var            auditAttributes    = propInfo.GetCustomAttributes <AuditAttribute>(false);
                var            auditAttributeList = new List <AuditAttribute>(auditAttributes);
                AuditAttribute auditAttribute     = null;

                if (auditAttributeList.Count == 1)
                {
                    auditAttribute = auditAttributeList[0];
                }

                if (auditAttribute != null)
                {
                    list.Add(propInfo.GetValue(instance, null) != null ? new SortablePropertyBasket(auditAttribute.AuditSequence, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), propInfo.GetValue(instance, null).ToString()) : new SortablePropertyBasket(auditAttribute.AuditSequence, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), Null));
                }
                else if (includeAllProperties && propInfo.Name != "Item")
                {
                    nonAttributedPropertyIndex += 1;
                    list.Add(propInfo.GetValue(instance, null) != null ? new SortablePropertyBasket(nonAttributedPropertyIndex, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), propInfo.GetValue(instance, null).ToString()) : new SortablePropertyBasket(nonAttributedPropertyIndex, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), Null));
                }
            }

            if (list.Count > 0)
            {
                list.Sort();

                foreach (SortablePropertyBasket propertyBasket in list)
                {
                    sb.Append(propertyBasket);
                    sb.Append(delimiter);
                }

                if (sb.Length > delimiter.Length)
                {
                    sb.Length -= delimiter.Length;
                }
            }
            else
            {
                sb.Append(defaultValue);
            }

            return(sb.ToString());
        }
Пример #6
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor is equal to the other specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="ComparePasswordRuleDescriptor" />.</param>
        /// <returns><c>True</c> if the target property specified in the ruleDescriptor is equal to the other specified property, otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentNullException">target or ruleDescriptor is null.</exception>
        /// <exception cref="ArgumentException">Wrong rule passed to ComparePropertyRule</exception>
        public static Boolean ComparePasswordRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            if (target == null)
            {
                throw new ArgumentNullException(nameof(target));
            }
            if (ruleDescriptor == null)
            {
                throw new ArgumentNullException(nameof(ruleDescriptor));
            }
            var args = ruleDescriptor as ComparePasswordRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to ComparePasswordRule {ruleDescriptor.GetType()}");
            }

            PropertyInfo pi     = PclReflection.GetPropertyInfo(target, args.PropertyName);
            var          source = pi.GetValue(target, null);

            if (source == null)
            {
                return(true);
            }

            pi = PclReflection.GetPropertyInfo(target, args.CompareToPropertyName);
            var testAgainst = pi.GetValue(target, null);

            if (testAgainst == null)
            {
                return(true);
            }

            var iSource      = (IComparable)source;
            var iTestAgainst = (IComparable)testAgainst;
            var result       = iSource.CompareTo(iTestAgainst);

            if (result == 0)
            {
                return(true);
            }
            ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be equal to {InputStringFormatting.CamelCaseString.GetWords(args.CompareToPropertyName)}.";
            return(false);
        }
Пример #7
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the String length criteria for the specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="StringLengthRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor meets the String length criteria for the specified property; otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentException">wrong rule passed to ruleDescriptor</exception>
        public static Boolean StringLengthRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            var args = ruleDescriptor as StringLengthRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to StringLengthRule {ruleDescriptor.GetType()}");
            }

            var objPi  = PclReflection.GetPropertyInfo(target, args.PropertyName);
            var testMe = Convert.ToString(objPi.GetValue(target, null));

            // ReSharper disable ConditionIsAlwaysTrueOrFalse
            if (args.AllowNullString == AllowNullString.No && (testMe == null))
            {
                // ReSharper restore ConditionIsAlwaysTrueOrFalse
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} can not be null";
                return(false);
            }

            if (args.AllowNullString == AllowNullString.Yes && String.IsNullOrWhiteSpace(testMe))
            {
                return(true);
            }

            if (String.IsNullOrEmpty(testMe))
            {
                testMe = String.Empty;
            }

            if (args.MinimumLength > 0 && testMe.Length < args.MinimumLength)
            {
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} can not be less than {args.MinimumLength} character's long";
                return(false);
            }

            if (args.MaximumLength > 0 && testMe.Length > args.MaximumLength)
            {
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} can not be greater than {args.MaximumLength} character's long";
                return(false);
            }

            return(true);
        }
Пример #8
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the domain rule. A domain in this case means an array of valid values.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="DomainRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor meets the domain rule, otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentNullException">target or ruleDescriptor was null.</exception>
        /// <exception cref="ArgumentException">If the ruleDescriptor is not of type <see cref="DomainRuleDescriptor" />.</exception>
        public static Boolean DomainRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            if (target == null)
            {
                throw new ArgumentNullException(nameof(target));
            }
            if (ruleDescriptor == null)
            {
                throw new ArgumentNullException(nameof(ruleDescriptor));
            }
            var args = ruleDescriptor as DomainRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to DomainRule: {ruleDescriptor.GetType()}");
            }

            PropertyInfo pi            = PclReflection.GetPropertyInfo(target, args.PropertyName);
            String       propertyValue = Convert.ToString(pi.GetValue(target, null));

            if (args.RequiredEntry == RequiredEntry.No && String.IsNullOrEmpty(propertyValue))
            {
                return(true);
            }

            if (args.Data.Any(s => String.Compare(s, propertyValue, StringComparison.OrdinalIgnoreCase) == 0))
            {
                return(true);
            }

            var sb = new System.Text.StringBuilder(1024);

            sb.AppendFormat("The {0} did not match any of the following acceptable values.", RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor));

            const String format = ", {0}";

            foreach (String s in args.Data)
            {
                sb.AppendFormat(format, s);
            }

            ruleDescriptor.BrokenRuleDescription = sb.ToString();
            return(false);
        }
Пример #9
0
        /// <summary>
        /// Populates the passed in IDictionary with property's name and value in the class for properties decorated with the <see cref="AuditAttribute"/>.
        /// </summary>
        /// <typeparam name="T">Class type.</typeparam>
        /// <param name="instance">The instance.</param>
        /// <param name="defaultValue">If no class properties are decorated with the <see cref="AuditAttribute"/> then a single entry will be added to the dictionary that is named 'DefaultValue' and will have the value of defaultValue.</param>
        /// <param name="dictionary">Pass an IDictionary object that needs to be populated. This could be the Data property of an exception object that you want to populate, etc.</param>
        /// <param name="sortByPropertyName">If set to <c>SortByPropertyName.Yes</c> then output will be sorted by AuditAttribute.AuditSequence and then property name; otherwise no additional sorting is performed and properties; will be left in ordinal order.</param>
        /// <returns>The dictionary passed in populated with properties and values.</returns>
        public static IDictionary <String, String> ClassToIDictionary <T>(T instance, String defaultValue, IDictionary <String, String> dictionary, SortByPropertyName sortByPropertyName = SortByPropertyName.Yes)
        {
            var list = new List <SortablePropertyBasket>();

            foreach (var propInfo in PclReflection.GetPropertiesInfo(instance))
            {
                var auditAttributes    = propInfo.GetCustomAttributes <AuditAttribute>(false);
                var auditAttributeList = new List <AuditAttribute>(auditAttributes);

                AuditAttribute auditAttribute = null;

                if (auditAttributeList.Count == 1)
                {
                    auditAttribute = auditAttributeList[0];
                }

                if (auditAttribute != null)
                {
                    list.Add(new SortablePropertyBasket(One, propInfo.Name, String.Empty, propInfo.GetValue(instance, null).ToString()));
                }
            }

            if (list.Count > 0)
            {
                if (sortByPropertyName == SortByPropertyName.Yes)
                {
                    list.Sort();
                }

                foreach (SortablePropertyBasket propertyBasket in list)
                {
                    dictionary.Add(propertyBasket.PropertyName, propertyBasket.Value);
                }
            }
            else
            {
                dictionary.Add(DefaultValue, defaultValue);
            }

            return(dictionary);
        }
Пример #10
0
        /// <summary>
        /// Populates the dictionary with property's name and value in the class for properties decorated with the <see cref="AuditAttribute"/>.
        /// </summary>
        /// <typeparam name="T">Class type.</typeparam>
        /// <param name="instance">The instance.</param>
        /// <param name="defaultValue">If no class properties are decorated with the <see cref="AuditAttribute"/> then a single entry will be added to the dictionary that is named 'DefaultValue' and will have the value of defaultValue.</param>.
        /// <param name="dictionary">Pass an IDictionary object that needs to be populated. This could be the Data property of an exception object that you want to populate, etc.</param>
        /// <returns>IDictionary populated with properties and values.</returns>
        public static IDictionary <String, String> AuditToIDictionary <T>(T instance, String defaultValue, IDictionary <String, String> dictionary)
        {
            var list = new List <SortablePropertyBasket>();

            foreach (var propInfo in PclReflection.GetPropertiesInfo(instance))
            {
                var auditAttributes    = propInfo.GetCustomAttributes <AuditAttribute>(false);
                var auditAttributeList = new List <AuditAttribute>(auditAttributes);

                AuditAttribute auditAttribute = null;

                if (auditAttributeList.Count == 1)
                {
                    auditAttribute = auditAttributeList[0];
                }
                if (auditAttribute != null)
                {
                    list.Add(new SortablePropertyBasket(auditAttribute.AuditSequence, propInfo.Name, CamelCaseString.GetWords(propInfo.Name), propInfo.GetValue(instance, null).ToString()));
                }
            }

            if (list.Count > 0)
            {
                list.Sort();

                foreach (var propertyBasket in list)
                {
                    dictionary.Add(propertyBasket.PropertyName, propertyBasket.Value);
                }
            }
            else
            {
                dictionary.Add(DefaultValue, defaultValue);
            }

            return(dictionary);
        }
Пример #11
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor is not null.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="NotNullRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor is not null, otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentNullException">Either target or ruleDescriptor is null.</exception>
        /// <exception cref="ArgumentException">If the ruleDescriptor is not of type <see cref="NotNullRuleDescriptor" />.</exception>
        public static Boolean NotNullRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            if (target == null)
            {
                throw new ArgumentNullException(nameof(target));
            }
            if (ruleDescriptor == null)
            {
                throw new ArgumentNullException(nameof(ruleDescriptor));
            }

            //Boxing and Unboxing
            //When a nullable type is boxed, the common language runtime automatically boxes the underlying value of the
            //Nullable Object, not the Nullable Object itself. That is, if the HasValue property is true, the contents
            //of the Value property is boxed. If the HasValue property is false, a null reference (Nothing in Visual Basic) is boxed.
            //When the underlying value of a nullable type is un-boxed, the common language runtime creates a new
            //Nullable structure initialized to the underlying value.
            var args = ruleDescriptor as NotNullRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to NotNullRule {ruleDescriptor.GetType()}");
            }

            PropertyInfo pi     = PclReflection.GetPropertyInfo(target, args.PropertyName);
            Object       source = pi.GetValue(target, null);

            //this handles both Nullable and standard uninitialized values
            if (source == null)
            {
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} is null.";
                return(false);
            }

            return(true);
        }
Пример #12
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the comparison criteria against another specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="ComparePropertyRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor meets the comparison criteria against another specified property, otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentNullException">target or ruleDescriptor is null.</exception>
        /// <exception cref="ArgumentException">Wrong rule passed to ComparePropertyRule</exception>
        /// <exception cref="OverflowException">comparison type not programmed</exception>
        public static Boolean ComparePropertyRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            if (target == null)
            {
                throw new ArgumentNullException(nameof(target));
            }
            if (ruleDescriptor == null)
            {
                throw new ArgumentNullException(nameof(ruleDescriptor));
            }
            var args = ruleDescriptor as ComparePropertyRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to ComparePropertyRule {ruleDescriptor.GetType()}");
            }

            PropertyInfo pi           = PclReflection.GetPropertyInfo(target, args.PropertyName);
            Object       source       = pi.GetValue(target, null);
            var          stringSource = source as String;

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (source == null || (stringSource != null && String.IsNullOrWhiteSpace(stringSource)))
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} was null or empty but is a required field.";
                    return(false);
                }
            }
            else
            {
                if (source == null)
                {
                    return(true);
                }
            }

            pi = PclReflection.GetPropertyInfo(target, args.CompareToPropertyName);
            Object testAgainst = pi.GetValue(target, null);

            if (testAgainst == null)
            {
                return(true);
            }

            var   iSource      = (IComparable)source;
            var   iTestAgainst = (IComparable)testAgainst;
            Int32 result       = iSource.CompareTo(iTestAgainst);

            switch (args.ComparisonType)
            {
            case ComparisonType.Equal:

                if (result == 0)
                {
                    return(true);
                }
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be equal to {testAgainst}.";
                return(false);

            case ComparisonType.GreaterThan:

                if (result > 0)
                {
                    return(true);
                }
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be greater than {testAgainst}.";
                return(false);

            case ComparisonType.GreaterThanEqual:

                if (result >= 0)
                {
                    return(true);
                }
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be greater than or equal to {testAgainst}.";
                return(false);

            case ComparisonType.LessThan:

                if (result < 0)
                {
                    return(true);
                }
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be less than {testAgainst}.";
                return(false);

            case ComparisonType.LessThanEqual:

                if (result <= 0)
                {
                    return(true);
                }
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be less than or equal to {testAgainst}.";
                return(false);

            case ComparisonType.NotEqual:

                if (result != 0)
                {
                    return(true);
                }
                ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must not equal {testAgainst}.";
                return(false);

            default:
                throw new OverflowException("comparison type not programmed");
            }
        }
Пример #13
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor is within the specified range.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="RangeRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor is within the specified range, otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentNullException">target or ruleDescriptor is null.</exception>
        /// <exception cref="ArgumentException">Wrong rule passed to InRangeRule</exception>
        public static Boolean InRangeRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            if (target == null)
            {
                throw new ArgumentNullException(nameof(target));
            }
            if (ruleDescriptor == null)
            {
                throw new ArgumentNullException(nameof(ruleDescriptor));
            }

            var args = ruleDescriptor as RangeRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to InRangeRule {ruleDescriptor.GetType()}");
            }

            PropertyInfo pi           = PclReflection.GetPropertyInfo(target, args.PropertyName);
            Object       source       = pi.GetValue(target, null);
            var          stringSource = source as String;

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (source == null || (stringSource != null && String.IsNullOrWhiteSpace(stringSource)))
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} was null or empty but is a required field.";
                    return(false);
                }
            }
            else
            {
                if (source == null)
                {
                    return(true);
                }
            }

            var    iSource     = (IComparable)source;
            Object lower       = args.LowerValue;
            Object upper       = args.UpperValue;
            Int32  lowerResult = iSource.CompareTo(args.LowerValue);

            if (args.LowerRangeBoundaryType == RangeBoundaryType.Inclusive)
            {
                if (lowerResult < 0)
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be greater than or equal to {lower}";
                    return(false);
                }
            }
            else
            {
                if (lowerResult <= 0)
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be greater than {lower}";
                    return(false);
                }
            }

            Int32 upperResult = iSource.CompareTo(args.UpperValue);

            if (args.UpperRangeBoundaryType == RangeBoundaryType.Inclusive)
            {
                if (upperResult > 0)
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be less than {upper}";
                    return(false);
                }
            }
            else
            {
                if (upperResult >= 0)
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} must be less than or equal to {upper}";
                    return(false);
                }
            }

            return(true);
        }
Пример #14
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the regular expression rule for the specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="RegularExpressionRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor meets the state abbreviation rule for the specified property; otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentException">wrong rule passed to ruleDescriptor</exception>
        /// <exception cref="InvalidOperationException">
        /// CustomRegularExpressionPattern not supplied
        /// or
        /// CustomRegularExpressionPattern is not a valid RegEx pattern.
        /// </exception>
        /// <exception cref="OverflowException">RegularExpressionPatternType type not programmed</exception>
        public static Boolean RegularExpressionRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            //great site for patterns
            //http://regexlib.com/Search.aspx
            //
            var args = ruleDescriptor as RegularExpressionRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to RegularExpressionRule {ruleDescriptor.GetType()}");
            }

            var objPi  = PclReflection.GetPropertyInfo(target, args.PropertyName);
            var testMe = Convert.ToString(objPi.GetValue(target, null));

            if (args.RegularExpressionPatternType == RegularExpressionPatternType.Custom && String.IsNullOrEmpty(args.CustomRegularExpressionPattern))
            {
                throw new InvalidOperationException("CustomRegularExpressionPattern not supplied");
            }

            if (!IsRegularExpressionPatternValid(args.CustomRegularExpressionPattern))
            {
                throw new InvalidOperationException("CustomRegularExpressionPattern is not a valid RegEx pattern.");
            }

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (String.IsNullOrWhiteSpace(testMe))
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} was null or empty but is a required field";
                    return(false);
                }
            }
            else
            {
                if (testMe.Trim().Length == 0)
                {
                    return(true);
                }
            }

            String pattern;
            String brokenRuleDescription;

            switch (args.RegularExpressionPatternType)
            {
            case RegularExpressionPatternType.Custom:
                pattern = args.CustomRegularExpressionPattern;
                brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required {pattern} pattern";

                break;

            case RegularExpressionPatternType.Email:
                pattern = "^\\w+([-+.]\\w+)*@\\w+([-.]\\w+)*\\.\\w+([-.]\\w+)*$";
                brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required email pattern";

                break;

            case RegularExpressionPatternType.IPAddress:
                pattern = "^((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])\\.){3}(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])$";
                brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required IP Address pattern";

                break;

            case RegularExpressionPatternType.SSN:
                pattern = "^\\d{3}-\\d{2}-\\d{4}$";
                brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required SSN pattern";

                break;

            case RegularExpressionPatternType.Url:
                pattern = "(?#WebOrIP)((?#protocol)((news|nntp|telnet|http|ftp|https|ftps|sftp):\\/\\/)?(?#subDomain)(([a-zA-Z0-9]+\\.*(?#domain)[a-zA-Z0-9\\-]+(?#TLD)(\\.[a-zA-Z]+){1,2})|(?#IPAddress)((25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[1-9])\\.(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[1-9]|0)\\.(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[1-9]|0)\\.(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[0-9])))+(?#Port)(:[1-9][0-9]*)?)+(?#Path)((\\/((?#dirOrFileName)[a-zA-Z0-9 \\-\\%\\~\\+]+)?)*)?(?#extension)(\\.([a-zA-Z0-9 ]+))?(?#parameters)(\\?([a-zA-Z0-9 \\-]+\\=[a-z-A-Z0-9 \\-\\%\\~\\+]+)?(?#additionalParameters)(\\&([a-zA-Z0-9 \\-]+\\=[a-z-A-Z0-9 \\-\\%\\~\\+]+)?)*)?";
                brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required URL pattern";

                break;

            case RegularExpressionPatternType.ZipCode:
                pattern = "^\\d{5}(-\\d{4})?$";
                brokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} did not match the required Zip Code pattern";

                break;

            default:
                throw new OverflowException("RegularExpressionPatternType type not programmed");
            }

            if (Regex.IsMatch(testMe, pattern, RegexOptions.IgnoreCase))
            {
                return(true);
            }
            ruleDescriptor.BrokenRuleDescription = brokenRuleDescription;
            return(false);
        }
Пример #15
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the bank routing number rule for the specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="BankRoutingNumberRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor meets the bank routing number rule for the specified property; otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentException">wrong rule passed to ruleDescriptor</exception>
        /// <exception cref="NotSupportedException">Bank routing number validation rule can only be applied to a String</exception>
        public static Boolean BankRoutingNumberRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            var args = ruleDescriptor as BankRoutingNumberRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule {ruleDescriptor.GetType()}, passed to BankRoutingNumberRule");
            }

            var objPi = PclReflection.GetPropertyInfo(target, args.PropertyName);

            if (objPi.PropertyType != typeof(String))
            {
                throw new NotSupportedException("Bank routing number validation rule can only be applied to a String");
            }

            String bankRoutingNumber = Convert.ToString(objPi.GetValue(target, null));

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (String.IsNullOrEmpty(bankRoutingNumber))
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} null or empty but is a required field";
                    return(false);
                }
            }
            else
            {
                if (String.IsNullOrEmpty(bankRoutingNumber))
                {
                    return(true);
                }
            }

            var lengthBankRoutingNumber = bankRoutingNumber.Length;
            var value = 0;

            if (lengthBankRoutingNumber != 9)
            {
                args.BrokenRuleDescription = $"The entered value {bankRoutingNumber} is not a valid bank routing number.  All bank routing numbers are 9 digit in length";
                return(false);
            }

            if (Int32.Parse(bankRoutingNumber.Substring(0, 1)) > 1)
            {
                args.BrokenRuleDescription = $"The entered value {bankRoutingNumber} is not a valid bank routing number. The first digit must be a 0 or a 1";
                return(false);
            }

            if (bankRoutingNumber.Cast <Char>().Any(c => !Char.IsDigit(c)))
            {
                args.BrokenRuleDescription = $"The entered value {bankRoutingNumber} is not a valid bank routing number. Only numeric input is allowed";
                return(false);
            }

            for (var intX = 0; intX <= 8; intX += 3)
            {
                value += Int32.Parse(bankRoutingNumber.Substring(intX, 1)) * 3;
                value += Int32.Parse(bankRoutingNumber.Substring(intX + 1, 1)) * 7;
                value += Int32.Parse(bankRoutingNumber.Substring(intX + 2, 1));
            }

            if (value % 10 != 0)
            {
                args.BrokenRuleDescription = $"The entered value {bankRoutingNumber} is not a valid bank routing number";
                return(false);
            }
            return(true);
        }
Пример #16
0
        /// <summary>
        /// Validation rule that checks if the target property specified in the ruleDescriptor meets the credit card number rule for the specified property.
        /// </summary>
        /// <param name="target">The target instance.</param>
        /// <param name="ruleDescriptor">The ruleDescriptor of type <see cref="CreditCardNumberRuleDescriptor" />.</param>
        /// <returns><c>True</c> is the target property specified in the ruleDescriptor meets the credit card number rule for the specified property; otherwise <c>false</c>.</returns>
        /// <exception cref="ArgumentException">wrong rule passed to ruleDescriptor</exception>
        /// <exception cref="NotSupportedException">Credit card number validation rule can only be applied to String properties</exception>
        public static Boolean CreditCardNumberRule(Object target, RuleDescriptorBase ruleDescriptor)
        {
            var args = ruleDescriptor as CreditCardNumberRuleDescriptor;

            if (args == null)
            {
                throw new ArgumentException($"Wrong rule passed to CreditCardNumberRule {ruleDescriptor.GetType()}");
            }

            var objPi = PclReflection.GetPropertyInfo(target, args.PropertyName);

            if (objPi.PropertyType != typeof(String))
            {
                throw new NotSupportedException("Credit card number validation rule can only be applied to String properties");
            }

            var cardNumber = Convert.ToString(objPi.GetValue(target, null));

            if (args.RequiredEntry == RequiredEntry.Yes)
            {
                if (String.IsNullOrEmpty(cardNumber))
                {
                    ruleDescriptor.BrokenRuleDescription = $"{RuleDescriptorBase.GetPropertyFriendlyName(ruleDescriptor)} was null or empty but is a required field";
                    return(false);
                }
            }
            else
            {
                if (String.IsNullOrEmpty(cardNumber))
                {
                    return(true);
                }
            }

            var   lengthCreditCardNumber = cardNumber.Length;
            var   cardArray = new Int32[lengthCreditCardNumber + 1];
            Int32 value;

            if (cardNumber.Cast <Char>().Any(c => !Char.IsDigit(c)))
            {
                args.BrokenRuleDescription = $"The entered value {cardNumber} is not a valid credit card number. Only numeric input is allowed";
                return(false);
            }

            for (var count = lengthCreditCardNumber - 1; count >= 1; count -= 2)
            {
                value            = Convert.ToInt32(cardNumber.Substring(count - 1, 1)) * 2;
                cardArray[count] = value;
            }

            value = 0;

            var start = lengthCreditCardNumber % 2 == 0 ? 2 : 1;

            for (var count = start; count <= lengthCreditCardNumber; count += 2)
            {
                value = value + Convert.ToInt32(cardNumber.Substring(count - 1, 1));
                var arrValue = cardArray[count - 1];

                if (arrValue < 10)
                {
                    value = value + arrValue;
                }
                else
                {
                    value = value + Convert.ToInt32(Convert.ToString(arrValue).Substring(0, 1)) + Convert.ToInt32(Convert.ToString(arrValue).Substring(Convert.ToString(arrValue).Length - 1));
                }
            }

            if (value % 10 != 0)
            {
                args.BrokenRuleDescription = $"The entered value {cardNumber} is not a valid credit card number";
                return(false);
            }
            return(true);
        }