2012-05-15 61 views
4

为我的弹簧应用程序编写Junit测试。因为我是新手,所以我尝试着写一个我熟知的DAO类的单元测试(在JBoss中运行它)。但是,我无法将它作为Eclipse中的单元测试工作。我一直收到“创建bean时出错...无法自动装入字段:NoSuchBeanDefinition”自动装配失败,弹簧Junit测试

我在StackOverflow和其他网站上看到类似这样的错误,它总是以语法错误或尝试自动调用接口的实现而不是接口等等。我没有看到任何这些错误用我的代码。

我没有从该项目附带的Spring配置中单独下载Spring-test.jar。两者都是由春2.5然而,所以我不认为这应该是一个问题:/

Eclipse附带使用JUnit 4.8和Spring单元测试捆绑不与,所以我降级我的JUnit使用工作4.4

有一件事要考虑......如果你看看我的单元测试的代码,你会注意到我自动装配了两个字段:我想测试的查询服务中的一个SimpleJdbcTemplate。那么如果我删除DrugDao和所有对它的引用,那么SimpleJdbcQuery自动连线就好了。

这里是您的评论的堆栈跟踪:

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'tst.hcps.glucosemanagement.dataaccess.DrugDaoTest': Autowiring of fields failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: com.hcps.glucosemanagement.repository.meds.DrugDao tst.hcps.glucosemanagement.dataaccess.DrugDaoTest.dQuery; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [com.hcps.glucosemanagement.repository.meds.DrugDao] is defined: Unsatisfied dependency of type [interface com.hcps.glucosemanagement.repository.meds.DrugDao]: expected at least 1 matching bean 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessAfterInstantiation(AutowiredAnnotationBeanPostProcessor.java:243) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:959) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireBeanProperties(AbstractAutowireCapableBeanFactory.java:329) 
    at org.springframework.test.context.support.DependencyInjectionTestExecutionListener.injectDependencies(DependencyInjectionTestExecutionListener.java:127) 
    at org.springframework.test.context.support.DependencyInjectionTestExecutionListener.prepareTestInstance(DependencyInjectionTestExecutionListener.java:85) 
    at org.springframework.test.context.TestContextManager.prepareTestInstance(TestContextManager.java:231) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.createTest(SpringJUnit4ClassRunner.java:95) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.invokeTestMethod(SpringJUnit4ClassRunner.java:139) 
    at org.junit.internal.runners.JUnit4ClassRunner.runMethods(JUnit4ClassRunner.java:51) 
    at org.junit.internal.runners.JUnit4ClassRunner$1.run(JUnit4ClassRunner.java:44) 
    at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:27) 
    at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:37) 
    at org.junit.internal.runners.JUnit4ClassRunner.run(JUnit4ClassRunner.java:42) 
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:49) 
    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) 
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire field: com.hcps.glucosemanagement.repository.meds.DrugDao tst.hcps.glucosemanagement.dataaccess.DrugDaoTest.dQuery; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [com.hcps.glucosemanagement.repository.meds.DrugDao] is defined: Unsatisfied dependency of type [interface com.hcps.glucosemanagement.repository.meds.DrugDao]: expected at least 1 matching bean 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:435) 
    at org.springframework.beans.factory.annotation.InjectionMetadata.injectFields(InjectionMetadata.java:105) 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessAfterInstantiation(AutowiredAnnotationBeanPostProcessor.java:240) 
    ... 18 more 
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [com.hcps.glucosemanagement.repository.meds.DrugDao] is defined: Unsatisfied dependency of type [interface com.hcps.glucosemanagement.repository.meds.DrugDao]: expected at least 1 matching bean 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:613) 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:412) 
    ... 20 more 

这里是接口和实现:

DrugDao.java

package com.hcps.glucosemanagement.repository.meds; 

import java.util.List; 

import com.hcps.glucosemanagement.domain.meds.Drug; 

public interface DrugDao { 

    public List<Drug> searchDrugsByPrimaryName(String facilityId, String name); 

    public List<Drug> searchDrugs(String facilityId, String primaryName, String secondaryName); 

} 

SpringJdbcDrugQuery.java

package com.hcps.glucosemanagement.repository.meds; 

import java.sql.ResultSet; 
import java.sql.SQLException; 
import java.util.HashMap; 
import java.util.List; 

import org.apache.log4j.Logger; 
import org.springframework.dao.EmptyResultDataAccessException; 
import org.springframework.jdbc.core.simple.ParameterizedRowMapper; 
import org.springframework.stereotype.Service; 

import com.hcps.glucosemanagement.domain.meds.Drug; 
import com.hcps.glucosemanagement.repository.DaoOperations; 

