当前位置: 首页 > 知识库问答 >
问题:

RESTTemplate:无法反序列化START_OBJECT标记之外的对象实例

黄德明
2023-03-14

我正在试用Spring中的RestTemplate。我试图读入这个JSON数据:JSON数据。数据是一个键值对,其中键是“GeoNames”,值是“GeoName”对象数组。

我有一个Geoname类来处理输入。这个类中还有getter和setter。然后,我有一个应用程序类,它只运行一个main方法来调用一个RestTemplate对象:

@JsonIgnoreProperties(ignoreUnknown = true)
public class Geoname {
    private String name;
    private long lat;
    private long lng;
    private String countrycode;
}
public class App 
{
    public static void main( String[] args )
    {
        String jsonUrl = "http://api.geonames.org/citiesJSON?north=44.1&south=-9.9&east=-22.4&west=55.2&lang=de&username=demo";

        RestTemplate template = new RestTemplate();
        ResponseEntity<Geoname[]> entity = template.getForEntity(jsonUrl, Geoname[].class);
        List<Geoname> data = Arrays.asList(entity.getBody());

        System.out.print("Success!");
    }
}
Exception in thread "main" org.springframework.http.converter.HttpMessageNotReadableException: Could not read JSON: Can not deserialize instance of com.declan.Geoname[] out of START_OBJECT token
 at [Source: sun.net.www.protocol.http.HttpURLConnection$HttpInputStream@54fc3ac5; line: 1, column: 1]; nested exception is com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of com.declan.Geoname[] out of START_OBJECT token
 at [Source: sun.net.www.protocol.http.HttpURLConnection$HttpInputStream@54fc3ac5; line: 1, column: 1]
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.readJavaType(AbstractJackson2HttpMessageConverter.java:208)
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.read(AbstractJackson2HttpMessageConverter.java:200)
    at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:96)
    at org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:812)
    at org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:796)
    at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:576)
    at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:529)
    at org.springframework.web.client.RestTemplate.getForEntity(RestTemplate.java:261)
    at com.declan.App.main(App.java:20)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:134)
Caused by: com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of com.declan.Geoname[] out of START_OBJECT token
 at [Source: sun.net.www.protocol.http.HttpURLConnection$HttpInputStream@54fc3ac5; line: 1, column: 1]
    at com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:148)
    at com.fasterxml.jackson.databind.DeserializationContext.mappingException(DeserializationContext.java:835)
    at com.fasterxml.jackson.databind.DeserializationContext.mappingException(DeserializationContext.java:831)
    at com.fasterxml.jackson.databind.deser.std.ObjectArrayDeserializer.handleNonArray(ObjectArrayDeserializer.java:232)
    at com.fasterxml.jackson.databind.deser.std.ObjectArrayDeserializer.deserialize(ObjectArrayDeserializer.java:139)
    at com.fasterxml.jackson.databind.deser.std.ObjectArrayDeserializer.deserialize(ObjectArrayDeserializer.java:17)
    at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:3560)
    at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:2660)
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.readJavaType(AbstractJackson2HttpMessageConverter.java:205)
    ... 13 more

编辑

好了,我现在有了这个新类,它现在对JSON数据发出GET请求。但是,在调试之后,ResponseEntity正文将数组设置为NULL。我需要手动在Geonames中实例化数组吗?

@JsonIgnoreProperties(ignoreUnknown = true)
public class Geonames {
    @JsonProperty("geonames")
    Geoname[] geonames;

    public void setGeonames(Geonames[] geonames) {
        this.geonames = geonames;
    }

    public void getGeonames() {
        return geonames;
    }
}

共有1个答案

戚森
2023-03-14

解决了。结果显示,空值是因为JSON链接有每小时最大点击量限制。通过在网站上创建我自己的帐户,api给了我自己的限制。因此,响应体随后填充了数据

 类似资料: