Thursday November 15, 2007
Go Light with Apache Struts 2 and REST by Don Brown After attending Dan's talk on REST, I stayed in the same room and listened to Don Brown talk about Struts 2's support for building RESTful applications. Below are my notes from the event.
What is wrong with today's web applications? You're using a modern web framework and you've cleanly separated your presentation and business logic. The biggest problem in modern web applications is Confusing URLs.
A URL should be a resource indicator - not a method invocation. Often, web applications have little or no caching. People use GET to perform data manipulation and POST may or may not change state (especially with JSF). Another big issue with modern web frameworks is there's too many abstraction layers that hide HTTP headers and it's difficult to manipulate them.
Today's applications are "information silos". There's a lot of information in your applications, but it's all buried in HTML, JavaScript and CSS. There's no way to get this information out of your application unless you explicitly expose it.
The answer to many of these problem is REST. It's the Way of the Web. To solve the information silo problem, you can create a single interface that has multiple representation of the same resource. There's one URI for all types of resources - be it XML, JSON or HTML. How does this work w/o modifying the URL? You modify the URL's extension.
Struts 2 has a couple of plugins that make developing RESTful services easier. The first is the Codebehind plugin and the 2nd is the REST plugin. Don is doing a demo with the REST plugin and shows that there's no Struts configuration files needed (no struts.xml and no struts.properties). The only thing that's necessary is to specify an "actionPackages" init-param on the DispatcherFilter in web.xml. This activates the Codebehind plugin that uses conventions to determine the view template's path.
In Don's demo, he's creating an "OrdersController" that implements ModelDriven. After implementing a setId() method (to set the id from the request parameters), a getModel() method (to return the Order object) and implementing a show() method that returns HttpHeaders, Don starts up his server and shows that http://localhost:8080/order/5 returns an HTML page. Changing the URL to end in /5.json returns JSON, /5.xml returns XML.
public HttpHeaders create() {
service.save(order);
return new DefaultHttpHeaders("success").setLocationId(order.getId());
}
The Poster Plugin for Firefox is great when you're working with REST services. Don used this plugin to show us that it's possible to post to JSON and get back JSON results. His demo was impressive, especially the fact that there was no XML configuration required for Struts. I also like how the DefaultHttpHeaders class allows you to manipulate headers in a type-safe manner.
To use the REST plugin, you'll want to use Struts 2.1. If you're using Maven, all you need to depend on is struts-rest-plugin. The struts-codebehind-plugin (as well as struts-core) will be pulled in by transitive dependencies.
One disadvantage of REST vs. WS-* is you can't generate client code from a WSDL. You'll have to write your client by hand. However, one advantage of REST is there's already lots of clients - your browser, curl, etc.
The Struts REST Plugin hasn't been officially released, but hopefully will be in Struts 2.1.1. You can checkout the code from SVN using the URL below. The documentation is located here.
http://svn.apache.org/repos/asf/struts/struts2/trunk/plugins/rest
Great talk Don - and excellent work on the REST plugin for Struts. I can't wait to try it out. Posted in Java at Nov 15 2007, 06:12:58 PM MST 12 Comments
Search This Site
Recent Entries
- New Passport in 9 Days
- EhCache Project Busy this Summer
- Spontaneous Stuff Weekend
- Awesome Birthday Present: A Kegerator
- Maven Plugin for Running Integration Tests against Multiple Containers
- Presenting Web Frameworks of the Future Tomorrow in Denver
- My OSCON Aftermath
- OSCON 2008 Wrapup
- [OSCON 2008] Even Faster Web Sites by Steve Souders
- [OSCON 2008] CSS for High Performance JavaScript UI by Gavin Doughtie
Posted by Don Brown on November 16, 2007 at 08:51 AM MST #
Thanks for this post. I was looking for similiar concept and yet use struts.
Many times, i thought, i should stick with vanilla jsp app. (basically MVC 1 model :) )
Posted by ashish jain on November 16, 2007 at 09:30 AM MST #
Posted by me on November 16, 2007 at 12:22 PM MST #
Posted by Stefan Tilkov's Random Stuff on November 16, 2007 at 12:38 PM MST #
- Improper use of GET - breaks cache proxies.
- URI's should describe resources, not methods to call. This breaks user expectations and usually results in an explosion of URLs, increasing the surface area of your application.
- Extra, useless characters in the URL - not a big issue, but makes your app look sloppy, as URLs are bookmarked and sent around via email, IM, etc.
- Improper use of query parameters - required identifying information should be in the URI, again affects caching by proxies
The bottom line is at the center of your application are your URLs, so it isn't about easing application development, but your users. More consistent, properly behaved URLs make an application easier to use and open the door for nice features like multiple representation types down the road. Web applications are built on HTTP and it is about time they stop abusing it.Posted by Don Brown on November 16, 2007 at 01:03 PM MST #
Posted by Don Brown on November 16, 2007 at 01:06 PM MST #
"Confusing URLs are hardly the 'biggest problem in modern web applications'. "
They are in Java. They indicate badly designed frameworks in the same way doing evrything through managers indicate badly designed middlware.
Frankly, web architecture seems lost on most Java devs, so let me put in terms you might actually understand: make your URLs object-oriented. And prepare to be unpleasantly surprised at how difficult that can be in Javaland.
http://www.dehora.net/journal/2007/07/struts_1_problems.html
read down the section called "Conceptual mismatch with the Web". This mismatch problem extends to the servlets spec itself.
Posted by Bill de hOra on November 16, 2007 at 02:35 PM MST #
Posted by Thiago HP on December 12, 2007 at 09:32 AM MST #
Posted by Nicola on March 18, 2008 at 11:45 AM MDT #
Posted by Mike W on May 18, 2008 at 03:43 PM MDT #
Posted by Matt Raible on May 28, 2008 at 09:22 PM MDT #
Posted by deebak on July 23, 2008 at 06:26 AM MDT #