public override bool Validate(RuleValidation validation) { if (validation == null) { throw new ArgumentNullException("validation"); } bool valid = true; if (_expression == null) { valid = false; string message = string.Format(CultureInfo.CurrentCulture, Messages.ConditionExpressionNull, typeof(CodePrimitiveExpression).ToString()); ValidationError error = new ValidationError(message, ErrorNumbers.Error_EmptyExpression); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); } else { valid = validation.ValidateConditionExpression(_expression); } return(valid); }
public override bool Validate(RuleValidation validator) { if (validator == null) { throw new ArgumentNullException("validator"); } if (codeDomStatement == null) { ValidationError error = new ValidationError(Messages.NullStatement, ErrorNumbers.Error_ParameterNotSet); error.UserData[RuleUserDataKeys.ErrorObject] = this; validator.AddError(error); return(false); } else { return(CodeDomStatementWalker.Validate(validator, codeDomStatement)); } }
public bool Validate(RuleValidation validation) { if (validation == null) { throw new ArgumentNullException("validation"); } // Validate each rule. Dictionary <string, object> ruleNames = new Dictionary <string, object>(); foreach (Rule r in rules) { if (!string.IsNullOrEmpty(r.Name)) // invalid names caught when validating the rule { if (ruleNames.ContainsKey(r.Name)) { // Duplicate rule name found. ValidationError error = new ValidationError(Messages.Error_DuplicateRuleName, ErrorNumbers.Error_DuplicateConditions); error.UserData[RuleUserDataKeys.ErrorObject] = r; validation.AddError(error); } else { ruleNames.Add(r.Name, null); } } r.Validate(validation); } if (validation.Errors == null || validation.Errors.Count == 0) { return(true); } return(false); }
public override bool Validate(RuleValidation validator) { if (validator == null) { throw new ArgumentNullException("validator"); } bool success = true; if (path == null) { ValidationError error = new ValidationError(Messages.NullUpdate, ErrorNumbers.Error_ParameterNotSet); error.UserData[RuleUserDataKeys.ErrorObject] = this; validator.AddError(error); success = false; } // now make sure that the path is valid string[] parts = path.Split('/'); if (parts[0] == "this") { Type currentType = validator.ThisType; for (int i = 1; i < parts.Length; ++i) { if (parts[i] == "*") { if (i < parts.Length - 1) { // The "*" occurred in the middle of the path, which is a no-no. ValidationError error = new ValidationError(Messages.InvalidWildCardInPathQualifier, ErrorNumbers.Error_InvalidWildCardInPathQualifier); error.UserData[RuleUserDataKeys.ErrorObject] = this; validator.AddError(error); success = false; break; } else { // It occurred at the end, which is okay. break; } } else if (string.IsNullOrEmpty(parts[i]) && i == parts.Length - 1) { // It's okay to end with a "/". break; } while (currentType.IsArray) { currentType = currentType.GetElementType(); } BindingFlags bindingFlags = BindingFlags.Public | BindingFlags.Instance | BindingFlags.Static | BindingFlags.FlattenHierarchy; if (validator.AllowInternalMembers(currentType)) { bindingFlags |= BindingFlags.NonPublic; } FieldInfo field = currentType.GetField(parts[i], bindingFlags); if (field != null) { currentType = field.FieldType; } else { PropertyInfo property = currentType.GetProperty(parts[i], bindingFlags); if (property != null) { currentType = property.PropertyType; } else { string message = string.Format(CultureInfo.CurrentCulture, Messages.UpdateUnknownFieldOrProperty, parts[i]); ValidationError error = new ValidationError(message, ErrorNumbers.Error_InvalidUpdate); error.UserData[RuleUserDataKeys.ErrorObject] = this; validator.AddError(error); success = false; break; } } } } else { ValidationError error = new ValidationError(Messages.UpdateNotThis, ErrorNumbers.Error_InvalidUpdate); error.UserData[RuleUserDataKeys.ErrorObject] = this; validator.AddError(error); success = false; } return(success); }
internal override bool Validate(RuleValidation validation, MemberInfo member, Type contextType, ParameterInfo[] parameters) { ValidationError error = null; string message = null; if (string.IsNullOrEmpty(attributePath)) { // It is allowed to pass null or the empty string to [RuleRead] or [RuleWrite]. This // is how you indicate that a method or property has no dependencies or side effects. return(true); } bool valid = true; string[] parts = attributePath.Split('/'); // Check the first part. string firstPart = parts[0]; int startOfRelativePortion = 0; if (attributeTarget == RuleAttributeTarget.This) { // When target is "This", the path is allowed to start with the token "this". It is // then skipped for the rest of the validation, and the contextType remains what it // was when passed in. if (firstPart == "this") { ++startOfRelativePortion; } } else { // When target is "Parameter", the path must start with the name of a parameter. bool found = false; for (int p = 0; p < parameters.Length; ++p) { ParameterInfo param = parameters[p]; if (param.Name == firstPart) { found = true; // The context type is the parameter type. contextType = param.ParameterType; break; } } if (!found) { message = string.Format(CultureInfo.CurrentCulture, Messages.InvalidRuleAttributeParameter, firstPart, member.Name); error = new ValidationError(message, ErrorNumbers.Error_InvalidRuleAttributeParameter); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); return(false); } ++startOfRelativePortion; } int numParts = parts.Length; // Check the last part. The last part is allowed to be empty, or "*". string lastPart = parts[numParts - 1]; if (string.IsNullOrEmpty(lastPart) || lastPart == "*") { numParts -= 1; } // Check the rest of the parts. Type currentType = contextType; for (int i = startOfRelativePortion; i < numParts; ++i) { // Can't have embedded "*" wildcards. if (parts[i] == "*") { // The "*" occurred in the middle of the path, which is a no-no. error = new ValidationError(Messages.InvalidWildCardInPathQualifier, ErrorNumbers.Error_InvalidWildCardInPathQualifier); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); valid = false; break; } // Skip array types. while (currentType.IsArray) { currentType = currentType.GetElementType(); } // Make sure the member exists in the current type. BindingFlags bindingFlags = BindingFlags.Public | BindingFlags.Instance | BindingFlags.Static | BindingFlags.FlattenHierarchy; if (validation.AllowInternalMembers(currentType)) { bindingFlags |= BindingFlags.NonPublic; } FieldInfo field = currentType.GetField(parts[i], bindingFlags); if (field != null) { currentType = field.FieldType; } else { PropertyInfo property = currentType.GetProperty(parts[i], bindingFlags); if (property != null) { currentType = property.PropertyType; } else { message = string.Format(CultureInfo.CurrentCulture, Messages.UpdateUnknownFieldOrProperty, parts[i]); error = new ValidationError(message, ErrorNumbers.Error_UnknownFieldOrProperty); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); valid = false; break; } } } return(valid); }
private bool ValidateInvokeAttribute(RuleValidation validation, MemberInfo member, Type contextType, Stack <MemberInfo> methodStack) { string message; ValidationError error; if (string.IsNullOrEmpty(methodInvoked)) { // Invoked method or property name was null or empty. message = string.Format(CultureInfo.CurrentCulture, Messages.AttributeMethodNotFound, member.Name, this.GetType().Name, Messages.NullValue); error = new ValidationError(message, ErrorNumbers.Warning_RuleAttributeNoMatch, true); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); return(false); } bool valid = true; // Go through all the methods and properties on the target context, // looking for all the ones that match the name on the attribute. MemberInfo[] members = contextType.GetMember(methodInvoked, MemberTypes.Method | MemberTypes.Property, BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.FlattenHierarchy); if (members == null || members.Length == 0) { // Invoked method or property didn't exist. message = string.Format(CultureInfo.CurrentCulture, Messages.AttributeMethodNotFound, member.Name, this.GetType().Name, methodInvoked); error = new ValidationError(message, ErrorNumbers.Warning_RuleAttributeNoMatch, true); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); valid = false; } else { for (int i = 0; i < members.Length; ++i) { MemberInfo mi = members[i]; if (!methodStack.Contains(mi)) // Prevent recursion { methodStack.Push(mi); object[] attrs = mi.GetCustomAttributes(typeof(RuleAttribute), true); if (attrs != null && attrs.Length != 0) { foreach (RuleAttribute invokedRuleAttr in attrs) { if (invokedRuleAttr is RuleReadWriteAttribute readWriteAttr) { // This read/write attribute may not specify a target of "Parameter", since // we can't map from the invoker's parameters to the invokee's parameters. if (readWriteAttr.Target == RuleAttributeTarget.Parameter) { message = string.Format(CultureInfo.CurrentCulture, Messages.InvokeAttrRefersToParameterAttribute, mi.Name); error = new ValidationError(message, ErrorNumbers.Error_InvokeAttrRefersToParameterAttribute, true); error.UserData[RuleUserDataKeys.ErrorObject] = this; validation.AddError(error); valid = false; } else { // Validate the read/write attribute normally. readWriteAttr.Validate(validation, mi, contextType, null); } } else { RuleInvokeAttribute invokeAttr = (RuleInvokeAttribute)invokedRuleAttr; invokeAttr.ValidateInvokeAttribute(validation, mi, contextType, methodStack); } } } methodStack.Pop(); } } } return(valid); }