2011-10-11 147 views
0

我建立了本地艺术家的在线商店,并要求之一是增加要与特定产品关联的图像。对于图像,有多个元素需要验证;特别是尺寸,文件大小和类型。验证多发性属性

目前,我有以下设置验证图像:

[LocalizedDisplayName(typeof(StoreManagementRes), "Image")] 
[ImageSize(typeof(BesLogicSharedRes),"ValidationImageFileSizeMustBeLessThan20kb")] 
[ImageDimension(typeof(BesLogicSharedRes), "ValidationImageDimensionMustBeLessThan640x480")] 
[ImageType(typeof(BesLogicSharedRes), "ValidationImageTypeMustBeJpgOrPng")] 
public int ImageFileId { get; set; } 

被上传并得到验证正确,但是,他们并不一定每次叫以相同的顺序文件的应用程序运行。最后,如果验证在多个属性上失败,则只显示一条错误消息。再次,不一定是第一次失败的验证,也不是最后一次。我想一次显示所有错误,以免挫伤用户。

如果这是相关的,所有三个图像验证类子从ValidationAttribute归类。

回答

1

有一两件事要感谢的是,该模型保存所有错误,而不是他们中的一个,它只是效果展示第一个的HtmlHelper。

的ValidationSummary其实应该显示所有的错误在你的模型虽然我怀疑你想为一个单独的属性相当。

不幸的是一对夫妇的有用的方法是私有的,而不是保护,使他们不得不复制并粘贴出来的ValidationExtensions.cs。我做了一个稍微减少的版本(没有使用错误消息的资源文件,通过获取原始版本的GetUserErrorMessageOrDefault很容易完成,但是您还必须检查是否也从类中获取相关的方法和字段) 。我也只做了一个函数调用,但如果需要的话,它很容易引起过载。

public static MvcHtmlString ValidationSummaryForSubModel(this HtmlHelper html, bool excludePropertyErrors, string message, IDictionary<string, object> htmlAttributes) 
    { 
     string prefix = html.ViewData.TemplateInfo.HtmlFieldPrefix; 
     var props = html.ViewData.ModelState.Where(x => x.Key.StartsWith(prefix)); 
     var errorprops = props.Where(x => x.Value.Errors.Any()).SelectMany(x=>x.Value.Errors); 

     if (html == null) { 
      throw new ArgumentNullException("html"); 
     } 
     FormContext formContext = (html.ViewContext.ClientValidationEnabled) ? html.ViewContext.FormContext : null; 
     if (formContext == null && html.ValidForSubModel()) 
     { 
      return null; 
     } 

     string messageSpan; 
     if (!String.IsNullOrEmpty(message)) { 
      TagBuilder spanTag = new TagBuilder("span"); 
      spanTag.SetInnerText(message); 
      messageSpan = spanTag.ToString(TagRenderMode.Normal) + Environment.NewLine; 
     } 
     else { 
      messageSpan = null; 
     } 

     StringBuilder htmlSummary = new StringBuilder(); 
     TagBuilder unorderedList = new TagBuilder("ul"); 


     foreach (ModelError modelError in errorprops) { 
      string errorText = GetUserErrorMessageOrDefault(html.ViewContext.HttpContext, modelError, null /* modelState */); 
      if (!String.IsNullOrEmpty(errorText)) { 
       TagBuilder listItem = new TagBuilder("li"); 
       listItem.SetInnerText(errorText); 
       htmlSummary.AppendLine(listItem.ToString(TagRenderMode.Normal)); 
      } 
     } 


     if (htmlSummary.Length == 0) { 
      htmlSummary.AppendLine(_hiddenListItem); 
     } 

     unorderedList.InnerHtml = htmlSummary.ToString(); 

     TagBuilder divBuilder = new TagBuilder("div"); 
     divBuilder.MergeAttributes(htmlAttributes); 
     divBuilder.AddCssClass((html.ViewData.ModelState.IsValid) ? HtmlHelper.ValidationSummaryValidCssClassName : HtmlHelper.ValidationSummaryCssClassName); 
     divBuilder.InnerHtml = messageSpan + unorderedList.ToString(TagRenderMode.Normal); 

     if (formContext != null) { 
      // client val summaries need an ID 
      divBuilder.GenerateId("validationSummary"); 
      formContext.ValidationSummaryId = divBuilder.Attributes["id"]; 
      formContext.ReplaceValidationSummary = !excludePropertyErrors; 
     } 
     return MvcHtmlString.Create(divBuilder.ToString(TagRenderMode.Normal)); 
    } 

    private static string GetUserErrorMessageOrDefault(HttpContextBase httpContext, ModelError error, ModelState modelState) 
    { 
     if (!String.IsNullOrEmpty(error.ErrorMessage)) 
     { 
      return error.ErrorMessage; 
     } 
     if (modelState == null) 
     { 
      return null; 
     } 

     string attemptedValue = (modelState.Value != null) ? modelState.Value.AttemptedValue : null; 
     //return String.Format(CultureInfo.CurrentCulture, GetInvalidPropertyValueResource(httpContext), attemptedValue); 
     return "Error"; 
    }