2

我正在使用 aurelia-validate 并且如果我使用变量,我的验证工作正常,但我需要它来验证对象的属性而不是变量:

这是有效的:

  import {Validation} from 'aurelia-validation';
  import {ensure} from 'aurelia-validation';
  import {ItemService} from './service';

  export class EditItem {
    static inject() {
      return [Validation, ItemService];
    }

    @ensure(function(it){
      it.isNotEmpty()
        .hasLengthBetween(3,10);
    })
      name = '';

    @ensure(function(it){
      it.isNotEmpty()
        .hasMinLength(10)
        .matches(/^https?:\/\/.{3,}$/) //looks like a url
        .matches(/^\S*$/); //no spaces
    })
      url = '';

    constructor(validation, service) {
      this.validation = validation.on(this);
      this.service = service;
    }

    activate(params){
      return this.service.getItem(params.id).then(res => {
        console.log(res);
        this.name = res.content.name; //populate
        this.url = res.content.url;
      });
    }

    update() {
      this.validation.validate().then(
        () => {
          var data = {
            name: this.name,
            url: this.url
          };

          this.service.updateItem(data).then(res => {
            this.message = "Thank you!";
          })
        }
      );
    }
  }

这就是我正在尝试做的事情(但不起作用)......我也不确定是否最好将属性保留在类上或有一个this.item包含属性的名为的属性(这是典型的角度方式):

  import {Validation} from 'aurelia-validation';
  import {ensure} from 'aurelia-validation';
  import {ItemService} from './service';

  export class EditItem {
    static inject() {
      return [Validation, ItemService];
    }

    @ensure(function(it){
      it.isNotEmpty()
        .hasLengthBetween(3,10);
    })
      this.item.name; //no assignment here should happen 

    @ensure(function(it){
      it.isNotEmpty()
        .hasMinLength(10)
        .matches(/^https?:\/\/.{3,}$/) //looks like a url
        .matches(/^\S*$/); //no spaces
    })
      this.item.url; //no assignment?

    constructor(validation, service) {
      this.validation = validation.on(this);
      this.service = service;
      this.item = null;
    }

    activate(params){
      return this.service.getItem(params.id).then(res => {
        console.log(res);
        this.item = res.content; //populate with object from api call
      });
    }

    update() {
      this.validation.validate().then(
        () => {
          var data = {
            name: this.item.name,
            url: this.item.url
          };

          this.service.updateItem(data).then(res => {
            this.message = "Thank you!";
          })
        }
      );
    }
  }

有人可以在这里给我一些关于如何对现有对象(用于编辑页面)使用验证器的指导吗?

4

2 回答 2

4

验证适用于各种情况,但使用 @ensure 装饰器只能用于声明简单属性的规则(就像你发现的那样)。

因此...

选项 a:用 fluent API 'ensure' 方法替换 ensure 装饰器,这支持 'nested' 或 'complex' 绑定路径,例如:

import {Validation} from 'aurelia-validation';
import {ItemService} from './service';

export class EditItem {
static inject() {
  return [Validation, ItemService];
}

constructor(validation, service) {
  this.validation = validation.on(this)
    .ensure('item.url')
      .isNotEmpty()
      .hasMinLength(10)
      .matches(/^https?:\/\/.{3,}$/) //looks like a url
      .matches(/^\S*$/)
    .ensure('item.name')
      .isNotEmpty()
      .hasLengthBetween(3,10);
  this.service = service;
  this.item = null;
}

activate(params){
  return this.service.getItem(params.id).then(res => {
    console.log(res);
    this.item = res.content; //populate with object from api call
  });
}

update() {
  this.validation.validate().then(
    () => {
      var data = {
        name: this.item.name,
        url: this.item.url
      };

      this.service.updateItem(data).then(res => {
        this.message = "Thank you!";
      })
    }
  );
}

}

注意:您甚至可以在设置项目之前设置验证。酷,不是吗?

选项 b:由于验证规则特定于项目,因此您可以使用该类中的 @ensure 装饰器将验证规则移动到项目类中。然后,您可以在检索项目后在 VM 中设置验证:this.validation = validation.on(this.item);或者,您的服务可以在将项目返回到 VM 并使其成为模型的固有部分时设置验证:item.validation = validation.on(item);

选项 a 最简单,似乎符合您的经验。选项 b 更易于维护,因为模型的验证规则将存在于模型上,而不是视图模型上。但是,如果您使用选项 b,您可能需要稍微调整您的 HTML 以确保出现验证提示

于 2015-05-29T03:30:47.730 回答
1

使用验证器的 .on 方法将规则应用于对象属性。

下面的示例在我检索到一个名为 stock 的对象后被调用,它验证数量不是空的并且只是数字。希望这可以帮助...

let stock = {
  name: 'some name'
  minimumQuantity: '1'
};

applyRules() {
  ValidationRules
    .ensure((m: EditStock) => m.minimumQuantity)
    .displayName("Minimum Quantity")
    .required()
    .withMessage(`\${$displayName} cannot be blank.`)
    .matches( /^[0-9]*$/)
    .withMessage(`\${$displayName} must be numeric only.`)       

  .on(this.stock);
}
于 2017-11-17T20:27:20.637 回答