users@jersey.java.net

JSON Unmarshalling Issue

From: Ni Yue <ni2yue4_at_gmail.com>
Date: Wed, 3 Jun 2009 00:02:27 +0800

Hello,

I am using Jersey to serve JSON response and met some issue. In my case, I
used JAXB for XML marshalling and used Jersey's build-in function to map XML
to JSON. And there're multiple namespaces in my XML schema, for example:
*
base.xsd:*

> <?xml version="1.0" encoding="UTF-8"?>
> <schema
> xmlns="http://www.w3.org/2001/XMLSchema"
> xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
> xmlns:base="http://fruitbase.example.org"
> targetNamespace="http://fruitbase.example.org"
> elementFormDefault="qualified">
>
> <element name="fruits">
> <complexType>
> <sequence>
> <element name="fruit" type="base:Fruit"
> minOccurs="0"></element>
> </sequence>
> </complexType>
> </element>
>
> <complexType name="Fruit">
> <sequence>
> <element name="name" type="string"/>
> <element name="color" type="string"/>
> </sequence>
> </complexType>
> </schema>


*fruits.xsd:*

> <?xml version="1.0" encoding="UTF-8"?>
> <schema
> xmlns="http://www.w3.org/2001/XMLSchema"
> xmlns:base="http://fruitbase.example.org"
> xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
> xmlns:fruits="http://fruits.example.org"
> targetNamespace="http://fruits.example.org"
> elementFormDefault="qualified">
> <import namespace="http://fruitbase.example.org"
> schemaLocation="base.xsd"></import>
> <complexType name="Apple">
> <complexContent>
> <extension base="base:Fruit">
> <sequence>
> <element name="weight" type="int"></element>
> </sequence>
> <anyAttribute/>
> </extension>
> </complexContent>
> </complexType>
>
> <complexType name="Orange">
> <complexContent>
> <extension base="base:Fruit">
> </extension>
> </complexContent>
> </complexType>
> </schema>
>

My question is:
1) In order to correctly marshall/unmarshall JSON request/response using
Jersey and its client API, which JSON notation (mapped, mappedJettison,
badgerFish, natual) should I use in this case (with multiple namespaces in
schema)? It seems only mappedJettison notation can be used as I did a simple
search in the mail list archive, but I am not sure.

2) I implemented a JAXBContextResolver and tried mappedJettison notation:

> public JAXBContextResolver() throws Exception {
> Map<String, String> namespaceMap = new HashMap<String, String>();
> namespaceMap.put("http://www.w3.org/2001/XMLSchema", "xs");
> namespaceMap.put("http://www.w3.org/2001/XMLSchema-instance",
> "xsi");
> namespaceMap.put("http://fruitbase.example.org", "base");
> namespaceMap.put("http://fruits.example.org", "fruits");
> JSONConfiguration config =
> JSONConfiguration.mappedJettison().xml2JsonNs(namespaceMap).build();
> this.m_context = new JSONJAXBContext(
> config,
> m_types);
> }

But in the JSON response, I found JAXB used a random prefix (ns2) for QName
in attribute values:

> {"base.fruits":{"base.fruit":{"@xsi.type":"*ns2:Apple*","base.name":"apple","base.color":"red","fruits.weight":2}}}
>
> Is it a bug for Jersey? I know it is possible to change that behavior via
JAXB API (https://jaxb.dev.java.net/guide/Changing_prefixes.html), but it is
wrapped by Jersey, and how can I control that in Jersey?

I attached a zipped maven project, which contains detailed implementation
and test case for my issue. Thanks in advance for all your help.

Environment:
Jersey 1.0.3
Java 1.5

Regards,
Ni Yue