开发者

Unit testing controllers with annotations

I'm trying to write some unit tests for my controllers in a Spring MVC web app. I have already got a fairly comprehensive set of unit tests for the domain model, but for completeness I want to test the controllers too.

The issue I'm facing is trying to test them without loading a Spring context. I thought I could get around this with mocking, but the method in the controller has a @Transactional annotation which attempts to open a transaction (and fails with a NullPointerException because no Spring context is loaded).

Code example:

public class UsersController {

  @Autowired private UserManager userManager;

  @Transactional
  @RequestMapping(method = RequestMethod.POST)
  public ModelAndView create(User user) {

    userManager.save(user);

    ModalAndView mav = new ModelAnd开发者_JAVA技巧View();    
    mav.addObject("user", user);
    mav.setViewName("users/view");
    return mav;
  }

}

So essentially I want to test the behaviour without loading a context and actually persisting the user.

Does anyone have any ideas on how I can achieve this?

Cheers,

Caps


I'd say mocking is the way to go here. The @Transactional annotation will have no effect unless there is a Spring context loaded and instructed to configure annotation-based transactions.

Make sure that you aren't instructing JUnit to run your test within a spring context by specifying something like:

@ContextConfiguration(locations = "classpath:spring/ITestAssembly.xml")
@RunWith(SpringJUnit4ClassRunner.class)

To prevent confusion, I keep my unit tests (not running in a spring context) in separate files than my integration tests. Typically all mocking occurs in the unit tests and not in integration tests.


The NullPointerException occurs not because of the Transactional, but because nothing gets injectedas UserManager. You have two options:

  • run with the spring test runner
  • mock the userManager and set it.
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