10

У меня есть модель с аннотациями данных, и я динамически привязываю, что с viewmodel с использованием привязки шаблона нокаута и картографического плагина. Я пытаюсь сделать ненавязчивую проверку клиента для моей модели. Как мы можем это сделать в этом сценарии. Любая помощь/предложения?ненавязчивая проверка клиента при привязке шаблона нокаута

public class MyUser 
    { 
     [Required] 
     [StringLength(35)] 
     public string Username { get; set; } 

     [Required] 
     [StringLength(35)] 
     public string Forename { get; set; } 

     [Required] 
     [StringLength(35)] 
     public string Surname { get; set; } 
    } 

На мой взгляд, я динамически привязываю список MyUser, используя ajax.

public JsonResult TestKnockout() 
     { 
      IList<MyUser> myUserList = new List<MyUser>(); 
      myUserList.Add(new MyUser { Username = "ajohn", Surname = "surname" }); 
      myUserList.Add(new MyUser { Username = "ajohn1", Surname = "surname1" }); 

      return Json(myUserList, JsonRequestBehavior.AllowGet); 
     } 
    } 

Вид:

<form id="Userform" action='@Url.Action("Save", "Home")' data-bind="template: {name: 'UserTemplate', foreach:UserList}"> 
<input type="Submit" name="name" value="Submit" /> 
</form> 
<script id="UserTemplate" type="text/Html"> 
<input type="text" data-bind="value: Username"></input> 
<input type="text" data-bind="value: Forename"></input> 
<input type="text" data-bind="value: Surname"></input> 
</script> 
<script type="text/javascript"> 


    var viewModel = { 
     UserList: ko.observableArray(new Array()), 

     Save: function() {   
      //// reached here means validation is done. 
      alert("Save"); 
     } 
    } 
    ko.applyBindings(viewModel); 


    $.ajax({ 
     type: 'GET', 
     url: '../Home/TestKnockout', 
     contentType: "application/json", 
     success: function (data) { 
      $.each(ko.mapping.fromJS(data)(), function() { 
       viewModel.UserList.push(this); 
      }) 

      // attach the jquery unobtrusive validator 
      $.validator.unobtrusive.parse("#Userform"); 

      // bind the submit handler to unobtrusive validation. 
      $("#Userform").data("validator").settings.submitHandler = viewModel.Save; 
     }, 
     error: function (xhr, ajaxOptions, thrownError) { 
      alert(xhr.status); 
      alert(thrownError); 
     } 
    }); 

</script> 

ответ

2

Я бы с обязательным событием JQuery для этого.

Сначала добавьте свои атрибуты data-val к ​​входам, которые вы хотите проверить. (Для того, чтобы выяснить, какие атрибуты для использования данных Val, я обычно связывают формы на стороне сервера в модели и вид источника.)

 <input data-val-required="test" data-val="true" data-bind="visible: 
    $parent.userEditMode, value: FirstName" /> 

Во-вторых, добавить функцию полезности проверки --this вызывает плагин проверки JQuery используемый MVC под крышками.

function validateForm(thisForm) { 
     var val = thisForm.validate(); 
     var isValid = val.form(); 
     alert(isValid); 
     if (!isValid) { 
      thisForm.find('.input-validation-error').first().focus(); 
     } 
     return isValid; 
    } 

В-третьих, подтвердите свой запрос перед выдачей метода viewmodel. Не забудьте удалить атрибут привязки данных «щелчок» из разметки на вашей странице.

$('#..your form id...').live('submit', function (e) { 
    e.preventDefault(); 
    if(validateForm($(this))) 
     viewModel.saveUser(); 
}); 
2

Если вы используете knockoutjs и JQuery, я придумал следующий очень простой метод для ведения основной проверки.

Везде, где вы хотите, чтобы отобразить сообщение об ошибке на странице, включают в себя поверочного тег так:

<span name="validationError" style="color:Red" 
data-bind="visible: yourValidationFunction(FieldNameToValidate())"> 
* Required. 
</span> 

Очевидно, что нужно писать «yourValidationFunction», чтобы делать то, что вы хотите, чтобы это сделать. Это просто нужно вернуть true или false, true означает отображение ошибки.

Вы можете использовать jquery, чтобы предотвратить попытку пользователя, если будут отображаться ошибки проверки. Вы, вероятно, уже есть кнопка сохранения, которое запускает яваскрипта функцию, чтобы сделать некоторые Ajax или что-то, так что просто включить это в верхней части его:

if ($("[name='validationError']:visible").length > 0) { 
     alert('Please correct all errors before continuing.'); 
     return; 
    } 

Это намного проще и гибче, чем многие другие решения проверки, выполненной там. Вы можете разместить сообщение об ошибке там, где хотите, и вам не нужно изучать, как использовать некоторую библиотеку проверки.

11

ответы pilavdzice и drogon неплохие, но мы забываем основную точку.

Поскольку мы используем шаблон MVVM для разделения пользовательского интерфейса и данных (+ vm), мы не хотим выполнять проверку UI, но DAL VALIDATION. Эти два совершенно разные, jquery validate - отличный плагин, но он проверяет UI (он начинается с пользовательского интерфейса, чтобы проверить поля).

К сожалению, если ваш viewmodel становится сложным, этот плагин будет иметь некоторые проблемы, но в любом случае это путь.

Проверка подлинности UI прекрасна до тех пор, пока мы не используем шаблон MVVM, ведь для чего мы разделяем компоненты (M-V-VM)?

Надеюсь, я помог!

Спасибо!

+3

привет, я просто изучаю плагин knockoutvalidation, и я просто хочу знать, поддерживает ли он аннотации данных на стороне сервера из коробки? или нужно выполнить всю проверку на клиентской модели viewmodel. благодаря? – afr0

+0

В качестве побочного примечания - я думаю, что комментарий к первой части @pilavdzice был довольно близок к этому - он полагается на метод из ViewModel для предоставления результатов проверки данных. – ZenMaster

+0

Да, это ближе к проверке модели, но с другой стороны это решение зависит от пользовательского интерфейса, вызывающего определенную функцию, для проверки элемента модели. Это означает, что модель и ui связаны. Лучшим решением будет модель для автоматической проверки, а ui - только для проверки/отображения результатов проверки. –