java 稍微从 POJO 生成 Json Schema
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/27863689/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Generate Json Schema from POJO with a twist
提问by StormeHawke
What I have:
我有的:
I'm generating a JSON schema from a pojo. My code to generate the schema looks like so:
我正在从 pojo 生成一个 JSON 模式。我生成架构的代码如下所示:
ObjectMapper mapper = new ObjectMapper();
TitleSchemaFactoryWrapper visitor = new TitleSchemaFactoryWrapper();
mapper.acceptJsonFormatVisitor(clazz, visitor);
JsonSchema schema = visitor.finalSchema();
schemas.put(clazz, mapper.writerWithDefaultPrettyPrinter().writeValueAsString(schema));
I'm generating several schemas via the above code. One of the pojos has an internal embedded enum to limit the possible values, like so:
我通过上面的代码生成了几个模式。其中一个 pojo 有一个内部嵌入式枚举来限制可能的值,如下所示:
public class MyClass {
@JsonProperty("name")
private String name;
@JsonProperty("startDayOfWeek")
private MyClass.StartDayOfWeek startDayOfWeek;
/**
* The ID of a timezone returned by the timezones route.
*
*/
@JsonProperty("timezone")
private String timezone;
@JsonIgnore
private Map<String, Object> additionalProperties = new HashMap<String, Object>();
/**
*
* @return
* The startDayOfWeek
*/
@JsonProperty("startDayOfWeek")
public MyClass.StartDayOfWeek getStartDayOfWeek() {
return startDayOfWeek;
}
/**
*
* @param startDayOfWeek
* The startDayOfWeek
*/
@JsonProperty("startDayOfWeek")
public void setStartDayOfWeek(MyClass.StartDayOfWeek startDayOfWeek) {
this.startDayOfWeek = startDayOfWeek;
}
public static enum StartDayOfWeek {
MONDAY("Monday"),
TUESDAY("Tuesday"),
WEDNESDAY("Wednesday"),
THURSDAY("Thursday"),
FRIDAY("Friday"),
SATURDAY("Saturday"),
SUNDAY("Sunday");
private final String value;
private static Map<String, MyClass.StartDayOfWeek> constants = new HashMap<String, MyClass.StartDayOfWeek>();
static {
for (MyClass.StartDayOfWeek c: values()) {
constants.put(c.value, c);
}
}
private StartDayOfWeek(String value) {
this.value = value;
}
@JsonValue
@Override
public String toString() {
return this.value;
}
@JsonCreator
public static MyClass.StartDayOfWeek fromValue(String value) {
MyClass.StartDayOfWeek constant = constants.get(value);
if (constant == null) {
throw new IllegalArgumentException(value);
} else {
return constant;
}
}
}
}
The above code should limit the possible String values in the JSON data that's passed around to "Monday", "Tuesday", "Wednesday", etc.
上面的代码应该限制传递给“星期一”、“星期二”、“星期三”等的 JSON 数据中可能的字符串值。
When I run the schema generator on the code in question, I expect to get something like the following schema:
当我在有问题的代码上运行模式生成器时,我希望得到类似于以下模式的内容:
{
"type" : "object",
"javaType" : "my.package.MyClass",
"properties": {
"startDayOfWeek" : {
"type" : "string",
"enum" : [ "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday" ]
}
}
}
but instead I'm getting this:
但相反,我得到了这个:
{
"type" : "object",
"id" : "urn:jsonschema:my:package:MyClass",
"title" : "Lmy/package/MyClass;",
"properties" : {
"startDayOfWeek" : {
"type" : "string"
}
}
}
I've done some digging in the Hymanson Schema Module source code and figured out that what's happening is Hymanson's using ".toString()" as the default serialization method for enum types, but what I need it to do instead is create the line that looks like this based on StartDayOfWeek.values()
:
我已经对 Hymanson Schema Module 源代码进行了一些挖掘,并发现发生的事情是 Hymanson 使用“.toString()”作为枚举类型的默认序列化方法,但我需要它做的是创建一行看起来像这样基于StartDayOfWeek.values()
:
"enum" : [ "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday" ]
Does anyone know how to do that?
有谁知道这是怎么做到的吗?
采纳答案by James Oravec
Storme's answer references org.codehaus
, which is an older version of Hymanson. The following is similar but uses fasterxml (newer version).
Storme 的答案参考org.codehaus
,这是 Hymanson 的旧版本。以下内容类似,但使用了fasterxml(较新版本)。
Pom:
波姆:
<dependency>
<groupId>com.fasterxml.Hymanson.core</groupId>
<artifactId>Hymanson-core</artifactId>
<version>2.7.1</version>
</dependency>
<dependency>
<groupId>com.fasterxml.Hymanson.core</groupId>
<artifactId>Hymanson-databind</artifactId>
<version>2.7.1</version>
</dependency>
<dependency>
<groupId>com.fasterxml.Hymanson.core</groupId>
<artifactId>Hymanson-annotations</artifactId>
<version>2.7.1</version>
</dependency>
<dependency>
<groupId>com.fasterxml.Hymanson.module</groupId>
<artifactId>Hymanson-module-jsonSchema</artifactId>
<version>2.1.0</version>
</dependency>
Code:
代码:
import ...TargetClass;
import com.fasterxml.Hymanson.databind.ObjectMapper;
import com.fasterxml.Hymanson.databind.SerializationFeature;
import com.fasterxml.Hymanson.databind.jsonschema.JsonSchema;
import java.io.IOException;
public final class JsonSchemaGenerator {
private JsonSchemaGenerator() { };
public static void main(String[] args) throws IOException {
System.out.println(JsonSchemaGenerator.getJsonSchema(TargetClass.class));
}
public static String getJsonSchema(Class clazz) throws IOException {
ObjectMapper mapper = new ObjectMapper();
mapper.configure(SerializationFeature.WRITE_ENUMS_USING_TO_STRING, true);
JsonSchema schema = mapper.generateJsonSchema(clazz);
return mapper.writerWithDefaultPrettyPrinter().writeValueAsString(schema);
}
}
回答by StormeHawke
It seems to not be possible using the instructions I found using databind. However I found another Hymanson module that seems to do the trick nicely. Oddly several of the objects are named the same.
使用我使用数据绑定找到的说明似乎无法使用。但是我发现了另一个 Hymanson 模块,它似乎很好地解决了这个问题。奇怪的是,有几个对象的名称相同。
TLDR: use objects from the org.codehaus.Hymanson.map
package rather than the com.fasterxml.Hymanson.databind
package. If you're following the instructions on thispage then you're doing it wrong. Just use the Hymanson-mapper module instead.
TLDR:使用org.codehaus.Hymanson.map
包中的对象而不是com.fasterxml.Hymanson.databind
包中的对象。如果您按照此页面上的说明进行操作,那么您就做错了。只需使用 Hymanson-mapper 模块即可。
Here's the code for future googlers:
这是未来谷歌员工的代码:
private static String getJsonSchema(Class clazz) throws IOException {
org.codehaus.Hymanson.map.ObjectMapper mapper = new ObjectMapper();
//There are other configuration options you can set. This is the one I needed.
mapper.configure(SerializationConfig.Feature.WRITE_ENUMS_USING_TO_STRING, true);
JsonSchema schema = mapper.generateJsonSchema(clazz);
return mapper.writerWithDefaultPrettyPrinter().writeValueAsString(schema);
}
回答by rufreakde
If someone comes here and wants to support the newest draft version in his code.
如果有人来到这里并希望在他的代码中支持最新的草稿版本。
Look here for your preferred language: https://json-schema.org/implementations.html
在此处查看您的首选语言:https: //json-schema.org/implementations.html