Java Dev
Java Dev

Reputation: 21

How to use session in unit test?

I have a spring service method that gets an object stored in the session (using FacesContext) as follows:

(MyObject)((HttpServletRequest) FacesContext
                .getCurrentInstance().getExternalContext().getRequest())
                .getSession().getAttribute("myObject");

and I would like to put that object in session in unit test before invoking the method.

so i tried the solution in this post:

Spring Test session scope bean using Junit

and in my test method i put the object in session before calling the service, but the service throws an exception when trying to get the object from the session, i guess that this is because the facescontext is not available, what do you think ?

I am using Spring, Junit, JSF2, please advise, thanks.

Upvotes: 2

Views: 11265

Answers (3)

MariuszS
MariuszS

Reputation: 31587

With Spring 3.2 this is very easier

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(...)
@WebAppConfiguration
public class SessionTest {

    @Autowired
    MockHttpSession session;


    @Test
    public void sessionAttributeTest() throws Exception {

        MyObject myObject = session.getAttribute("myObject");
        ...

    }
}

More information: Request and Session Scoped Beans

Upvotes: 2

Aaron Digulla
Aaron Digulla

Reputation: 328624

Add spring-mock to your test classpath which gives you org.springframework.mock.web.MockHttpSession. This is a pretty simple implementation that you can create with new without a Java EE container.

The JAR also contains mocks for requests, responses and everything else.

Another solution is to use MockRunner which does the same.

Upvotes: 0

JB Nizet
JB Nizet

Reputation: 691785

I'm assuming that you're talking about HttpSession.

Create a mock session, tell the mock session to always return this object when its getAttribute method is called with the name used by the object under test, and pass this mock session rather than a real one to the object under test.

Mocking APIs such as Mockito or EasyMock will help doing that.

EDIT: Suppose the method you want to test looks like this:

public String foo() {
    // some lines of code
    MyObject o = 
        (MyObject)((HttpServletRequest) FacesContext
             .getCurrentInstance().getExternalContext().getRequest())
             .getSession().getAttribute("myObject");
    // some more lines of code, using o.
}

You could refactor it like this:

public String foo() {
    // some lines of code
    MyObject o = getMyObjectFromSession();
    // some more lines of code, using o.
}

protected MyObject getMyObjectFromSession() {
    return (MyObject)((HttpServletRequest) FacesContext
             .getCurrentInstance().getExternalContext().getRequest())
             .getSession().getAttribute("myObject");
}

And you could then use a mocking framework to do something like this (pseudo-code):

// mockFoobar is the object to test. We just mock its getMyObjectFromSession method
FooBar mockFoobar = mock(Foobar.class);
MyObject objectInSession = new MyObject();
when(mockFoobar.getMyObjectFromSession()).thenReturn(objectInSession);

String s = mockFoobar.foo();
assertEquals("expected result", s);

Upvotes: 1

Related Questions