Don't like ads? PRO users don't see any ads ;-)
Guest

Untitled

By: a guest on Jul 20th, 2012  |  syntax: None  |  size: 3.76 KB  |  hits: 11  |  expires: Never
download  |  raw  |  embed  |  report abuse  |  print
Text below is selected. Please press Ctrl+C to copy to your clipboard. (⌘+C on Mac)
  1. JQuery Validation: Add custom method to validate on submit
  2. var totalFileSize = 0;
  3. $("input:file").each(function () {
  4.     var file = $(this)[0].files[0];
  5.     if (file) totalFileSize += file.size;
  6. });
  7.  
  8. return totalFileSize < maxFileSize; // I've set maxFileSize elsewhere.
  9.        
  10. public class MyViewModel
  11. {
  12.     [MaxFileSize(2 * 1024 * 1024, ErrorMessage = "The total file size should not exceed {0} bytes")]
  13.     public IEnumerable<HttpPostedFileBase> Files { get; set; }
  14. }
  15.        
  16. public class MaxFileSizeAttribute : ValidationAttribute, IClientValidatable
  17. {
  18.     public MaxFileSizeAttribute(int maxTotalSize)
  19.     {
  20.         MaxTotalSize = maxTotalSize;
  21.     }
  22.  
  23.     public int MaxTotalSize { get; private set; }
  24.  
  25.     public override bool IsValid(object value)
  26.     {
  27.         var files = value as IEnumerable<HttpPostedFileBase>;
  28.         if (files != null)
  29.         {
  30.             var totalSize = files.Where(x => x != null).Sum(x => x.ContentLength);
  31.             return totalSize < MaxTotalSize;
  32.         }
  33.  
  34.         return true;
  35.     }
  36.  
  37.     public override string FormatErrorMessage(string name)
  38.     {
  39.         return base.FormatErrorMessage(MaxTotalSize.ToString());
  40.     }
  41.  
  42.     public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
  43.     {
  44.         var rule = new ModelClientValidationRule
  45.         {
  46.             ErrorMessage = FormatErrorMessage(MaxTotalSize.ToString()),
  47.             ValidationType = "maxsize"
  48.         };
  49.         rule.ValidationParameters["maxsize"] = MaxTotalSize;
  50.         yield return rule;
  51.     }
  52. }
  53.        
  54. public class HomeController : Controller
  55. {
  56.     public ActionResult Index()
  57.     {
  58.         return View(new MyViewModel());
  59.     }
  60.  
  61.     [HttpPost]
  62.     public ActionResult Index(MyViewModel model)
  63.     {
  64.         if (!ModelState.IsValid)
  65.         {
  66.             // Server side validation failed => redisplay the view so
  67.             // that the user can fix his errors
  68.             return View(model);
  69.         }
  70.  
  71.         // Server side validation passed => here we can process the
  72.         // model.Files collection and do something useful with the
  73.         // uploaded files knowing that their total size will be smaller
  74.         // than what we have defined in the custom MaxFileSize attribute
  75.         // used on the view model
  76.         // ...
  77.  
  78.         return Content("Thanks for uploading all those files");
  79.     }
  80. }
  81.        
  82. @model MyViewModel
  83.  
  84. <script src="@Url.Content("~/Scripts/jquery.validate.js")" type="text/javascript"></script>
  85. <script src="@Url.Content("~/Scripts/jquery.validate.unobtrusive.js")" type="text/javascript"></script>
  86. <script type="text/javascript">
  87.     (function ($) {
  88.         $.validator.unobtrusive.adapters.add('maxsize', ['maxsize'], function (options) {
  89.             options.rules['maxsize'] = options.params;
  90.             if (options.message) {
  91.                 options.messages['maxsize'] = options.message;
  92.             }
  93.         });
  94.  
  95.         $.validator.addMethod('maxsize', function (value, element, params) {
  96.             var maxSize = params.maxsize;
  97.             var $element = $(element);
  98.             var files = $element.closest('form').find(':file[name=' + $element.attr('name') + ']');
  99.             var totalFileSize = 0;
  100.             files.each(function () {
  101.                 var file = $(this)[0].files[0];
  102.                 if (file && file.size) {
  103.                     totalFileSize += file.size;
  104.                 }
  105.             });
  106.             return totalFileSize < maxSize;
  107.         }, '');
  108.     })(jQuery);
  109. </script>
  110.  
  111.  
  112. @Html.ValidationMessageFor(x => x.Files)
  113. @using (Html.BeginForm(null, null, FormMethod.Post, new { enctype = "multipart/form-data" }))
  114. {
  115.     <div>
  116.         @foreach (var item in Enumerable.Range(1, 3))
  117.         {
  118.             @Html.TextBoxFor(x => x.Files, new { type = "file" })
  119.         }
  120.     </div>
  121.     <button type="submit">OK</button>
  122. }