2013-06-03 61 views
2

我用ko.validation检查有效数据我的网页上是这样的:ko.validation与validatedObservable让我奇怪的结果

var postcode = ko.observable(), 
    name = ko.observable(); 

var validationModel = ko.validatedObservable({ 
    postcode: postcode.extend({ required: true }), 
    name: name.extend({ required: true }) 
}); 

然后在我的OK按钮提交我前检查验证:

var buttonOk = function() { 

    if (!validationModel.isValid()) { 
     validationModel.errors.showAllMessages(); 
     return false; 
    } 
    ... 

它工作得很好:如果用户没有输入邮编的内容并且名称验证失败。

现在我加入了一些更验证规则:

postcodeMustNotAlreadyExists + denominationMustNotAlreadyExists这样的:

var validationModel = ko.validatedObservable({ 
    postcode: postcode.extend({ required: true }), 
    name: name.extend({ required: true }) 
}).extend({ 
    postcodeMustNotAlreadyExists: cities, 
    denominationMustNotAlreadyExists: cities 
}); 

ko.validation.rules['postcodeMustNotAlreadyExists'] = { 
    validator: function (val, cities) { 
     // Try to find a match between the typed postcode and the postcode in the list of cities 
     var match = ko.utils.arrayFirst(cities(), function (item) { 
      return (val.postcode() === item.postCode()); 
     });    
     return !match; 
    }, 
    message: 'This postcode already exists!' 
}; 
ko.validation.rules['denominationMustNotAlreadyExists'] = { 
    validator: function (val, cities) { 
     // Try to find a match between the typed denomination and the denomination in the list of cities 
     var match = ko.utils.arrayFirst(cities(), function (item) { 
      return (val.name() === item.name()); 
     }); 
     return !match; 
    }, 
    message: 'This denomination already exists!' 
}; 
ko.validation.registerExtenders(); 

现在validationModel.isValid()回报总是如此,当用户不键入邮政编码或名称什么。我注意到validationModel().postcode.isValid()是错误的,因此这不是逻辑将validationModel.isValid()设置为True。

现在与我的新的实施一定要考2两件事:(!validationModel.isValid() || validationModel().errors().length>0)

任何想法?

谢谢。

回答

5

尝试用替代您的ViewModel里面你isValid()功能:

self.isValid = ko.computed(function() { 
     return ko.validation.group(
      self, 
      { 
       observable: true, 
       deep: true 
      }).showAllMessages(true); 
    }, self); 
+0

我不得不深入false,因为它给我一个堆栈溢出..但是这个覆盖似乎是我需要myModel.isValid()开始工作。在文档中它似乎并不需要? –

0

IsValid属性只在validationObservable在observable.subscribe处理程序,这意味着它很可能不会与.extend被重新定义重新界定,并与之前版本的ko.validation不同,即使对象发生更改也不会更新。

还有一个问题,用undefined/null初始化验证的observable,并且不传递对象 - >那么isValid定义永远不会更新以匹配新的可观察对象。

最后但并非最不重要的是,Tom Studee在他的回答中提出的选项可以并且应该在ko.validation.init(app级别)或ko.validationObservable定义级别中定义。它绝对更具可读性和可维护性。在这里,'deep:true'很可能会失败,因为在视图模型中有一个循环引用。

此外,在isValid计算上调用showAllMessages将会阻止仅在修改(ko.validation酷炫功能之一)后才显示消息,这会导致ex。通常会创建新的实体表单以完全覆盖验证消息。虽然通常你会看到它们只有不正确的值被传递或试图保存它们。总结:确保已更新ko.validation,在validationObservsable或app级别传递选项,仅在需要时调用showAllMessages。创建ko.validationObservable作为第二个构造函数参数传递空选项object {};如果不是其他选项,则重新定义isValid属性为新的ko.validation.group调用。