如何使用Restlet将Json结果反序列化为POJO

时间:2012-04-01 17:52:36

标签: java json restlet pojo

我正在尝试将Web服务的Json结果反序列化为POJO。

ClientResource clientResource = new ClientResource("http://itunes.apple.com/search?term=marc+jordan&media=music&entity=album");
AlbumInfoResource resource = clientResource.wrap(AlbumInfoResource.class);
AlbumInfo albumInfo = resource.retrieve();

结果albumInfo为空,不会抛出任何异常 我是Restlet的新手,我做错了什么?

接口:

public interface AlbumInfoResource {
  @Get
  public AlbumInfo retrieve();
 }

来自Web服务的Json结果如下所示:

{
    "resultCount": 49,
    "results": [
        {
            "wrapperType": "collection",
            "collectionType": "Album",
            "artistId": 771969,
            "collectionId": 205639995,
            "amgArtistId": 4640,
            "artistName": "Marc Jordan",
            "collectionName": "This Is How Men Cry",
            "collectionCensoredName": "This Is How Men Cry",
            "artistViewUrl": "http://itunes.apple.com/us/artist/marc-jordan/id771969?uo=4",
            "collectionViewUrl": "http://itunes.apple.com/us/album/this-is-how-men-cry/id205639995?uo=4",
            "artworkUrl60": "http://a5.mzstatic.com/us/r30/Music/cd/3f/13/mzi.rxpvpvdd.60x60-50.jpg",
            "artworkUrl100": "http://a1.mzstatic.com/us/r30/Music/cd/3f/13/mzi.rxpvpvdd.100x100-75.jpg",
            "collectionPrice": 9.9,
            "collectionExplicitness": "notExplicit",
            "trackCount": 10,
            "copyright": "1999 Cafe Productions Inc.",
            "country": "USA",
            "currency": "USD",
            "releaseDate": "2006-11-07T08:00:00Z",
            "primaryGenreName": "Jazz"
        },
...
...
    }
]

}

AlbumInfo类:

public class AlbumInfo implements Serializable {

    private static final long serialVersionUID = 1L;

    private int _resultCount;
    private ArrayList<Album> _albums;

    public AlbumInfo() {
        _albums = new ArrayList<Album>();
    }

    public AlbumInfo(int resultCount, ArrayList<Album> albums) {
        _resultCount = resultCount;
        _albums = albums;
    }

    public int getResultCount() {
        return _resultCount;
    }

    public void setResultCount(int resultCount) {
        _resultCount = resultCount;
    }

    public ArrayList<Album> getAlbums() {
        return _albums;
    }

    public void setAlbums(ArrayList<Album> _albums) {
        this._albums = _albums;
    }

}

Album类可以在这里发布,但我已尽可能合理地映射元素。

4 个答案:

答案 0 :(得分:2)

如果您还没有,则需要将Restlet的JacksonConverter添加到已注册的转换器列表中:

    List<ConverterHelper> converters = Engine.getInstance().getRegisteredConverters();
    converters.add(new JacksonConverter());

,当然,将org.restlet.ext.jackson.jar添加到您的构建路径。

答案 1 :(得分:1)

注意:我是EclipseLink JAXB (MOXy)主管,是JAXB 2 (JSR-222)专家组的成员。

以下是如何通过利用JAXB注释来实现MOXy:

<强> AlbumInfo

package forum9966753;

import java.io.Serializable;
import java.util.ArrayList;
import javax.xml.bind.annotation.*;

@XmlType(propOrder={"resultCount", "albums"})
public class AlbumInfo implements Serializable {

    private static final long serialVersionUID = 1L;

    private int _resultCount;
    private ArrayList<Album> _albums;

    public AlbumInfo() {
        _albums = new ArrayList<Album>();
    }

    public AlbumInfo(int resultCount, ArrayList<Album> albums) {
        _resultCount = resultCount;
        _albums = albums;
    }

    public int getResultCount() {
        return _resultCount;
    }

    public void setResultCount(int resultCount) {
        _resultCount = resultCount;
    }

    @XmlElement(name="results")
    public ArrayList<Album> getAlbums() {
        return _albums;
    }

    public void setAlbums(ArrayList<Album> _albums) {
        this._albums = _albums;
    }

}

<强>相册

以下是Album课程的缩小版:

package forum9966753;

