XML produce by RESTful webservice - java

I have a RESTful web services , up and running and it produces XML output upon a call by the client.
So I have a class to represent the data and I have annotated with #XMLRootElemnt and so it produces the data accordingly as XML. My question is - what is the best way to represent the XML , when there is an inner class in the class that I have annotated with #XMLRootElement? Pardon me if the question is not clear, and if you ask me more detail, I can explain. But if someone already got what I am asking, please advise.

I think that you want to explain that you want to produce an XML like this:
<programmer>
<name>Marcelo Tataje</name>
<pl>Java</pl>
<id>1</id>
</programmer>
And you have used something like this to produce it:
#XmlRootElement
public class Programmer
{
private String name;
private String pl;
private int id;
public Programmer()
{
}
//here your getters and setters
}
And your web services looks like this:
#GET
#Produces(MediaType.APPLICATION_XML)
#Path("/getProgrammer")
public Programmer getProgrammer()
{
Programmer p = new Programmer();
p.setName("Marcelo Tataje");
p.setPl("Java");
p.setId(1);
return p;
}
Ant then you invoke your client and so on... I think that's the simpliest way to do it and it's not bad, if you want the best way or a better method it is by using Spring3 which supports Rest and XML, you will have a structure for your requirements in a flash, is a faster framework. Recommended, well I'm answering to you of what I understand to your question.
http://blog.springsource.com/2009/03/08/rest-in-spring-3-mvc/

Got it worked. basically need to use the #XmlElementWrapper and #XmlElement and the field property will be a list of string.

Related

Use #RequestMapping with Dynamic URL at Controller Level

I've been doing my fair amount of research through Stack Overflow and Google and the closest I found was something like this post but still it does not answer my question. The documentation for #RequestMapping doesn't say anything about the possibilities of using dynamic URLs at the controller level so I was wondering if something like the code below is possible:
#RequestMapping("/something/{somethingsId}")
public class ExampleController{
//Some methods mapping to some endpoints that start with /something/{somethingsId}
#GetMapping("/getOtherThing")
public ResponseEntity<> getOtherThing(#PathVariable("somethingsId")String somethingsId){
//Do something with somethingsId
}
}
This is just an example code of what I intend to achieve. I want to do this to separate some functionalities into different controllers that need this somethingsId to be able to work but I don't know if what I want is possible or if I will have to content myself with repeating the same thing in every method of the controller to get that "somethingsId" path variable.
Thank you in advance for your answers.
Yes you can achive it, follow the same way as I mentioned
#Controller
#RequestMapping("/owners/{ownerId}")
public class Test {
#RequestMapping("/pets/{petId}")
public void findPet(#PathVariable String ownerId, #PathVariable String petId, Model model) {
System.out.println("ownerId "+ownerId+" petId "+petId);
}
}

How to support Backward Comparability for the type of param in REST APIs

I've 40-45 REST APIs built using Apache CXF framework. I do have a parameter as telehpneNumber which is of type Long now I need to change it to String but also want that these should be backward compatible.
Current thoughts over it to create two rest controllers like v1(old) v2(new) v2 will be acceptingStringformat. Using adaptor pattern I'll proxyv1request tov2. ButtelephoneNumberparam is used in various objects & places. I though of making it as a type ofObject` but this work as expected when it's about taking request, but it will not when I'll be returning response.
What will be the right approach to solve this kind of backward-forawrd compatibility issue ?
Currently my thoughts is similar to something as coded below:
class OldTelephoneRequest{
Long telephoneNumber;
//some more variables
//getters & setters
}
class TelephoneRequest{
String telephoneNumber;
//some more variables
//getters & setters
}
#Path("/rest/services/v1")
class OldRestAPI{
#Path("telephoneDetails")
public Response telephoneDetails(OldTelephoneRequest oldTelephoneRequest){
//make proxy call to v2 which will accept telephoneRequst object
//Convert telephoneRequst to newTelephoneRequst(which will have telephoneNumber as String )
TelephoneRequest request=new TelephoneRequest(oldTelephoneRequest);
return RestAPI.telephoneDetails(telephoneRequest)
}
}
#Path("/rest/services/v2")
class RestAPI{
#Path("telephoneDetails")
public Response telephoneDetails(TelephoneRequest telephoneRequest){
//business logic
}
}
The above approach has issue is that I'll have to construct 40-45 constructors for each request which will basically convert from oldRequest to newRequst
Let me know what will be the better approach to solve this problem.
The cleanest solution would be to leave the design as is and let MapStruct do the mapping for you:
#Mapper
public interface TelephoneRequestMapper {
TelephoneRequestMapper INSTANCE = Mappers.getMapper(TelephoneRequestMapper.class );
#Mapping(source = "oldTelephoneRequest", target = "telephoneRequest")
TelephoneRequest oldTelephoneRequestToTelephoneRequest(OldTelephoneRequest oldTelephoneRequest);
}
For more information:
http://mapstruct.org/

How to JSON parse immutable object in Java + Jersey

