【问题标题】:How to replace Swagger's enum with a link to a resource?如何用资源链接替换 ​​Swagger 的枚举?
【发布时间】:2016-06-01 12:50:00
【问题描述】:

我从the documentation 知道我可以像这样注释我的 POJO:

@ApiModelProperty(value = "pet status in the store", allowableValues = "available,pending,sold")
public String getStatus() {
    return status;
  }

产生类似的东西:

"properties": {
        ...,
        "status": {
          "type": "string",
          "description": "pet status in the store",
          "enum": [
            "available",
            "pending",
            "sold"
          ]
        }
      }

现在实现该方法的图像:

@ApiModelProperty(value = "pets in the store")
public Set<String> getPets() {
    return pets;
  }

返回商店中可用的宠物列表。例如,有一天它可能是["cats", "dogs", "songbirds"],然后当鸣禽售罄时就只是["cats", "dogs"]

我的 API 实际上会有一个端点来获取宠物列表:

http://petShop.foo/pets

而不是使用allowableValues = "cats, dogs, songbirds", 我想用 Swagger 注释指定 该字段必须包含给定端点返回的值。也就是说,类似于:

@ApiModelProperty(value = "pets in the store", allowableValues = "/pets")
public Set<String> getPets() {...}

这是为了让我的客户端/前端知道在发出请求时可以使用哪些值, 例如,在线购买宠物。如果我有"enum": ["cats", "dogs", ..],我该怎么办

【问题讨论】:

    标签: java rest swagger dropwizard jsonschema


    【解决方案1】:

    您可以执行以下操作:

    • 分叉Swagger
    • io.swagger.util.ParameterProcessor 类中扩展方法processAllowedValues 以使用除逗号分隔值之外的枚举类。 (目前只支持逗号分隔的值和范围)
    • 在构建 Web 应用程序时使用自定义的 Swagger 变体

    但是,使用这种方法,您需要继续维护您的 Swagger 分支。

    【讨论】:

    • 这并没有解决我的问题,但是 +1 的努力。看起来 Swagger 目前不支持我需要的东西。分叉 Swagger 将是一个解决方案,具有您解释的缺点。
    • @Niccolò 你的不是“问题”,而是“功能问题”:D
    • 这是真的!当我写这个问题时,我仍然认为我可能错过了文档中的某些内容。
    【解决方案2】:

    Java 注释是句法元数据。它在编译期间得到处理,并且(如果上面指定了 @Retention(RetentionPolicy.RUNTIME))在运行时可用于 reflective 访问。因此,在运行时没有直接的解决或设置方法!

    但是,Java 中有一种方法可以完成您想要的 - 但它有点太复杂了(并且使用了一些未记录的功能!)。方法如下:

    • 创建一个自定义注解 ApiModelProperty(一个带有@Retention(RetentionPolicy.COMPILE)) - 这将充当@ApiModelProperty 的包装器
    • 为上面的注解写一个注解处理器类(它必须从javax.annotation.processing.AbstractProcessor类扩展)
    • 在您的注释处理器中,inject @ApiModelProperty 使用从您的 Enum 读取的值(这部分相当复杂,因为您需要遍历 Enum 的 AST 以获取允许的值)

    Project Lombok 就是一个很好的例子。它操纵 Java 的 抽象语法树 以在 Java 中添加新功能。

    it's source codelombok.javac.handlers下,看看:

    • HandleConstructor.addConstructorProperties 方法了解如何在编译时添加注释。 (使用com.sun.tools.javac.tree.JCAnnotation
    • HandleVal.visitLocal 方法来了解如何读取 literal 值。

    你也可以看看这个教程:Creating Custom Transformations

    【讨论】:

    • 我不需要在运行时解析注释:我希望 Swagger 读取包含端点地址的注释,客户端可以从中检索字段的可能值。如果我理解正确,您的方法是尝试在运行时生成枚举列表。虽然很有趣,但这并不是我所需要的(1- 至少与实现新的 swagger 注释一样复杂 2- swagger.json 模式的静态版本呢?)。
    • @Niccolò “如果我理解正确,您的方法是尝试在运行时生成枚举列表”。我建议的方法在编译时生成allowedValues,而不是运行时。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-10-02
    相关资源
    最近更新 更多