【问题标题】:Library for Json Schema and Validation in Java [closed]Java中用于Json模式和验证的库[关闭]
【发布时间】:2020-04-10 08:13:55
【问题描述】:

我可以看到有一些库可以生成 Json Schema 和其他可以验证的库。您能否建议一些可以在 Java 中提供这两种功能的库(带有示例和活动库)。我正在寻找 Apache 许可库。

我试过 Jackson 和 Gson。
Gson 不支持 json 模式创建和验证。
Jackson 支持 json 模式生成但不完全支持(例如它不支持 json 模式中的默认值)

问候,

【问题讨论】:

    标签: java json jsonschema json-schema-validator


    【解决方案1】:

    GSON 和 Jackson 的主要范围是处理数据与 JSON 之间的序列化/反序列化。 JSON Schema 的生成和验证都不是他们的(主要)关注点。

    根据您的其他问题 (How to display default value in JSON Schema using Jackson) 中的 cmets,有几个替代方案可用于生成模式 - 这同样适用于它们的验证。

    实现列表(生成和验证)

    根据R.Groote 的回答,您可以在https://json-schema.org/implementations.html 上找到其中的一些(但不是全部)——生成库和验证库。

    验证

    就我个人而言,到目前为止我只使用过networknt/json-schema-validator,发现它非常直观且易于使用。它在后台使用了 Jackson,这在我的用例中很实用,因为我已经使用同一个库来(反)序列化来自/到 JSON 的数据——因此减少了额外的依赖。


    一代

    免责声明:这是有偏见的部分,因为我是 victools/jsonschema-generator.

    JSON Schema 生成库的一个示例是victools/jsonschema-generator。这也在内部使用了 Jackson,因此再次与 networknt/json-schema-validator 类似的依赖关系。

    jsonschema-generator 库不会填充开箱即用的“默认”值,但您可以像这样轻松配置它(根据您的其他问题,基于 Jackson @JsonProperty 注释):

    SchemaGeneratorConfigBuilder configBuilder = new SchemaGeneratorConfigBuilder(SchemaVersion.DRAFT_2019_09, OptionPreset.PLAIN_JSON);
    configBuilder.forFields().withDefaultResolver(field -> {
        JsonProperty annotation = field.getAnnotationConsideringFieldAndGetter(JsonProperty.class);
        return annotation == null || annotation.defaultValue().isEmpty() ? null : annotation.defaultValue());
    });
    SchemaGenerator generator = new SchemaGenerator(configBuilder.build());
    JsonNode jsonSchema = generator.generateSchema(YourClass.class);
    
    System.out.println(jsonSchema.toString());
    

    如果您需要数字默认值,则可能必须包含对 @JsonProperty.defaultValue String 的一些条件解析。

    此外,如果您想要对 Jackson 注释进行更具体的处理,您还可以考虑添加可选的 victools/jsonschema-module-jackson


    编辑(作为对您必须在代码和注释中定义两次默认值的担忧的回应):

    使用victools/jsonschema-generator,您可以完全控制默认值的来源。一种可能的方法是从遇到的各个对象的实际实例中查找默认值——这里通过您自己的包过滤以跳过外部类型。
    以下只是可能的粗略示例:

    ConcurrentMap<Class<?>, Object> instanceCache = new ConcurrentHashMap<>();
    configBuilder.forFields().withDefaultResolver(field -> {
        Class<?> declaringClass = field.getDeclaringType().getErasedType();
        if (!field.isFakeContainerItemScope()
                && declaringClass.getName().startsWith("your.package")) {
            MethodScope getter = field.findGetter();
            if (getter != null) {
                try {
                    Object instance = instanceCache.computeIfAbsent(declaringClass, declaringClass::newInstance);
                    Object defaultValue = getter.getRawMember().invoke(instance);
                    return defaultValue;
                } catch (Exception ex) {
                    // most likely missing a no-args constructor
                }
            }
        }
        return null;
    });
    

    【讨论】:

    • 谢谢。能否请您也回答一下这个问题:stackoverflow.com/questions/61140930/…
    • 我看到了这个问题,但无法回答。我从未使用过 mbknor 库,但在调查现有生成器库时发现它不适合我非常具体的用例并最终编写了自己的库。
    • 我认为默认值还有一个问题。如果我使用注释 JsonProperty(defaultValue="abc")。此注释将在生成模式时受到尊重,但在通过 Jackson 将 json 反序列化为 POJO 时不会受到尊重。这意味着我必须在两个地方(注解和赋值)为每个属性指定默认值
    • 可能,是的。根据注解的 JavaDoc,注解的默认值用于文档目的。看起来你是对的。如果您在代码中遵循某些约定,您还可以从代码中查找默认值。例如。如果对于所有具有默认值的字段总是有一个无参数的构造函数和 getter,您总是可以创建一个新的对象实例并通过 getter 检索默认值。
    • 是的,但我仍然必须在多个位置指定默认值。我不确定是否可以覆盖或扩展 Jackson 反序列化过程并检查 @JsonProperty 是否与具有默认值的属性关联。
    【解决方案2】:

    我更喜欢使用 GSON 或 Jackson: - https://www.baeldung.com/jackson-vs-gson

    您可以使用 Justify 或 json-schema-validator 请参阅以下链接: - https://json-schema.org/implementations.html - Validate JSON schema compliance with Jackson against an external schema file

    希望以上链接能给你足够的信息

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-01-30
      • 2012-08-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-02-15
      • 1970-01-01
      相关资源
      最近更新 更多