Jersey RESTful Framework with Forms

I needed a RESTful service from which a variety of disparate apps and systems can submit to in order to create a new user. The basic flow will be for a user to fill out an HTML Form, and have the data sent to my service.

I have used the Jersey RESTful Framework for quite some time now, I and like its simple, intuitive API. I had not used Jersey as an endpoint for Form submissions, but I know other frameworks have this features, and some simple searching showed that Jersey supports Forms as well.

@Path("/user")
public class UserRestService extends AbstractSpringRestAware {

    UserService userService;

    public UserRestService(){
        userService = (UserService) context.getBean("userService");
    }

    @POST
    @Path("create")
    @Consumes(MediaType.APPLICATION_FORM_URLENCODED)
    public Response createUser(@FormParam("userId") String userId,
            @FormParam("password") String password, @FormParam("firstName") String firstName,
            @FormParam("lastName") String lastName, @FormParam("email") String email, 
            @FormParam("phone") String phone, @FormParam("fax") String fax,
            @FormParam("address") String address, @FormParam("city") String city, 
            @FormParam("state") String state, @FormParam("zip") String zip){ 

        if(StringUtils.isBlank(userId) || StringUtils.isBlank(password) 
                || StringUtils.isBlank(password) || StringUtils.isBlank(firstName)
                || StringUtils.isBlank(lastName) || StringUtils.isBlank(phone)
                || StringUtils.isBlank(address) || StringUtils.isBlank(city)
                || StringUtils.isBlank(state) || StringUtils.isBlank(zip)
                || StringUtils.isBlank(email)){

            if(logger.isDebugEnabled()){
                logger.debug("One of the required params was not provided.  userId=" + userId); 
            }

            // 412 - The server does not meet one of the preconditions that the requester put on the request.[2]
            return Response.status(412).entity("One of the required params was not provided.  userId=" + userId).build();
        }

        User existingUser = userService.getUser(userId); 

        if(existingUser != null){

            // 412 - The server does not meet one of the preconditions that the requester put on the request.[2]
            return Response.status(412).entity("userId already exists: " + userId).build();

        } else {

            User u = new User(); 
            u.setUserId(userId);
            u.setPassword(password);

            //set all User attributes

            User u2 = userService.createUser(u);

            if(u2 == null){
                return Response.status(412).entity("User was not created due to unforeseen issues. userId=" + userId).build();
            }

            String userXml = WSUtils.getXmlForObject(u2);

            return Response.status(200).entity(userXml).build();
        }
    }

}

My custom AbstractSpringRestAware class loads my ApplicationContext.xml to inject my services. I need to update this codebase to let Jersey know about spring in the web.xml (com.sun.jersey.spi.spring.container.servlet.SpringServlet) , but I have not completed that task just yet.

public abstract class AbstractSpringRestAware {
    ApplicationContext context = null; 

    public AbstractSpringRestAware(){
        String env = System.getProperty(StaticVars.ENV_VAR); 

        if(env != null && env.equals(StaticVars.TRUE)){
            context = new FileSystemXmlApplicationContext("applicationContext.xml");
        } else {

            //Try-Catch is needed b/c in UAT, the appContext.xml is used, but when testing locally, we want the test-appContext.xml
            try{
                context = new FileSystemXmlApplicationContext("classpath:test-applicationContext.xml");
            } catch(Exception e){
                context = new FileSystemXmlApplicationContext("classpath:applicationContext.xml");
            }
        }
    }
}

My hope was to use Grizzly integrated with Maven to test this feature locally, but I ran into SSL issues on my local machine when trying to save the user, which I have not yet fixed. (Post on local SSL config coming soon, hopefully) That left me with having to deploy the WAR out to our WebSphere environment, and testing the form submission manually. Not a good long-term solution, but it was able to get the other developers something to test against in a timely fashion while I figure out the SSL issues.

I used a few different client frameworks to try and mock the form submission (mainly straight-up URLConnection and Apache HTTPClient), but ran into a multiple issues, and once they were working, it was somewhat messy. My guess is I was doing something wrong with those frameworks, but once I found the JerseyClient API, it was a much easier and cleaner solution in my opinion.

public class TestUserRestService {
    private static final String userCreateUrl = "http://dev.corporation.com/app/rest/user/create"; 
    private static String userId = "testUser_";

    @BeforeTest
    public static void beforeTests(){
            userId = userId + WSUtils.getCurrentDateAndTimeAsString();
    }

    @Test
    public void test_createUser() throws Exception {

        User u = TestData.getTestUser_1(userId); 

        ClientConfig config = new DefaultClientConfig();
        Client client = Client.create(config);
        WebResource webResource = client.resource(userCreateUrl);

        MultivaluedMap<String, String> formData = new MultivaluedMapImpl();
        formData.add("userId", u.getUserId());
        formData.add("password", u.getPassword());

        //set all User data

        ClientResponse response = webResource.type(MediaType.APPLICATION_FORM_URLENCODED_TYPE).post(ClientResponse.class, formData);

        String xml = this.getResponseAsString(response.getEntityInputStream());

        User uFromXml = (User) WSUtils.getObjectFromXml(xml); 

        Assert.assertNotNull(uFromXml); 
        Assert.assertEquals(u.getUserId(), uFromXml.getUserId()); 

        //assert all User values were saved

    }
}