Using Betwixt, Struts and REST

My latest project at work launched a couple weeks ago, unfortunately there isn’t much to look at, but it’s not like I’m a Flash developer, so unless I start writing Windows apps, no one will ever be able to see my work anyway. Alas, a major portion of the project involved consolidating some business logic behind a SOAP API (I’ll go into that some other time). We were supposed to be moving our front end to ASP.NET but at the last minute, the ASP.NET migration didn’t happen so we ended up needing something that ASP could use as well, which meant REST. With the business logic wrapped up behind business delegates, all that was needed as a Servlet Filter to map requests for /myapp/xml to a Struts Action class, which invoked the business delegates and then returned XML to the client. Now on the SOAP end of things (Axis embedded in Tomcat), I didn’t have to deal with XML (Axis handles all the XML serialization and deserialization). But with REST you’re in conundrum: do you create toXML() methods on all of your JavaBeans? do you put the JavaBean or collection of beans in the Request scope and then generate the XML using JSP? Those options all seemed error prone and harder to test. I looked at JAXB (makes more sense when you have XML that you want to turn into a JavaBean) and Castor (same thing) but finally decided on using Betwixt, a Jakarta Commons library that provide a simple way of turning a JavaBean into XML. The end result looked something like this:

public class RESTAction extends DispatchAction {
  public ActionForward doSomething(...) {
    MyBean bean = BusinessLogic.getBean();
    response.setContentType("text/xml");
    OutputStream sos = response.getOutputStream();
    BeanWriter beanWriter = new BeanWriter(sos);
    BindingConfiguration config = beanWriter.getBindingConfiguration();
    config.setMapIDs(false);
    beanWriter.enablePrettyPrint();
    String declr = "<?xml version='1.0' encoding='UTF-8' ?>";
    beanWriter.writeXmlDeclaration(declr);
    beanWriter.write("mybean", bean);
    beanWriter.flush();
    beanWriter.close();
    return null;
  }
}

which when combined with this action mapping:

<action
  path="/xml"
  type="com.mycompany.web.actions.RESTAction"
  name="xmlForm"
  scope="request"
  parameter="method"
  validate="false">
  <forward name="error" path="/WEB-INF/views/xml/error.jsp" />
</action>

is invoked like so:

http://myserver/myapp/xml?method=doSomething

I’m not 100% sold on this as the “way”, but I do like how simple Betwixt is. If you’ve got a different idea, comment away.

6 thoughts on “Using Betwixt, Struts and REST”

  1. Aaron: I’m no RESTian, but what you’ve described above isn’t actually a RESTful implementation.

    For example, your example implies that you can GET the provided URI and, well, “doSomething”. In RESTland, GET should *never* do anything ‘cept return a message. It should have zero effect on the state of any server-bound data.

    If I’ve misunderstood, or inferred too much from the example, my apologies in advance.

  2. Hi, have you experience with betwixt? I’m trying to convert an XML to an array of beans. Do you know how to do that?

    Tks

Leave a Reply

Your email address will not be published. Required fields are marked *