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

Spring Boot中如何为POST/PUT接口动态设置@ApiModelProperty的required属性

适配POST/PUT接口必填规则的请求体实现方案

针对POST接口要求所有字段必填、PUT仅address必填的场景,以下是几种可行方案:

方案一:基于校验分组+Swagger分组(单一类实现)

通过定义校验分组和Swagger分组,让同一个实体类在不同接口下应用不同的必填规则:

  1. 定义校验分组接口
// POST接口专属校验分组
public interface PostStudentGroup {}
// PUT接口专属校验分组
public interface PutStudentGroup {}
  1. 修改StudentCreation实体类
    给校验注解和Swagger注解指定分组,实现不同接口下的必填逻辑:
@Data
public class StudentCreation {

    // POST时必填,PUT时可选
    @NotBlank(groups = PostStudentGroup.class)
    @ApiModelProperty(
        value = "名字",
        required = true,
        groups = PostStudentGroup.class
    )
    @ApiModelProperty(
        value = "名字",
        required = false,
        groups = PutStudentGroup.class
    )
    private String firstName;

    // POST时必填,PUT时可选
    @NotBlank(groups = PostStudentGroup.class)
    @ApiModelProperty(
        value = "姓氏",
        required = true,
        groups = PostStudentGroup.class
    )
    @ApiModelProperty(
        value = "姓氏",
        required = false,
        groups = PutStudentGroup.class
    )
    private String lastName;

    // POST和PUT都必填
    @NotBlank(groups = {PostStudentGroup.class, PutStudentGroup.class})
    @ApiModelProperty(
        value = "地址",
        required = true,
        groups = {PostStudentGroup.class, PutStudentGroup.class}
    )
    private String address;
}
  1. 接口层指定分组
    用@Validated指定校验分组,同时通过Swagger的@ApiOperation指定分组匹配文档显示:
// POST创建接口
@PostMapping("/api/v1/student")
@ApiOperation(value = "创建学生", groups = PostStudentGroup.class)
public ResponseEntity<Void> createStudent(
    @Validated(PostStudentGroup.class) @RequestBody StudentCreation request
) {
    // 业务逻辑实现
    return ResponseEntity.ok().build();
}

// PUT更新接口
@PutMapping("/api/v1/student/{student_id}")
@ApiOperation(value = "更新学生", groups = PutStudentGroup.class)
public ResponseEntity<Void> updateStudent(
    @PathVariable Long student_id,
    @Validated(PutStudentGroup.class) @RequestBody StudentCreation request
) {
    // 业务逻辑实现
    return ResponseEntity.ok().build();
}

方案二:继承拆分实体类(简洁易维护)

如果觉得分组配置繁琐,可通过继承拆分公共字段与专属字段,代码直观且维护成本低:

  1. 公共父类(存放POST/PUT共享字段)
@Data
public class BaseStudentRequest {
    @NotBlank
    @ApiModelProperty(required = true)
    private String address;
}
  1. POST专属请求体
@Data
public class StudentCreation extends BaseStudentRequest {
    @NotBlank
    @ApiModelProperty(required = true)
    private String firstName;

    @NotBlank
    @ApiModelProperty(required = true)
    private String lastName;
}
  1. PUT专属请求体
@Data
public class StudentUpdate extends BaseStudentRequest {
    @ApiModelProperty(required = false)
    private String firstName;

    @ApiModelProperty(required = false)
    private String lastName;
}

接口层直接使用对应请求体类即可,无需额外配置。

方案三:手动校验+Swagger注解覆盖(不推荐)

若不想创建多类或配置分组,可在PUT接口手动校验必填字段,并用Swagger注解覆盖实体类默认配置,但该方式易遗漏规则,且文档与实体类分离,维护成本高:

@PutMapping("/api/v1/student/{student_id}")
@ApiImplicitParams({
    @ApiImplicitParam(name = "firstName", value = "名字", required = false, dataTypeClass = String.class),
    @ApiImplicitParam(name = "lastName", value = "姓氏", required = false, dataTypeClass = String.class),
    @ApiImplicitParam(name = "address", value = "地址", required = true, dataTypeClass = String.class)
})
public ResponseEntity<Void> updateStudent(
    @PathVariable Long student_id,
    @RequestBody StudentCreation request
) {
    // 手动校验address非空
    if (StringUtils.isBlank(request.getAddress())) {
        throw new IllegalArgumentException("地址不能为空");
    }
    // 业务逻辑实现
    return ResponseEntity.ok().build();
}

方案推荐

  • 追求单一实体类时优先选方案一;
  • 追求代码直观、易维护时优先选方案二,这也是多数团队的常用实践。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.11 14:35:21