You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

能否让@Min校验注解message中的${id}获取Person类的id字段值?

Can @Min's message reference another field's value in the same bean?

Great question! Unfortunately, standard JSR-380 (Bean Validation) annotations like @Min don't support directly referencing other fields of the same object in their message attribute using ${id} out of the box. The EL expressions available in default validation messages only have access to a limited set of context variables (like ${validatedValue} for the current field's value, or ${value} for the annotation's parameter), not other properties of the bean being validated.

But don't worry—there are two solid workarounds to achieve what you want:


1. Create a custom field-level validator

This approach gives you full control over the validation logic and error message customization. Here's how to implement it:

Step 1: Define the custom validation annotation

import javax.validation.Constraint;
import javax.validation.Payload;
import java.lang.annotation.*;

@Target({ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = AgeValidator.class)
public @interface ValidAge {
    String message() default "Age of person id '{id}' must be greater than 0.";
    Class<?>[] groups() default {};
    Class<? extends Payload>[] payload() default {};
}

Step 2: Implement the validator logic

import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;

public class AgeValidator implements ConstraintValidator<ValidAge, Integer> {
    @Override
    public boolean isValid(Integer age, ConstraintValidatorContext context) {
        if (age == null || age <= 0) {
            // Access the root bean (your Person instance)
            Object rootBean = context.getRootBean();
            if (rootBean instanceof Person) {
                Person person = (Person) rootBean;
                // Replace the {id} placeholder with the actual id value
                String originalMessage = context.getDefaultConstraintMessageTemplate();
                String customizedMessage = originalMessage.replace(
                    "{id}", 
                    person.getId() != null ? person.getId() : "unknown"
                );
                
                // Disable the default message and add our customized one
                context.disableDefaultConstraintViolation();
                context.buildConstraintViolationWithTemplate(customizedMessage)
                       .addConstraintViolation();
            }
            return false;
        }
        return true;
    }
}

Step 3: Update your Person class

public class Person {
    private String id;

    @ValidAge
    private int age;

    // Don't forget to add getters (the validator needs access to id)
    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
}

2. Use Hibernate Validator's @ScriptAssert (class-level validation)

If you're using Hibernate Validator (the most common Bean Validation implementation), you can use the @ScriptAssert annotation to add class-level validation. This lets you reference other fields via the _this variable in the message:

import org.hibernate.validator.constraints.ScriptAssert;

@ScriptAssert(
    lang = "javascript",
    script = "_this.age > 0",
    message = "Age of person id '{_this.id}' must be greater than 0."
)
public class Person {
    private String id;
    private int age;

    // Getters and setters are required here too
    public String getId() { return id; }
    public void setId(String id) { this.id = id; }
    public int getAge() { return age; }
    public void setAge(int age) { this.age = age; }
}

Note that @ScriptAssert is a Hibernate-specific extension, so it won't work with other Bean Validation implementations.


Key Notes

  • Make sure your bean has getters for the fields you want to reference—validators need access to those values.
  • Handle null values gracefully (like we did with "unknown" if id is null) to avoid NullPointerExceptions.

内容的提问来源于stack exchange,提问作者Anna

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 08:28:14