如何将ko.validation错误与相关的ViewModel字段名称联系在一起 [英] How to tie together ko.validation errors with related viewmodel field names
问题描述
我正在使用Knockout.Validation,并且希望能够显示错误摘要,其中每行显示错误消息(很明显!)以及与之相关的视图模型上的字段名称,例如>
- 年龄-请输入一个数字
- 出生日期-请输入正确的日期
到目前为止,我已经包装了一个封装了视图模型的validatedObservable,这会自动在我的视图模型上放置一个error数组,其中包含我所有的错误.但是,我看不到任何简单的方法来检索每个错误所涉及的字段.
我知道我可以自己遍历视图模型,并从isValid属性建立我自己的错误集合-这是我唯一的选择吗?
一旦有了字段名称,我就可以将验证摘要映射到该字段的相关友好"标签(例如,出生日期"而不是"DateOfBirth").
这是到目前为止我拥有的代码的简化版本:
ViewModel
function PersonModel(){
var self = this;
self.Age = ko.observable().extend({ number: true});
self.DateOfBirth = ko.observable({ date: true});
self.Validate = function() {
if (!self.isValid()) {
self.errors.showAllMessages();
return false;
}
return true;
};
ko.validation.init({
grouping: { deep: true, observable: true },
registerExtenders: true,
messagesOnModified: true,
insertMessages: true
});
ko.applyBindings(ko.validatedObservable(new PersonModel()));
HTML
<ul data-bind='foreach: model().errors' class="message">
<li>
<span data-bind='text: $data'></span>
</li>
</ul>
非常感谢
您可以执行以下操作:
- 添加一个
friendlyName
扩展器,为您的观测对象提供一个友好的名称 - 缺少显示消息的绑定处理程序
好记的名字:
有史以来最简单的敲除扩展器:
ko.extenders.friendlyName = function (obs, options) {
obs.friendlyName = options;
}
用法:self.Age = ko.observable(3).extend({ friendlyName: "My Age" });
显示邮件黑客:
敲除验证插件创建绑定处理程序validationMessage
以显示错误消息.您可以直接使用它(带有一些html标记),也可以让插件使用配置选项insertMessages
处理消息.
在这里,我只是编辑它创建的html(仍然调用原始绑定处理程序)以将friendlyName
考虑在内:
var originalValidationMessageUpdate= ko.bindingHandlers.validationMessage.update;
ko.bindingHandlers.validationMessage.update =
function (element, valueAccessor, allBindingAccessor, viewModel,
bindingContext) {
if (originalValidationMessageUpdate)
originalValidationMessageUpdate(element, valueAccessor,
allBindingAccessor, viewModel,
bindingContext);
var prepend = (ko.isObservable(valueAccessor())
&& valueAccessor().friendlyName)
? valueAccessor().friendlyName + " - "
: "";
$(element).html(prepend + $(element).html());
// ^^^^ This is the line that is actually useful
}
注意:我没有将friendlyName
创建为可观察的,因为我猜它不会被更新,但是有可能做到这一点.
演示
I'm using Knockout.Validation and I'd like to be able to display an error summary where each line displays the error message (obviously!) and also the field name on the view model related to it, e.g.
- Age - please enter a number
- Date of birth - please enter a proper date
So far I've got a validatedObservable wrapping my view model, and this puts an errors array on my viewmodel automatically, containing all my errors. However I can't see any easy way to retrieve which field each error relates to.
I know I could traverse the view model myself, building up an errors collection of my own from the isValid property - is this my only option though?
Once I have the field name, I can map my validation summary to the related "friendly" label for that field (e.g. "Date of birth" rather than "DateOfBirth").
Here's a simplified version of the code I have so far:
ViewModel
function PersonModel(){
var self = this;
self.Age = ko.observable().extend({ number: true});
self.DateOfBirth = ko.observable({ date: true});
self.Validate = function() {
if (!self.isValid()) {
self.errors.showAllMessages();
return false;
}
return true;
};
ko.validation.init({
grouping: { deep: true, observable: true },
registerExtenders: true,
messagesOnModified: true,
insertMessages: true
});
ko.applyBindings(ko.validatedObservable(new PersonModel()));
Html
<ul data-bind='foreach: model().errors' class="message">
<li>
<span data-bind='text: $data'></span>
</li>
</ul>
Many Thanks
You can do the following:
- Add a
friendlyName
extender to provide a friendly name to your observables - Hack the binding handler that shows the messages
Friendly Name:
Simplest knockout extender ever:
ko.extenders.friendlyName = function (obs, options) {
obs.friendlyName = options;
}
Usage: self.Age = ko.observable(3).extend({ friendlyName: "My Age" });
Display message hack:
Knockout validation plugin creates a bindinghandler validationMessage
to display error messages. You can use it directly (with some html markup) or let the plugin handle the messages with the configuration option insertMessages
.
Here I just edit the html it creates (the original binding handler is still called) to take the friendlyName
into account:
var originalValidationMessageUpdate= ko.bindingHandlers.validationMessage.update;
ko.bindingHandlers.validationMessage.update =
function (element, valueAccessor, allBindingAccessor, viewModel,
bindingContext) {
if (originalValidationMessageUpdate)
originalValidationMessageUpdate(element, valueAccessor,
allBindingAccessor, viewModel,
bindingContext);
var prepend = (ko.isObservable(valueAccessor())
&& valueAccessor().friendlyName)
? valueAccessor().friendlyName + " - "
: "";
$(element).html(prepend + $(element).html());
// ^^^^ This is the line that is actually useful
}
Note: I did not create friendlyName
as an observable since I guess it will not be updated, but it is possible to do it.
Demo
这篇关于如何将ko.validation错误与相关的ViewModel字段名称联系在一起的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!