14
votes

I have a bunch of servlets running under the Tomcat servlet container. I would like to separate test code from production code, so I considered using a test framework. JUnit is nicely integrated into Eclipse, but I failed to make it run servlets using a running Tomcat server. Could you please recommend a unit testing framework that supports testing Tomcat servlets? Eclipse integration is nice but not necessary.

6
I use jUnit to launch a Jetty servlet container Before and turn if off After.Lee Goddard

6 Answers

9
votes

Check out ServletUnit, which is part of HttpUnit. In a nutshell, ServletUnit provides a library of mocks and utilities you can use in ordinary JUnit tests to mock out a servlet container and other servlet-related objects like request and response objects. The link above contains examples.

6
votes

The Spring Framework has nice ready made mock objects for several classes out of the Servlet API:

http://static.springframework.org/spring/docs/2.5.x/api/org/springframework/mock/web/package-summary.html

5
votes

Okay. Ignoring the 'tomcat' bit and coding to the servlet, your best bet is to create mocks for the response and request objects, and then tell it what you expect out of it.

So for a standard empty doPost, and using EasyMock, you'll have

public void testPost() {
   mockRequest = createMock(HttpServletRequest.class);
   mockResponse = createMock(HttpServletResponse.class);
   replay(mockRequest, mockResponse);
   myServlet.doPost(mockRequest, mockResponse);
   verify(mockRequest, mockResponse);
}

Then start adding code to the doPost. The mocks will fail because they have no expectations, and then you can set up the expectations from there.

Note that if you want to use EasyMock with classes, you'll have to use the EasyMock class extension library. But it'll work the same way from then on.

2
votes

Separate the parts of that code that deal with HTTP requests and response from the parts that do business logic or data-base manipulation. In most cases this will produce a three tier architecture, with a data-layer (for the data-base/persistence), service-layer (for the business logic) and a presentation-layer (for the HTTP requests and responses).

  1. You can unit test the first two layers without any servlet stuff at all; it will be easier to test that way.
  2. You can test the presentation layer, as others suggest, using mock HTTP request and response objects.
  3. Finally, if you feel it really is necessary, you can do integration tests using a too such as HtmlUnit or JWebUnit .
1
votes

For "in-container" testing, have a look at Cactus

If you want to be able to test without a running container you can either simulate its components with your own mockobjects (e.g. with EasyMock) or you could try MockRunner which has "pre-defined" Stubs for testing servlets, jdbc-connections etc.

0
votes

Updated Feb 2018: OpenBrace Limited has closed down, and its ObMimic product is no longer supported.

If you want a newer alternative to ServletUnit for JUnit testing of Servlets, you might find my company's ObMimic library useful. It's available for free from the website's downloads page.

As with ServletUnit, it provides a library of classes that you can use in normal JUnit or TestNG tests outside of any servlet container to simulate the Servlet API.

Its Servlet API objects have no-argument constructors, are fully configurable and inspectable for all relevant Servlet API data and settings, and provide a complete simulation of all of the behaviour specified by the Servlet API's javadoc. To help with testing there's support for selective recording of Servlet API calls, control over any container-dependent behaviour, checks for any ambiguous calls (i.e. where the Servlet API behavour isn't fully defined), and an in-memory JNDI simulation for any servlet code that relies on JNDI lookups.

For full details, example code, "how to" guides, Javadoc etc, see the website.