So I am just trying out Jersey for REST services and it seems to we working out fine. I only expose get services and all of the object types that I expose with these services have an immutable object representation in Java. By default Jersey seems to use a parser (JAXB?), requiring a #XmlRootElement annotation for the class that should be parsed, zero-arg constructor and setters.
I have been using Gson with no zero-arg constructor, no setters and final on all fields with no problems at all. Is there any way to accomplish this with Jersey(i.e. the paser it is using)? I have seen solutions with adapter classes that map data from a immutable object to a mutable representation, but this seems like a lot of boilerplate(new classes, more annotations, etc.) if it can be achieved with Gson without anything added.
Note: 1) I have heard people promote using zero-arg constructor and claim that Gson should not work without it. This is not what I am interested in. 2) I really have tried googling this but my keywords might be off. In other words, humiliate me in moderation.
EDIT 1:
My webservice works if I do like this:
#XmlRootElement
public class Code{
private String code; //Silly object just used for example.
public Code(){}
//(G || S)etters
}
With this class exposing the object:
#GET
#Produces(MediaType.APPLICATION_JSON)
public Set<Code> get(#QueryParam("name") String name) { // Here I want to use a class of my own instead of String name, haven't figured out how yet.
return this.codeService.get(name);
}
If I replace the Code with the following, the webservice stops working:
public class Code{
private final String code;
#JsonCreator
public Code(#JsonProperty("code") String code) {
this.code = code;
}
//Getters omitted
}
What I want is to be able to 1) have immutable objects that can be parsed to/from json and 2) Be able to define something like #RequestBody in Spring MVC for my incoming objects.
Actually this could be pretty easy with Genson. You just need the jar and then configure the Genson feature to use constructors with arguments (if you don't want to put annotations on it).
Genson genson = new GensonBuilder().useConstructorWithArguments(true).create();
// and then register it with jersey
new ResourceConfig().register(new GensonJaxRSFeature().use(genson));
Or you can use JsonProperty on the arguments. See the User Guide for more details.

Parsing nested tags with XStream

I'm using a database API called Socrata to parse information for recycling services. An example of the XML output from this service can be found here:
http://www.datakc.org/api/views/zqwi-c5q3/rows.xml?search=%22computer%22
As you can probably tell, this seems just like bad XML. The problem I'm having is that the tag containing the list of rows is called row (with no attributes) and each row is also called row (with attributes). This seems like it will confuse the hell out of XStream, and I cannot find a way at all to handle this data with XStream.
Any of you XStream/XML gurus out there know what I can do?
The solution wasn't very intuitive but I managed to figure it out. First I had to declare a class that represented the response tag. This class also contains a container of a list of recycle services. Here's how the class looks:
#XStreamAlias("response")
public class QueryResponse {
#XStreamAlias("row")
private RecycleServices services;
public RecycleServices getServices() {
return services;
}
public void setServices(RecycleServices services) {
this.services = services;
}
}
The RecycleServices class is the real trick here, which wraps an implicit List of RecycleService classes.
#XStreamAlias("row")
public class RecycleServices {
#XStreamImplicit(itemFieldName = "row")
private List<RecycleService> services = new ArrayList<RecycleService>();
public List<RecycleService> getServices() {
return services;
}
public void setServices(List<RecycleService> services) {
this.services = services;
}
}
The RecycleService class was then just a straight representation of each recycle service row, and is not really relevant to the answer of this question. I had some frustration figuring this out and I hope that this helps someone out there.
This is more a workaround than a solution, but the row/element naming would be surmountable by using XSLT to rewrite the DOM to something XStream would be better able to consume.

Patterns: Populate instance from Parameters and export it to XML

I'm building a simple RESTFul Service; and for achieve that I need two tasks:
Get an instance of my resource (i.e Book) from request parameters, so I can get that instance to be persisted
Build an XML document from that instance to send the representation to the clients
Right now, I'm doing both things in my POJO class:
public class Book implements Serializable {
private Long id;
public Book(Form form) {
//Initializing attributes
id = Long.parseLong(form.getFirstValue(Book.CODE_ELEMENT));
}
public Element toXml(Document document) {
// Getting an XML Representation of the Book
Element bookElement = document.createElement(BOOK_ELEMENT);
}
I've remembered an OO principle that said that behavior should be where the data is, but now my POJO depends from Request and XML API's and that doesn't feels right (also, that class has persistence anotations)
Is there any standard approach/pattern to solve that issue?
EDIT:
The libraries i'm using are Restlets and Objectify.
I agree with you when you say that the behavior should be where the data is. But at the same time, as you say I just don't feel confortable polluting a POJO interface with specific methods used for serialization means (which can grow considerably depending on the way you want to do it - JSON, XML, etc.).
1) Build an XML document from that instance to send the representation to the clients
In order to decouple the object from serialization logic, I would adopt the Strategy Pattern:
interface BookSerializerStrategy {
String serialize(Book book);
}
public class XmlBookSerializerStrategy implements BookSerializerStrategy {
public String serialize(Book book) {
// Do something to serialize your book.
}
}
public class JsonBookSerializerStrategy implements BookSerializerStrategy {
public String serialize(Book book) {
// Do something to serialize your book.
}
}
You POJO interface would become:
public class Book implements Serializable {
private Long id;
private BookSerializerStrategy serializer
public String serialize() {
return serializer.serialize(this);
}
public void setSerializer(BookSerializerStrategy serializer) {
this.serializer = serializer;
}
}
Using this approach you will be able to isolate the serialization logic in just one place and wouldn't pollute your POJO with that. Additionally, returning a String I won't need to couple you POJO with classes Document and Element.
2) Get an instance of my resource (i.e Book) from request parameters, so I can get that instance to be persisted
To find a pattern to handle the deserialization is more complex in my opinion. I really don't see a better way than to create a Factory with static methods in order to remove this logic from your POJO.
Another approach to answer your two questions would be something like JAXB uses: two different objects, an Unmarshaller in charge of deserialization and a Marshaller for serialization. Since Java 1.6, JAXB comes by default with JDK.
Finally, those are just suggestions. I've become really interested in your question actually and curious about other possible solutions.
Are you using Spring, or any other framework, in your project? If you used Spring, it would take care of serialization for you, as well as assigning request params to method params (parsing as needed).

Categories