using System; using System.Collections; using System.Collections.Generic; using System.Text.RegularExpressions; using log4net; using Sleis.Models; using Sleis.Utility; using Sleis.ViewModels; using Spring.Validation; using System.Text; using Spring.Expressions; using Spring.Objects; using System.Reflection; namespace Sleis.Validation.Spring { public class UniqueListValidator : BaseSimpleValidator { public string ProviderFormat { get; set; } public string MessageId { get; set; } public Dictionary Keys { get; set; } internal static ILog Log; public UniqueListValidator() { Log = LogManager.GetLogger(this.GetType()); } public override string ToString() { return ReflectionUtility.GetPublicPropertiesString(this); } public override bool Validate(object validationContext, IDictionary contextParams, IValidationErrors errors) { Log.DebugFormat("Validate({0},{1},{2})", validationContext, contextParams, errors); if (Keys == null) { throw new ArgumentNullException("Keys"); } if (base.EvaluateWhen(validationContext, contextParams)) { object objectToValidate = base.EvaluateTest(validationContext, contextParams); IEnumerable objects = objectToValidate as IEnumerable; IEnumerator enumerator = objects.GetEnumerator(); int counter = 0; List uniqKeys = new List(); while (enumerator.MoveNext()) { object candidateObject = enumerator.Current; Log.DebugFormat("Validating: {0}", candidateObject); ObjectWrapper wrapper = new ObjectWrapper(candidateObject); IValidationContextProvider contextProvider = candidateObject as IValidationContextProvider; List keyParts = new List(); //Spool all the values into a collection foreach (KeyValuePair key in Keys) { try { object keyPartValue = wrapper.GetPropertyValue(key.Key); keyParts.Add((keyPartValue == null) ? String.Empty : keyPartValue.ToString()); } catch (Exception wrapperEx) { Log.ErrorFormat("Error while getting {0} value from {1}. Exception: {2}", key.Key, wrapper.WrappedInstance, ExceptionUtility.GetDeepExceptionMessageOnly(wrapperEx)); } } string uniqKey = String.Join("-", keyParts.ToArray()); if (!String.IsNullOrEmpty(uniqKey) && uniqKeys.Contains(uniqKey)) { string outterProvider = String.Format(ProviderFormat, counter); foreach (KeyValuePair key in Keys) { string innerProvider = outterProvider + key.Value; Log.DebugFormat("List Provider: {0}", innerProvider); errors.AddError(innerProvider, new ErrorMessage(MessageId, (contextProvider == null) ? null : contextProvider.ValidationContxt)); } } else { uniqKeys.Add(uniqKey); } counter++; } } return errors.IsEmpty; } protected override bool Validate(object objectToValidate) { return Validate(objectToValidate, null, new ValidationErrors()); } } }