强制使用空构造函数的前置条件

时间:2018-03-28 09:29:04

标签: java validation constructor preconditions

我有几个对象需要能够解析,其中包括球衣。这迫使我显式添加一个空构造函数,因为框架使用反射和空构造函数进行实例化。

我看到的问题是我不能强迫任何先决条件。以下面的代码为例:

public class Model {
    /**
     * 0 < value < 100
     */
    int value;

    public Model() {} //The much needed empty constructor

    public Model(int value) {
        if(value < 1 || value > 99)
            throw new IllegalArgumentException("Value must be between 1 and 99 inclusive");
        this.value = value;
    }
}

这里的值确实有前提条件,根据使用情况,将其设置为任何默认值可能没有意义(例如,如果value是必须存在于数据库中的ID)。但是,由于其他框架需要一个空构造函数,因此可以创建一个违反前提条件的Model对象,因此无效。

所以我对这通常如何解决有点好奇。有没有办法让空构造函数只为反射调用打开?或者接受它是错误的并且在其中创建一个isValid函数是否更为标准,您可以调用它以确保前置条件成立?或者可能有一个不同的验证器对象来检查其有效性(以保持模型与业务逻辑清晰)?

1 个答案:

答案 0 :(得分:3)

您遇到的情况是框架会强制您接受最初无效对象的创建。据推测,框架必须使用setter才能使对象在使用之前有效。您可以使用Builder来确保只能创建有效对象。您的框架只知道构建器,而不是模型本身:

@Resource // or whatever your framework needs
public class ModelBuilder {
    private int value;

    public ModelBuilder() {}

    public setValue(int value) {
        if(value < 1 || value > 99)
            throw new IllegalArgumentException("Value must be between 1 and 99 inclusive");
        this.value = value;
    }

    public Model build() {
        if (value == 0)
            throw new IllegalStateException("Value must be set before building.");
        return new Model(value);
}

public class Model {
    /**
     * 0 < value < 100
     */
    private final int value;

    public Model(int value) {
        if(value < 1 || value > 99)
            throw new IllegalArgumentException("Value must be between 1 and 99 inclusive");
        this.value = value;
    }

    // Other methods...
}