I am receiving following error message, I have Status class but it is not being recognized. I've got no idea how to proceed and could not find an answer online.
Error
org.springframework.http.converter.HttpMessageNotReadableException: Could
not read JSON: Unrecognized field "Status" (class
com.myproject.ticket.EventsResponse), not marked as ignorable (3 known
properties: "events", "status", "page"])
....
Caused by:
com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException:
Unrecognized field "Status" (class com.myproject.ticket.EventsResponse),
not marked as ignorable (3 known properties: "events", "status", "page"])
EventsResponse
@XmlRootElement(name = "EventsResponse")
@XmlAccessorType(XmlAccessType.FIELD)
public class EventsResponse {
@XmlElement(name = "Status")
private Status status;
@XmlElement(name = "Paging")
private Page page;
@XmlElementWrapper(name="Events")
@XmlElement(name = "Event")
private List<Event> events;
.....
Status
@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class Status {
@XmlElement(name = "Version")
private double version;
@XmlElement(name = "TimeStampUtc")
private Date timeStampUtc;
@XmlElement(name = "Code")
private int code;
@XmlElement(name = "Message")
private String message;
@XmlElement(name = "Details")
private String details;
Response
<EventsResponse xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<Status>
<Version>2.0</Version>
<TimeStampUtc>2016-06-11T09:32:21</TimeStampUtc>
<Code>0</Code>
<Message>Success</Message>
<Details />
</Status>
<Paging>
<PageNumber>1</PageNumber>
<PageSize>50</PageSize>
<PageResultCount>15</PageResultCount>
<TotalResultCount>15</TotalResultCount>
<TotalPageCount>1</TotalPageCount>
</Paging>
<Events>
<Event>
I added following to Status but I am still receiving the same error.
@XmlElement(name = "Status")
@JacksonXmlProperty(localName = "Status")
private Status status;
I failed to reconstruct your issue.
I created a test project github here that has Jackson configuration and JAXB annotations that meet your needs.
I added dependencies to jackson-dataformat-xml and woodstox-core-asl as your Stax implementations (in my test project I am using Jackson 2.6.6. ,Spring 4.2.6)
<dependency>
<groupId>com.fasterxml.jackson.dataformat</groupId>
<artifactId>jackson-dataformat-xml</artifactId>
<version>2.6.6</version>
</dependency>
<dependency>
<groupId>org.codehaus.woodstox</groupId>
<artifactId>woodstox-core-asl</artifactId>
<version>4.4.1</version>
</dependency>
Configure the Jackson2ObjectMapperBuilder to use both Jackson and JAXB annotations. This is a Spring-boot example to convert to Simple Spring-MVC look here
@SpringBootApplication
public class EventAppConfiguration {
public static void main(String[] args) {
SpringApplication.run(EventAppConfiguration.class, args);
}
@Bean
public Jackson2ObjectMapperBuilder jacksonBuilder() {
Jackson2ObjectMapperBuilder b = new Jackson2ObjectMapperBuilder();
b.indentOutput(true)
//Enable Introspects for both Jackson and JAXB annotation
.annotationIntrospector(introspector())
//Use CamelCase naming
.propertyNamingStrategy(PropertyNamingStrategy.PASCAL_CASE_TO_CAMEL_CASE)
.dateFormat(new SimpleDateFormat("yyyy-MM-dd'T'hh:mm:ss"));
return b;
}
@Bean
public AnnotationIntrospector introspector(){
AnnotationIntrospector primary = new JacksonAnnotationIntrospector();
AnnotationIntrospector secondary = new JaxbAnnotationIntrospector(TypeFactory.defaultInstance());
AnnotationIntrospector pair = AnnotationIntrospector.pair(primary, secondary);
return pair;
}
}
Note the use of
PropertyNamingStrategy.PASCAL_CASE_TO_CAMEL_CASE
it will save you the need to specify alternative naming for first letter capitalization and will require the use for JAXB annotation only for warping and renaming for example my EventsResponse will look like:
@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class EventsResponse {
private Status status;
@XmlElement(name = "Paging")
private Page page;
@XmlElementWrapper(name = "Events")
@XmlElement(name = "Event")
private List<Event> events;
...
}
You have two options, assuming you are using Jackson to deserialize your XML objects. The simplest is to use Jackson's own XML annotations instead of or as well as the JAXB @XmlElement
annotations. For example:
@XmlElement(name = "Status")
@JacksonXmlProperty(localName = "Status")
private Status status;
(The @XmlElement
annotation is in the jackson-dataformat-xml
package in Maven - the version should match your other Jackson package versions.)
The alternative is to register an AnnotationIntrospector as part of your deserialization chain - ie. (from a unit test):
XmlMapper mapper = new XmlMapper();
AnnotationIntrospector aiJaxb = new JaxbAnnotationIntrospector(TypeFactory.defaultInstance());
mapper.setAnnotationIntrospector(aiJaxb);
// EVENTS_RESPONSE is the incoming XML
EventsResponse response = mapper.readValue(EVENTS_RESPONSE, EventsResponse.class);
This recognises the @XmlElement
annotation. There are more details in this answer if you need to include this as part of a Spring configuration, for example.
(In order to use the JaxbAnnotationIntrospector
class, you will need the jackson-module-jaxb-annotation
module from Maven.)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With