public class Album {

    private String wrapperType;

    public String getWrapperType() {
        return wrapperType;
    }

    public void setWrapperType(String wrapperType) {
        this.wrapperType = wrapperType;
    }

}

<强> jaxb.properties

要将MOxy指定为JAXB提供程序,您需要在与域类相同的程序包中添加名为jaxb.properties的文件,并使用以下条目:

javax.xml.bind.context.factory = org.eclipse.persistence.jaxb.JAXBContextFactory

<强>演示

package forum9966753;

import java.io.InputStream;
import java.net.*;
import java.util.List;
import javax.xml.bind.*;
import javax.xml.transform.stream.StreamSource;
import org.example.Customer;

public class JavaSEClient {

    private static final String MEDIA_TYPE = "application/json";

    public static void main(String[] args) throws Exception {
        String uri = "http://itunes.apple.com/search?term=marc+jordan&media=music&entity=album";
        URL url = new URL(uri);
        HttpURLConnection connection =
            (HttpURLConnection) url.openConnection();
        connection.setRequestMethod("GET");
        connection.setRequestProperty("Accept", MEDIA_TYPE);

        JAXBContext jc = JAXBContext.newInstance(AlbumInfo.class);

        Unmarshaller unmarshaller = jc.createUnmarshaller();
        unmarshaller.setProperty("eclipselink.media-type", MEDIA_TYPE);
        unmarshaller.setProperty("eclipselink.json.include-root", false);
        InputStream xml = connection.getInputStream();
        AlbumInfo albumInfo = unmarshaller.unmarshal(new StreamSource(xml), AlbumInfo.class).getValue();
        connection.disconnect();

        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.setProperty("eclipselink.media-type", MEDIA_TYPE);
        marshaller.setProperty("eclipselink.json.include-root", false);
        marshaller.marshal(albumInfo, System.out);
    }

}

<强>输出

以下是运行演示代码的输出。由于示例域模型仅包含一些属性,因此输出远小于输出。可以轻松应用JAXB映射来映射文档的其余部分。

{
   "resultCount" : 49,
   "results" : [ {
      "wrapperType" : "collection"
   } ]
}

了解更多信息

答案 2 :(得分:0)

尝试使用JAXB annotations或使用Jersey进行JSON映射。本手册对您有用:link

答案 3 :(得分:0)

最近我不得不开发一个带有Restlet框架的Android应用程序,我花了很多时间来了解如何反序列化JSONObject。 在这里,我将解释我的方法。 我还在GitHub上发布了一个完整的Android应用程序:
https://github.com/alchimya/android-restlet

Restlet 2.3.2包含Gson lib。 使用Gson可以非常简单地映射和反序列化资源。

1)使用以下类映射您的实体库:

import com.google.gson.annotations.SerializedName;
import java.io.Serializable;

public class Album implements Serializable {

    @SerializedName("wrapperType")
    private String wrapperType;

    @SerializedName("collectionType")
    private String collectionType;

    @SerializedName("artistId")
    private String artistId;

    public String getWrapperType() {
        return wrapperType;
    }
    public void setWrapperType(String wrapperType) {
        this.wrapperType = wrapperType;
    }

    public String getCollectionType() {
        return collectionType;
    }
    public void setCollectionType(String collectionType) {
        this.collectionType = collectionType;
    }

    public String getArtistId() {
        return artistId;
    }
    public void setArtistId(String artistId) {
        this.artistId = artistId;
    }

    ......
    ......
    ......
}

注意:在上一个类中,每个属性都有一个注释(@SerializedName)来映射相应的JSON字段。有关更多信息,请参阅本教程:
http://www.javacodegeeks.com/2011/01/android-json-parsing-gson-tutorial.html

2)创建一个具有List属性的类:

public class Albums {
    public List<Album> results;
}

3)使用Restlet

使用您的资源
String uri="http://itunes.apple.com/search?term=marc+jordan&media=music&entity=album";

ClientResource resource = new ClientResource(url);
Representation rep = resource.get();

JsonRepresentation represent = new JsonRepresentation(rep);
JSONObject jsonobject = represent.getJsonObject();
String jsonText = jsonobject.toString();

Gson gson = new Gson();
Albums response = gson.fromJson(jsonText, Albums.class);

对于response.results,将会有所有反序列化的项目。