cancel
Showing results for 
Search instead for 
Did you mean: 

commercewebservices/REST API (v2): customize serialized output

Former Member

Hi,

I'm using OCC (REST API v2) and try to rename instances of serialized *WsDTO objects in JSON/XML responses. In the wiki I found hints for doing that in v1 of API which is using XStream library: https://wiki.hybris.com/display/release5/Customizing+the+Commerce+Web+Services (e.g. TypeAliasMapping)

API v2 seems to apply JAX instead of XStream library. Are there any examples how to rename particular types in this version? For example I have a TestWsDTO and I would like to rename the root element of the XML response from "Test" to another name. Also I would like to configure for particular collections to be implicit or not as it is done in API v1 via xstream-converters-spring.xml. What is the way to do that in v2?

Regards,

Oliver

Accepted Solutions (1)

Accepted Solutions (1)

Former Member

Hi,

In V2 version of API we completely changed the way how marshallers work. There were many reasons for this, like: simplification, scalability, separation of concerns and performance. In V1 version there was many custom converters for many types, converters were aware of particular formats (mixed JSON and XML logic, etc.).

Now in V2 version it works in much clearer way:

  1. Business objects are converted to POJO objects dedicated for REST API (WsDTO's), it is done by Orika

  2. Those WsDTO objects are marshalled/unmarshalled directly by JAXB. ALL objects are marshalled and unmarshalled in the same way, there is no customization during this process.

In general I don't recommend to customize it. In my opinion it is better to convert all DTO's always in the same way. It is the simplest and the most predictable behaviour. If you still would like to do it, here is detailed description how it works:

  1. Jaxb2HttpMessageConverter is a converter class declared in spring configuration as message converter (separate instances for XML and JSON)

  2. At runtime HttpMessageConverter's methods have the information about 'root' class that is converted (root class = class annotated by RequestBody or ResponseBody in controller)

  3. During the marshalling or unmarshalling process Jaxb2HttpMessageConverter creates JAXBContext for given 'root' class. It uses by default MoxyJaxbContextFactoryImpl for that purpose.

  4. MoxyJaxbContextFactoryImpl factory creates JAXBContext using EeLink Moxy implementation of JAXB. This implementation allows to set all JAXB metadata programmatically instead of annotations. This is important, because DTO classes are autogenerated and there is simple no way to use annotations in them.

  5. In order to provide JAXB metadata the factory creates WsDTOGenericMetadataSourceAdapter for each seen class (see http://ee.org/eelink/documentation/2.5/moxy/runtime004.htm for details).

  6. WsDTOGenericMetadataSourceAdapter creates JAXB metadata at runtime in the same way for all classes (all WsDTO's).

The implementation of naming root elements in XML payload is done in this WsDTOGenericMetadataSourceAdapter. It simply cuts 'WsDTO' from class name (function createNodeNameFromClass). This class is also responsible for wrapping collections (in XML).

In order to customize it, you have to change this implementation, it can be done on vairous levels. The best way is to provide configuration to WsDTOGenericMetadataSourceAdapter, so that it will be able to work with any class with default settings but with customizations for particular classes.

Regards,

Marek

sahoomanoja
Explorer
0 Kudos

Hi Marek,

while I am trying to use unmarshalling (posting of json data and consuming it ) I am getting below error. { "errors" : [ { "message" : "Could not instantiate JAXBContext for class [class java.lang.String]: null; nested exception is javax.xml.bind.JAXBException\n - with linked exception:\n[java.lang.NullPointerException]", "type" : "HttpMessageConversionError" } ] }

Can you please help on this.

Regards, Manoja

Answers (1)

Answers (1)

Former Member
0 Kudos

Hi,

thank you for the answer. Unfortunately I can't find any hints for customizing tag names in the response XML on that wiki page. I just found the possibility to map one single field of a data object to another with a different name of a WsDTO object.

Regards,

Oliver

Former Member
0 Kudos

how did you achieve map one single field of a data object to another with a different name of a WsDTO object? can you please give sample snippet.