2012-12-20 94 views
2

我正在運行單元測試並使用Service類來執行某些業務邏輯。然而,單元測試沒有說服務類是無效的,爲它設置Autorwire註釋。Spring autowire問題

下面

是我的單元測試:

@RunWith(SpringJUnit4ClassRunner.class) 
@ContextConfiguration(locations = { "file:src/main/webapp/WEB-INF/FreedomSpring-servlet.xml" }) 
public class UserControllerTest 
{ 
    private UserController controller; 

    @Inject 
    private ApplicationContext applicationContext; 

    private String jsonUser = "{ \"username\":\"jonneymendoza\",\"emailAddress\":\"[email protected]\", \"password\":\"12345678\",\"firstName\":\"jono\", \"surname\":\"richy\", \"country\":\"united kingdom\",\"bio\":\"Bio stuff goes here about the user. where he comes from etc etc. all is well. lets go go go\" }"; 

    @Before 
    public void setup() 
    { 
     controller = new UserController(); 

     assertNotNull(applicationContext); 
    } 

    @Test 
    public void testCreateNewAccount() 
    { 
     ResponseEntity<String> response = controller 
              .createNewAccount(new HttpEntity<String>(jsonUser)); 
     assertEquals(HttpStatus.CREATED, response.getStatusCode()); 
    } 
} 

這裏是控制器我測試

@Controller 
public class UserController 
{ 
    @Autowired 
    private UserService userService; 

    @RequestMapping(value = "/user", method = RequestMethod.PUT, consumes = "application/json") 
    public ResponseEntity<String>createNewAccount(HttpEntity<String>request) 
    { 
     userService.registerNewUser(JSONObject.fromObject(request.getBody())); //fails here 

     return new ResponseEntity<String>(null, responseHeaders, HttpStatus.CREATED); 
    } 
} 

服務類:

@Service("UserService") 
@Transactional 
public class UserService implements UserServiceInterface 
{ 
    @Override 
    public void registerNewUser(JSONObject user) throws InvalidDataException, JSONException 
    { 
     // parse json object to a User object 
     User newUser = parseJsonObject(user); 

     UserDao userDao = new UserDao(); 

     userDao.addNewUser(newUser); 
    } 
} 

我的服務-config.xml中

<?xml version="1.0" encoding="UTF-8"?> 
<beans xmlns="http://www.springframework.org/schema/beans" 
    xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:context="http://www.springframework.org/schema/context" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation=" 
     http://www.springframework.org/schema/beans 
     http://www.springframework.org/schema/beans/spring-beans-3.1.xsd 
     http://www.springframework.org/schema/mvc 
     http://www.springframework.org/schema/mvc/spring-mvc-3.1.xsd 
     http://www.springframework.org/schema/context 
     http://www.springframework.org/schema/context/spring-context-3.1.xsd"> 

    <context:annotation-config /> 

    <!-- Define services here --> 

    <bean id="UserService" class="com.jr.freedom.user.UserService"></bean> 
</beans> 

我servlett:

<?xml version="1.0" encoding="UTF-8"?> 
<beans xmlns="http://www.springframework.org/schema/beans" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" 
    xsi:schemaLocation=" 
     http://www.springframework.org/schema/beans  
     http://www.springframework.org/schema/beans/spring-beans-3.1.xsd 
     http://www.springframework.org/schema/context 
     http://www.springframework.org/schema/context/spring-context-3.1.xsd"> 

    <bean id="propertyConfigurer" 
     class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer"> 
     <property name="locations"> 
      <list> 
       <value>database.properties</value> 
      </list> 
     </property> 
    </bean> 

    <import resource="mvc-config.xml" /> 

    <import resource="service-config.xml" /> 

    <import resource="classpath:datasource-config.xml" /> 

    <bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping" /> 

    <!-- Resolves views selected for rendering by @Controllers to .jsp resources 
     in the /WEB-INF/views directory --> 
    <bean id="viewResolver" 
     class="org.springframework.web.servlet.view.InternalResourceViewResolver"> 
     <property name="prefix" value="/WEB-INF/views/" /> 
     <property name="suffix" value=".jsp" /> 
    </bean> 

    <bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" /> 

    <context:component-scan base-package="com.jr.freedom.controllers"></context:component-scan> 
</beans> 

最後的錯誤我收到

java.lang.NullPointerException 
    at com.jr.freedom.controllers.UserController.createNewAccount(UserController.java:56) 
    at com.jr.freedom.controllers.UserControllerTest.testCreateNewAccount(UserControllerTest.java:51) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
    at java.lang.reflect.Method.invoke(Method.java:597) 
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:45) 
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15) 
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:42) 
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20) 
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28) 
    at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:74) 
    at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:83) 
    at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:72) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:231) 
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:47) 
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:231) 
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:60) 
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:229) 
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:50) 
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:222) 
    at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61) 
    at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:71) 
    at org.junit.runners.ParentRunner.run(ParentRunner.java:300) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:174) 
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50) 
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197) 
+1

您需要使用應用程序上下文來獲取服務和/或控制器的實例。如果你像你一樣調用構造函數,沒有什麼特別的事情會發生。 –

+0

忘記Spring bean的新運算符。 – user1516873

回答

3

你需要注入(有一些註釋),或在ApplicationContext中retreive UserController中,這樣神奇的春天(即注入或userService在你的情況)工程。

@RunWith(SpringJUnit4ClassRunner.class) 
@ContextConfiguration(locations = { "file:src/main/webapp/WEB-INF/FreedomSpring-servlet.xml" }) 
public class UserControllerTest { 

@Autowired 
private UserController userController; 

@Inject 
private ApplicationContext applicationContext; 

private String jsonUser = "{ \"username\":\"jonneymendoza\",\"emailAddress\":\"[email protected]\", \"password\":\"12345678\",\"firstName\":\"jono\", \"surname\":\"richy\", \"country\":\"united kingdom\",\"bio\":\"Bio stuff goes here about the user. where he comes from etc etc. all is well. lets go go go\" }"; 

@Before 
public void setup() { 
    assertNotNull(applicationContext); 
    assertNotNull(userController); 

} 
+0

看起來像它的工作!我所做的只是將AutoWired添加到我的控制器,如上所示它修復了空指針。奇怪,因爲在我的設置方法上,我創建了一個控制器對象 – jonney

+0

當您手動創建控制器對象時(即調用新的Controller()):Spring不會正確設置對象。另一方面,當你要求Spring注入bean時:Spring會安裝它並執行設置(即查看所有需要注入的bean域並執行此注入。 – ben75