Java 带有URL的jsonschema2pojo不';t工作
我在代码中使用jsonschema2pojo时遇到问题。 因此,我使用jsonschema2pojo生成器()从以下URL生成POJO: 最后,我在一个包“model”中创建所有这些类。 然后在中,我尝试使用它从链接读取json,但收到异常:Java 带有URL的jsonschema2pojo不';t工作,java,json,jsonschema2pojo,Java,Json,Jsonschema2pojo,我在代码中使用jsonschema2pojo时遇到问题。 因此,我使用jsonschema2pojo生成器()从以下URL生成POJO: 最后,我在一个包“model”中创建所有这些类。 然后在中,我尝试使用它从链接读取json,但收到异常: Exception in thread "main" java.lang.NullPointerException at controller.View.main(View.java:26) 我不明白为什么。 下面是我如何做到这一点的代码: pu
Exception in thread "main" java.lang.NullPointerException
at controller.View.main(View.java:26)
我不明白为什么。
下面是我如何做到这一点的代码:
public class View {
private static String urlStr = "http://store.steampowered.com/api/appdetails/?appids=10";
public static void main(String[] args) {
ObjectMapper objectMapper = new ObjectMapper();
try {
Game game = objectMapper.readValue(new URL(urlStr), Game.class);
System.out.println(game.getData().getName());
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (JsonParseException e) {
e.printStackTrace();
} catch (JsonMappingException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
class是我在生成器中设置为“类名”的最终类
怎么了?如何从该链接获取所有这些数据
在maven中,我将其配置为:
<plugin>
<groupId>org.jsonschema2pojo</groupId>
<artifactId>jsonschema2pojo-maven-plugin</artifactId>
<version>0.4.18</version>
<configuration>
<sourceType>jsonschema</sourceType>
<outputEncoding>${project.build.sourceEncoding}</outputEncoding>
<outputDirectory>${project.build.directory}/generated-sources</outputDirectory>
<annotationStyle>jackson2</annotationStyle>
<generateBuilders>true</generateBuilders>
<initializeCollections>true</initializeCollections>
</configuration>
<executions>
<execution>
<id>generate-game</id>
<goals>
<goal>generate</goal>
</goals>
<configuration>
<targetPackage>model.game</targetPackage>
<sourceDirectory>${basedir}/src/main/resources/schema/game</sourceDirectory>
</configuration>
</execution>
</executions>
</plugin>
使用此配置,我可以使用此行而不是System.out.println之前读取所有数据:
System.out.println( objectMapper.writeValueAsString( game ) );
现在我可以看到完整的json字符串,但如何使用“game.getData().getName()”等来读取它?您给出的json模式将“10”定义为包含所有其他内容的顶级属性
{
"type": "object",
"required":false,
"javaType":"model.Game",
"properties": {
"10": {
"id": "10",
"type": "object",
"properties": {
"success": {
"id": "success",
"type": "boolean"
},
"data": {
"id": "data",
"type": "object",
"properties": {
"type": {
"id": "type",
"type": "string"
},
"name": {
"id": "name",
"type": "string"
},
...
jsonschema2pojo读取该模式并生成名为\u 10
的类作为模型的一部分。您可以在生成的sources目录中的_10.java中找到它
@JsonInclude(JsonInclude.Include.NON_NULL)
@Generated("org.jsonschema2pojo")
@JsonPropertyOrder({
"success",
"data"
})
public class _10 {
我不知道这在模式中是否是故意的。如果是故意的,那么您需要像这样访问名称
System.out.println(game.get10().getData().getName());
在做了那个改变之后,我能够让它工作
编辑:看来这些JSON消息应该有一个变量ID作为包含所有其他内容的顶级键,所以我们需要稍微不同地处理它。我们可以概括模式,使其不特定于特定的ID,然后我们可以使用两步过程来解析消息。首先,我们将使用[ObjectMapper#readValue
](com.fasterxml.jackson.core.type.TypeReference))将整个消息解析为映射。我们希望顶级映射将包含一个元素,对应于我们请求的文档的ID,其值将是包含我们感兴趣的值的子映射。然后,我们将通过[ObjectMapper#convertValue
](,java.lang.Class))传递该子映射,以获得所需的Game
对象
pom.xml
此外,我还需要对模式进行另一个更改。我删除了linux\u要求
属性。这是因为查看文档10和文档219,前者是一个对象,后者是一个数组。对于文档219,解析器不知道如何理解数组,因为我们需要一个对象。从API返回的数据像这样不一致是很奇怪的。您可能需要对模式进行更多的修改,以使其完全适用于从该API返回的所有可能的JSON文档
我已经把所有的代码放进了一个。您可以获取该代码,构建并运行它,以查看其工作情况。然后,您可以进一步调整它以满足您的需要。使用附加属性
而不是尝试使用属性对包含ID的对象建模。假设顶级类型包含多个游戏,您可以尝试替换
{
"type": "object",
"required":false,
"javaType":"model.Game",
"properties": {
"10": {
"id": "10",
"type": "object",
...
}
}
}
有点像
{
"type": "object",
"required":false,
"javaType":"model.Games",
"additionalProperties": {
"id": "game",
"type": "object",
"javaType": "model.Game"
...
}
}
这应该是一个模型。游戏
使用类似public Map getAdditionalProperties()
的方法键入,但是如果这个类也适用于ID=219,您是否尝试在URL中使用其他ID?我也像您一样尝试过这样做,但我得到了一个异常:无法识别的字段“steam\u appid”(Class model.Data),如果ID为(这是可变的)作为格式中的一个键,那么您可以考虑在没有特定数据绑定的情况下,将整个事物解析为原始图,然后拔出对应于该键的子映射,并通过使用不指定“10”的泛型模式再次序列化到JSON和反序列化来重新映射子映射。或任何其他特定ID。不幸的是,我不知道如何才能做到这一点。您是对的,这是指向此库的链接:)
import java.net.URI;
import java.util.Map;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import model.Game;
public class View {
public static void main(String[] args) throws Exception {
String id = args[0];
URI uri = new URI("http", "store.steampowered.com", "/api/appdetails",
"appids=" + id, null);
ObjectMapper objectMapper = new ObjectMapper();
Map<String, Object> obj = objectMapper.readValue(uri.toURL(),
new TypeReference<Map<String, Object>>(){});
Game game = objectMapper.convertValue(obj.get(id), Game.class);
System.out.println(game.getData().getName());
}
}
> mvn clean package
> java -jar target/test-json.jar 10
Counter-Strike
> java -jar target/test-json.jar 219
Half-Life 2: Demo
{
"type": "object",
"required":false,
"javaType":"model.Game",
"properties": {
"10": {
"id": "10",
"type": "object",
...
}
}
}
{
"type": "object",
"required":false,
"javaType":"model.Games",
"additionalProperties": {
"id": "game",
"type": "object",
"javaType": "model.Game"
...
}
}