@Service 
public class SpringJdbcDrugQuery extends DaoOperations implements DrugDao { 

private static final Logger logger = Logger.getLogger(SpringJdbcDrugQuery.class); 

public List<Drug> searchDrugsByPrimaryName(String facilityId, String name) 
{ 
    return searchDrugs(facilityId, name, null); 
} 

public List<Drug> searchDrugs(String facilityId, String primaryName, String secondaryName) 
{ 
    List<Drug> results = null; 

    StringBuffer sql = new StringBuffer();  
    HashMap<String, Object> namedParameters = new HashMap<String, Object>(); 

    if(primaryName==null) return null; 

    sql = new StringBuffer(); 

    sql.append("SELECT"); 
      ... 
     results = simpleJdbcTemplate.query(sql.toString(), new DrugMapper(), 


    return results; 
} 

private static final class DrugMapper implements ParameterizedRowMapper<Drug> 
{ 

    public Drug mapRow(ResultSet rs, int rowNum) throws SQLException { 
     Drug drug = new Drug(); 
     drug.setFacilityId(rs.getString("FACILITY_ID")); 
     drug.setPrimaryName(rs.getString("PRIMARY_NAME")); 
     drug.setSecondaryName(rs.getString("SEC_NAME")); 
     return drug; 
    } 

} 
} 

DrugDaoTest2.java(位于在第一单独的源文件夹,然后试图在相同的文件夹)

package com.hcps.glucosemanagement.repository.meds; 

import static org.junit.Assert.assertTrue; 

import java.util.List; 

import org.junit.Test; 
import org.junit.runner.RunWith; 
import org.springframework.beans.factory.annotation.Autowired; 
import org.springframework.jdbc.core.simple.SimpleJdbcTemplate; 
import org.springframework.test.context.ContextConfiguration; 
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; 

import com.hcps.glucosemanagement.domain.meds.Drug; 

@RunWith(SpringJUnit4ClassRunner.class) 
@ContextConfiguration(locations={ 
     "classpath:common-test.xml" 
}) 
public class DrugDaoTest2 { 

    @Autowired 
    DrugDao dQuery; 
    @Autowired 
    SimpleJdbcTemplate queryTemplate; 

    @Test public void glucoseFetch() { 
     List<Drug> rslts = dQuery.searchDrugsByPrimaryName(null, "INSU*"); 
     assertTrue(rslts.size()>0); 
     int i=0; 
     System.out.println(i); 

    } 

    public void setDrugDao(DrugDao drugDao) { 
     this.dQuery = drugDao; 
    } 
} 

共的test.xml

<?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:p="http://www.springframework.org/schema/p" 
    xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans-2.5.xsd" 
> 

    <!-- 
    Test configuration for Spring/JUnit Testing 
    --> 

    <bean id="contextApplicationContextProvider" class="com.hcps.glucosemanagement.spring.ApplicationContextProvider" /> 

    <bean id="jmxExporter" class="org.springframework.jmx.export.MBeanExporter" lazy-init="false"> 
    <property name="beans"> 
     <map> 
     <entry key="bean:name=Log4jJmxServiceMBean" value-ref="glucosemanagement.Log4jJmxService" /> 
     </map> 
    </property> 
    </bean> 
    <bean id="glucosemanagement.Log4jJmxService" class="com.hcps.glucosemanagement.logging.Log4jJmxService" /> 

    <bean id="messageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource"> 
    <property name="basename" value="/WEB-INF/messages" /> 
    </bean> 

    <bean id="parameterMappingInterceptor" class="org.springframework.web.portlet.handler.ParameterMappingInterceptor" /> 
    <bean id="viewResolverCommon" class="org.springframework.web.servlet.view.InternalResourceViewResolver" 
    p:order="2" 
    p:cache="false" 
    p:viewClass="org.springframework.web.servlet.view.JstlView" 
    p:prefix="/WEB-INF/jsp/" 
    p:suffix=".jsp" 
    /> 

    <bean id="defaultExceptionHandler" class="org.springframework.web.portlet.handler.SimpleMappingExceptionResolver"> 
    <property name="defaultErrorView" value="../error"/> 
    <property name="exceptionMappings"> 
     <props> 
     <prop key="javax.portlet.PortletSecurityException">notAuthorized</prop> 
     <prop key="javax.portlet.UnavailableException">notAvailable</prop> 
     </props> 
    </property> 
    </bean> 

    <bean id="simpleParameterJdbcTemplate" class="org.springframework.jdbc.core.simple.SimpleJdbcTemplate"> 
    <constructor-arg ref="hciDataSource" /> 
    </bean> 

    <bean id="hciDataSource" class="org.apache.commons.dbcp.BasicDataSource"> 
    <property name="driverClassName" value="oracle.jdbc.driver.OracleDriver" /> 
    <property name="url" value="jdbc:oracle:thin:@//vir-tst.com:1521/qar01.world" /> 
    <property name="username" value="ccuser" /> 
    <property name="password" value="bueno" /> 
    <property name="maxActive" value="30" /> 
    <property name="maxWait" value="30" /> 
    <property name="maxIdle" value="30" /> 
    </bean> 

</beans> 

回答

4

我的m istake:还有另一个我错过的Spring配置文件。添加此字段并在我的单元测试中为任何自动布线字段定义设置器解决了此问题。

我现在用的这个清单时,这些类型的错误发生:

  • 确保实现类接口类型的使用“@Service” 注释
  • 确保豆在XML配置正确:
  • 最简单的方法是使用:

<context:component-scan base-package="com.customization.packagename" />

  • 这增加了所有类的包名
  • 下或者创建XML bean定义
0

添加SpringJdbcDrugQuery到common-test.xml的豆定义

+0

我现在就试一试......尽管如此:应该有必要吗? – IcedDante

+0

Autowire无法找到它,所以添加它或修复组件扫描配置 –

-2

我遇到这样的问题太多了,我只是添加二传手,那么它工作得很好。

+1

也许你应该更多地解释你的解决方案。目前还不清楚你做了什么以及如何解决你的问题。 – oers

1

我有类似的问题,发现虽然我可以在Eclipse中成功AutoWire类,surefire只需要接口自动连线。特别是只有在使用Cobertura进行检测时才会发生,所以很确定代理生成有问题。现在,我刚刚介绍了一个新的界面,因为它适合我的用例,但肯定还有其他适当的解决方案。