Unit Testing Backing Beans with Mock dependencies
ranganathkini Feb 20, 2009 12:26 PMI work on a project which uses JSF (MyFaces) + Facelets, Spring Framework, Hibernate. I am writing JUnit test cases for testing the DAO and Service layers implemented as POJOs and integrated via Spring. Accidentally my team has coded a large amount of business logic into the backing beans which now requires us to write unit tests for the backing beans. The Service layer components are plugged into the Backing Beans via Spring's DelegatingVariableResolver configured in my faces-config.xml.
// Code in setUp() JSFSession session = new JSFSession("/login.jsf"); client = session.getJSFClientSession(); server = session.getJSFServerSession(); // code in some test method server.getFacesContext().getApplication().setVariableResolver( new VariableResolver() { public Object resolveVariable(FacesContext fcxt, String var) { PersonService ps = EasyMock.createStrictMock(PersonService.class); EasyMock.expect(ps.authenticate("johndoe", "secretpassword")) .andReturn(true).once(); EasyMock.replay(ps); return ps; } } ); client.setValue("loginForm:userName", "johndoe"); client.setValue("loginForm:password", "johndoe"); client.click("loginForm:loginButton");
As you can see, I have setup the objects to be mocked, after the initial page request to the login.jsf. Which means that the initialization of the backing bean has taken place. It seems to be working pretty well for now. But I have a scenario where I want to mock a dependency at the time when the backing bean needs to initialize. For example, say in my faces-config.xml I have this:
<managed-bean> <managed-bean-name>myBackingBean</managed-bean-name> <managed-bean-class>com.foo.MyBackingBean</managed-bean-class> <managed-bean-scope>request</managed-bean-scope> <managed-property> <property-name>personService</property-name> <value>#{personService}</value> </managed-property> <managed-property> <property-name>initialized</property-name> <value>true</value> </managed-property> </managed-bean>
And here is the backing bean code.
public class MyBackingBean { // the dependency I need to mock private PersonService personService; public MyBackingBean() { } public void setPersonService(PersonService ps) { personService = ps; } public void setInitialized() { // call to the dependency ps.doSomeImportantInitialization(); } // other methods of the backing beans }
I want to be able to mock PersonService here, i.e. the one which the backing bean will call at the time of initialization. How can I do this as I have access to the FacesContext via JSFServerSession only after the request is made. How can I do this with JSFUnit?