java - 如何手动记录 JAX-RS 参数的 Swagger 数据模型?

标签 java swagger

上下文

假设我有一个简单的 Java 数据类:

public class Person {
    private final String name;
    private final int age;

    Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    int String getAge() {
        return age;
    }
}

注意:在实践中,我使用 Immutables生成这个,但我正在显示 POJO这里是为了简单起见。

为了记录GET响应的模型,即使返回类型是Response,我也可以引用@ApiOperation中的类:

@GET
@ApiOperation(response = Person.class)
public Response getPerson() {
    return Response.ok(new Person("Julien", 28)).build();
}

基于此,Swagger 将正确记录此内容:

Model:

Person {
  name (string),
  age (number)
}

Example value:

{
  "name": "string",
  "age": 0
}

为了记录POST 主体的模型,我直接在代码中使用该类,Swagger 找到它并根据需要记录它:

@POST
@ApiOperation(response = Person.class)
public Response addPerson(Person newPerson) {
    return Response.ok(store.insert(newPerson)).build();
}

问题

我也想支持部分更新。我不能使用 POJO 本身,因为 POJO 中的所有字段都是强制性的,我依靠它来获得安全检查并在将无效的 JSON 发送到例如POST 方法。

在我的实际用例中,我的数据模型包含 map 。我希望用户能够在更新中指定某个键并将值设置为 null,以从现有 map 中删除元素。

我选择支持正文类型为普通 JsonNodePATCH 请求。这允许我的服务器接收任何 JSON,我可以根据需要应用更新。

@PATCH
@Path("/{name}")
@ApiOperation(response = Person.class)
public Response updatePerson(@PathParam("name") String name, JsonNode update) {
    return Response.ok(store.update(name, update)).build();
}

我对结果很满意,除了 Swagger 现在使用 JsonNode Java 对象的属性记录部分更新的模型:

Model:

JsonNode {
  array (boolean, optional),
  null (boolean, optional),
  number (boolean, optional),
  float (boolean, optional),
  pojo (boolean, optional),
  valueNode (boolean, optional),
  containerNode (boolean, optional),
  object (boolean, optional),
  missingNode (boolean, optional),
  nodeType (string, optional) = ['ARRAY', 'BINARY', 'BOOLEAN', 'MISSING', 'NULL', 'NUMBER', 'OBJECT', 'POJO', 'STRING'],
  integralNumber (boolean, optional),
  floatingPointNumber (boolean, optional),
  short (boolean, optional),
  int (boolean, optional),
  long (boolean, optional),
  double (boolean, optional),
  bigDecimal (boolean, optional),
  bigInteger (boolean, optional),
  textual (boolean, optional),
  boolean (boolean, optional),
  binary (boolean, optional)
}

Example value:

{
  "array": true,
  "null": true,
  "number": true,
  "float": true,
  "pojo": true,
  "valueNode": true,
  "containerNode": true,
  "object": true,
  "missingNode": true,
  "nodeType": "ARRAY",
  "integralNumber": true,
  "floatingPointNumber": true,
  "short": true,
  "int": true,
  "long": true,
  "double": true,
  "bigDecimal": true,
  "bigInteger": true,
  "textual": true,
  "boolean": true,
  "binary": true
}

我想在我的代码中指定模型类似于 Person,这样 Swagger UI 中给出的示例就更相关了。我试过@ApiImplicitParams:

@PATCH
@Path("/{name}")
@ApiOperation(response = Person.class)
@ApiImplicitParams({
  @ApiImplicitParam(name = "update", dataTypeClass = Person.class)
})
public Response updatePerson(@PathParam("name") String name, JsonNode update) {
    return Response.ok(store.update(name, update)).build();
}

这没有任何区别。 Swagger 仍然记录 JsonNode 本身。 @ApiImplicitParams 的文档提及:

While ApiParam is bound to a JAX-RS parameter, method or field, this allows you to manually define a parameter in a fine-tuned manner. This is the only way to define parameters when using Servlets or other non-JAX-RS environments.

由于我使用的是 JAX-RS,这可能意味着我不能使用 @ApiImplicitParams,但是 @ApiParam不提供任何覆盖类的内容。

如何手动指定 Swagger 自动检测到的 JAX-RS 参数的数据模型?

最佳答案

添加此答案使其更通用,以便更好地理解 @ApiImplicitParams

您必须使用 @ApiImplicitParams 来包装您希望保存在文档中的参数。 @ApiImplicitParam 有许多不那么明显的好处,比如传入额外的 header 参数而不将其添加为方法参数,或者在您的情况下包装参数以使它们有意义。

对于你的问题,你必须使用 @ApiImplicitParamparamType = "body" 因为你想在正文中进行更改,类似地 paramType = "head" 如果你想改变标题。

您还可以使用属性 required = true/false 控制 @ApiImplicitParam 中的必填字段。

如前所述,您可以传递一个参数而无需在方法参数中包含它,您可以使用属性 value = "required value" 控制它的值。

您还可以使用逗号分隔值控制 @ApiImplicitParam 中的允许值。例如,allowableValues = "no-cache, no-store"

关于java - 如何手动记录 JAX-RS 参数的 Swagger 数据模型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56397497/

相关文章:

java - FileOutputStream 删除文件内容

events - 如何在 OpenAPI/Swagger 规范中定义事件?

swagger - 在 Swagger Open API 3.0 中使用另一个参数时如何指示有条件地需要一个参数

Swagger UI 在部署时显示错误(验证)

java - 将字符串子集转换为数组变量的最佳方法是什么?

java - Java中的分数乘法器自定义方法

java.lang.IllegalArgumentException : argument type mismatch using setResultTransformer (hibernate)

amazon-web-services - 如何在云形成 yaml aws 中外部包含 swagger 文件路径

azure - 为 Azure Functions 启用 Swagger(OpenAPI 2.0 元数据)

java - 如何编写不显式创建对象的 Guice Provider?