Reputation: 21924
I am early on in a REST implementation and have recently learned that we could be putting our JAX-RS annotations on our Java service interfaces rather than the class implementations.
To me it seems like this could result in a clean class file, but might also result in developers have to constantly muddle between files.
What are the pros and cons of each approach?
Upvotes: 13
Views: 6863
Reputation: 11841
I had a similar question when using JAX-RS with JAX-B. My hope was to use JAX-B annotations on interfaces not classes. This doesn't work as I expected, the reason is due to the unmarshaller. To solve my issues, I ended up using classes. Here is a description of why and what I found.
Upvotes: 2
Reputation: 1202
I think I have to respectfully partially disagree with Blessed Geek here. What is mentioned is a very specific use case which requires the usage of annotations on the interface.
In my own experience, I have encountered cases where the framework either by design or by bug does not respond properly to placing annotations on the interface. For example, Apache CXF does not properly process @PUT requests with @PathParams defined in the path when you place the annotations on the interface. Don't ask me why. CXF is not alone in this; Spring Security suffers from similar limitations in placing annotations on interfaces. So this is a counterpoint to the one mentioned above.
In cases where you are free to choose where to place the annotations, I would urge you to consider what makes sense from a standpoint of intention, design, and ease of development.
As a philosophical argument, some folks say that placing annotations on interfaces is another form of contract programming- you are saying that implementations will abide by certain rules.
The other side of that coin (depending on your definition of interfaces) is that interfaces should not care about what steps their implementors take in achieving the goal defined in the method contract. For example, why place a @Transactional annotation on an interface when you might have two implementations, one of which has no idea what a "transaction" might be?
In practice, the lines blur. In the case of defining a restful endpoint, you may prefer to place the proper annotations on the interface. I think this makes sense in most cases; you probably won't have multiple implementations where the same method signature responds to different HTTP verbs. However you could come up with a situation where different implementations prefer to consume and produce different media types.
So, the big idea here is "it depends." But hopefully this is some food for thought for those who may stumble upon this question.
Upvotes: 7
Reputation: 21674
You should put it in an interface. Rather, my practice requires me to put it into an interface, because my client and server sides are sharing the same jax-rs definition.
I am inclined to use jax-rs for REST-RPC.
The reason for REST is to allow an web service URL API to be serviceable and "clientable" by any programming framework.
The use of jax-rs restricts us to using java on the server side.
The use of jax-rs for REST-RPC restricts us to using java on both server and client sides.
What is REST-RPC?
In a not too convoluted attitude of explanation, RPC is a way of calling a function/method on the client, which when sent over the wire is serviced by the server such that the same function/method exists on the server side.
RestEasy allows you to use the jax-rs definition on the client-side to call the same function serviced on the server side.
RestyGWT, too, with some modification to the interface to specify a callback method would allow you to (somewhat) use the jax-rs definition on both client and server side. You simply have to write a script to move the return type to the type argument of the callback method.
You might question why restrict ourselves to performing java on both sides? Would that not defeat one of the purposes in life of REST? I think jax-rs REST-RPC is a convenient route to implementing and testing a jax-rs service. If you wanted to implement a jax-rs service, you probably would do it initially in Java on both sides anyway. And then when your service gets off the ground, you could start writing PHP or python clients.
Writing your jax-rs in interface files would allow you to publish your interface for client side operations. This is especially true for REST-RPC. However, you could run enunciate over your jax-rs definition to publish your web service API to non-java programmers.
I have some ongoing rambling on this subject... http://h2g2java.blessedgeek.com/2011/11/gwt-with-jax-rs-aka-rpcrest-part-0.html.
Upvotes: 10