首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >不能在具有class-validator的父类的构造函数中使用验证

不能在具有class-validator的父类的构造函数中使用验证
EN

Stack Overflow用户
提问于 2018-12-24 20:16:14
回答 1查看 2.7K关注 0票数 1

我想在对象构造函数中使用validateSync,但我不能将其用于继承。

我得到了类似这样的东西:

代码语言:javascript
运行
复制
import { IsNotEmpty, IsString, validateSync, validate } from 'class-validator';

class Animal {

    @IsNotEmpty()
    @IsString()
    public name: string;

    constructor(name: string) {
        this.name = name;
        this.validate() // this method calls validate of class Dog, since this is an instance of Dog
    }

    protected validate() {
        const errors = validateSync(this);
        if (errors.length > 0) {
            console.log("Animal validation error: ", errors)
        }
    }
}

class Dog extends Animal {

    @IsNotEmpty()
    @IsString()
    public breed: string;

    constructor(name: string, breed: string) {
        super(name);
        this.breed = breed
        this.validate()
    }

    protected validate() {
        const errors = validateSync(this);
        if (errors.length > 0) {
            console.log("Dog validation error: ", errors)
        }
    }

}

const dog = new Dog('Aaron', 'Golden Retriever')

结果是:

代码语言:javascript
运行
复制
Dog validation error:  [ ValidationError {
    target: Dog { name: 'Aaron' },
    value: undefined,
    property: 'breed',
    children: [],
    constraints:
     { isString: 'breed must be a string',
       isNotEmpty: 'breed should not be empty' } } ]

当我调用Dog构造函数时,代码先运行super(),然后运行Animal类的this.validate()。这个方法验证了Dog的一个实例,因为Animal没有breed属性,所以代码抛出了上面的错误。

我不知道如何解决这个问题,也许将验证放在构造函数中不是一个好主意。

有没有变通的方法或者更好的方法呢?

EN

回答 1

Stack Overflow用户

发布于 2018-12-24 20:55:40

出现错误的原因不是因为Animal没有breed属性(实际上它有,因为实例实际上是Dog),而是因为您在设置所有要验证的值之前调用了验证(其中之一)。另一件事是,你做了两次验证,这听起来不太对。

代码语言:javascript
运行
复制
class Dog extends Animal {
    constructor(name: string, breed: string) {
        super(name); // <-- validation gets called in the parent but you did't set the breed property yet
        this.breed = breed; 
        this.validate(); // <-- validation gets called for the second time, but this time it passes
    }
}

由于super()必须是构造函数中的第一个语句,因此您无法在当前模式中避免这一点。

解决方案之一是避免在基类中调用validate(),让子类正确设置所有字段,然后才进行验证。

我不认为在构造函数中验证必需的属性有任何错误,因为您正在阻止创建具有无效状态的对象。但是,如果在创建对象时不一定要拥有所有的值,我建议让调用者决定何时进行验证:

代码语言:javascript
运行
复制
const dog = new Dog('Aaron');
// do some stuff like determine the breed...
dog.breed = 'Golden Retriever';
// do some more stuff
const validationResult = dog.validate(); // did I succeed?

另请注意,您似乎不需要在父类和子类中声明完全相同的方法validate()

票数 4
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/53913344

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档