Java 使用Jackson解析动态生成的JSON对象名
我正在尝试使用Jackson将一些MediaWiki上下文从JSON反序列化到POJO中。但是,问题是其中一个JSON对象名是本文的整数ID值,因此不能使用像Java 使用Jackson解析动态生成的JSON对象名,java,json,jackson,Java,Json,Jackson,我正在尝试使用Jackson将一些MediaWiki上下文从JSON反序列化到POJO中。但是,问题是其中一个JSON对象名是本文的整数ID值,因此不能使用像@JsonProperty这样的注释,因为该值从来都不是常量 下面是一些示例JSON来描述我的意思: http://en.wikipedia.org/w/api.php?action=query&titles=Albert%20Einstein&prop=info&format=json&indexpageids { "query"
@JsonProperty
这样的注释,因为该值从来都不是常量
下面是一些示例JSON来描述我的意思:
http://en.wikipedia.org/w/api.php?action=query&titles=Albert%20Einstein&prop=info&format=json&indexpageids
{
"query": {
"pageids": [
"736"
],
"pages": {
"736": {
"pageid": 736,
"ns": 0,
"title": "Albert Einstein",
"contentmodel": "wikitext",
"pagelanguage": "en",
"touched": "2014-01-05T03:14:23Z",
"lastrevid": 588780054,
"counter": "",
"length": 106159
}
}
}
}
(MediaWiki建议添加&indexpageids参数以帮助解析,但我看不出它对我有什么用处。)
我尝试使用@JsonAnyGetter
和@JsonAnySetter
注释,但它们似乎没有帮助,抛出了相同的异常com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException:Unrecognized字段“736”(类WikipediaPages),未标记为可忽略(一个已知属性:“wikipediaPage”)
谢谢你的帮助
编辑:以下是当前相关类的外观:
public class WikipediaPages {
private Map<String, WikipediaPage> wikipediaPageMap = new HashMap<String, WikipediaPage>();
public Map<String, WikipediaPage> getWikipediaPageMap() {
return wikipediaPageMap;
}
public void setWikipediaPageMap(Map<String, WikipediaPage> wikipediaPageMap) {
this.wikipediaPageMap = wikipediaPageMap;
}
}
为了回答异常的根本原因,
@JsonAnySetter
javadoc声明
可用于定义非静态的标记注释,
双参数方法(属性的第一个参数名称,属性的第二个值
设置),[…]
因此,使用这样的mixin
@JsonAnySetter
void setWikipediaPageMap(Map<String, WikipediaPage> wikipediaPageMap);
其中页面
为
class Page {
private int pageid;
private int ns;
private String title;
private String contentmodel;
private String pagelanguage;
private String touched; // this could be a Date, with the appropriate format configuration
private int lastrevid;
private String counter;
private int length;
@Override
public String toString() {
return "Page [pageid=" + pageid + ", ns=" + ns + ", title=" + title
+ ", contentmodel=" + contentmodel + ", pagelanguage="
+ pagelanguage + ", touched=" + touched + ", lastrevid="
+ lastrevid + ", counter=" + counter + ", length=" + length
+ "]";
}
public int getPageid() {
return pageid;
}
public void setPageid(int pageid) {
this.pageid = pageid;
}
public int getNs() {
return ns;
}
public void setNs(int ns) {
this.ns = ns;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getContentmodel() {
return contentmodel;
}
public void setContentmodel(String contentmodel) {
this.contentmodel = contentmodel;
}
public String getPagelanguage() {
return pagelanguage;
}
public void setPagelanguage(String pagelanguage) {
this.pagelanguage = pagelanguage;
}
public String getTouched() {
return touched;
}
public void setTouched(String touched) {
this.touched = touched;
}
public int getLastrevid() {
return lastrevid;
}
public void setLastrevid(int lastrevid) {
this.lastrevid = lastrevid;
}
public String getCounter() {
return counter;
}
public void setCounter(String counter) {
this.counter = counter;
}
public int getLength() {
return length;
}
public void setLength(int length) {
this.length = length;
}
}
剩下的就是将
Map
作为query
和pages
JSON元素的某个包装类中的一个字段。Makepages
aMap
其中Page
保存所有其他数据。相同的异常:com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException:unrecogned字段“38991692”(WikipediaPages类),未标记为可忽略(一个已知属性:“wikipediaPageMap”])
。只需使用相关代码编辑原始问题。如果使用顶部代码块,它也可以工作。我通过创建Jackson模块来应用mixin,在setupContext
方法中添加每个mixin,并在ObjectMapper
实例化中应用该模块。我希望与JSON反序列化代码的其余部分保持一致,并解决最初的问题。@ryan据我所知,发生错误的原因是Jackson不知道如何映射JSON元素名736
。我有4个模型类,WikipediaResult用于顶级JSON,WikipediaQuery用于“查询”对象,WikipediaPages用于“页面”对象,WikipediaPages用于动态命名对象。我通过调用WikipediaResult WikipediaResult=JacksonBuilder.getObjectMapper().readValue(getInputStreamFromConnection(buildURLFromQuery(query)),WikipediaResult.class)进行反序列化。从HTTP连接提供InputStream。JacksonBuilder只是实例化一个新的ObjectMapper
实例,并将包含mixin的模块添加到其中。@Ryan我对此无能为力。通过编辑您的问题向我展示。演示如何设置ObjectMapper
。我也想看看维基百科的结果。当然,我编辑了这个问题。谢谢你留下来帮忙。
@JsonAnySetter
void setWikipediaPageMap(Map<String, WikipediaPage> wikipediaPageMap);
String json = "{ \"query\": { \"pageids\": [ \"736\" ], \"pages\": { \"736\": { \"pageid\": 736, \"ns\": 0, \"title\": \"Albert Einstein\", \"contentmodel\": \"wikitext\", \"pagelanguage\": \"en\", \"touched\": \"2014-01-05T03:14:23Z\", \"lastrevid\": 588780054, \"counter\": \"\", \"length\": 106159 } } } }";
ObjectMapper mapper = new ObjectMapper();
JsonNode node =mapper.readTree(json);
node = node.get("query").get("pages");
Map<String, Page> pages = mapper.readValue(node.traverse(), new TypeReference<Map<String, Page>>() {
});
System.out.println(pages);
{736=Page [pageid=736, ns=0, title=Albert Einstein, contentmodel=wikitext, pagelanguage=en, touched=2014-01-05T03:14:23Z, lastrevid=588780054, counter=, length=106159]}
class Page {
private int pageid;
private int ns;
private String title;
private String contentmodel;
private String pagelanguage;
private String touched; // this could be a Date, with the appropriate format configuration
private int lastrevid;
private String counter;
private int length;
@Override
public String toString() {
return "Page [pageid=" + pageid + ", ns=" + ns + ", title=" + title
+ ", contentmodel=" + contentmodel + ", pagelanguage="
+ pagelanguage + ", touched=" + touched + ", lastrevid="
+ lastrevid + ", counter=" + counter + ", length=" + length
+ "]";
}
public int getPageid() {
return pageid;
}
public void setPageid(int pageid) {
this.pageid = pageid;
}
public int getNs() {
return ns;
}
public void setNs(int ns) {
this.ns = ns;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getContentmodel() {
return contentmodel;
}
public void setContentmodel(String contentmodel) {
this.contentmodel = contentmodel;
}
public String getPagelanguage() {
return pagelanguage;
}
public void setPagelanguage(String pagelanguage) {
this.pagelanguage = pagelanguage;
}
public String getTouched() {
return touched;
}
public void setTouched(String touched) {
this.touched = touched;
}
public int getLastrevid() {
return lastrevid;
}
public void setLastrevid(int lastrevid) {
this.lastrevid = lastrevid;
}
public String getCounter() {
return counter;
}
public void setCounter(String counter) {
this.counter = counter;
}
public int getLength() {
return length;
}
public void setLength(int length) {
this.length = length;
}
}