[英]How to set up a unit test for spring data with service and repository?
I have checked many SO comments and the docs for spring data and unit testing but I cant get this to work and I dont know why its not working. 我已经检查了很多SO注释和有关弹簧数据和单元测试的文档,但是我无法使其正常工作,而且我不知道为什么它不起作用。
I have a junit test class that looks like this: 我有一个junit测试类,看起来像这样:
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(loader = AnnotationConfigContextLoader.class)
public class DealServiceTest {
@Configuration
static class ContextConfiguration {
// this bean will be injected into the OrderServiceTest class
@Bean
public DealService orderService() {
DealService dealService = new DealService();
// set properties, etc.
return dealService;
}
@Bean
public EmployeeService employeeService(){
EmployeeService employeeService = new EmployeeService();
return employeeService;
}
}
@Autowired
DealService dealService;
@Autowired
EmployeeService employeeService;
@Test
public void createDeal() throws ServiceException {
Employee employee = new Employee("Daniel", "tuttle", "danielptm@me.com", "dannyboy", "secret password", 23.234, 23.23);
Deal d = dealService.createDeal("ADSF/ADSF/cat.jpg", "A title goes here", "A deal description", 23.22, "Name of business", 23.23,23.23, employee, "USA" );
Assert.assertNotNull(d);
}
} }
And then I have my service class that looks like this 然后我的服务类如下所示
@Service
public class DealService {
@Autowired
private DealRepository dealRepository;
public Deal createDeal(String image, String title, String description, double distance, String location, double targetLat, double targetLong, Employee employee, String country) throws ServiceException {
Deal deal = new Deal(image, title, description, distance, location, targetLat, targetLong, employee, country);
try {
return dealRepository.save(deal);
}catch(Exception e){
throw new ServiceException("Could not create a deal: "+deal.toString(), e);
}
}
public Deal updateDeal(Deal d) throws ServiceException {
try{
return dealRepository.save(d);
}catch(Exception e){
throw new ServiceException("Could not update deal at this time: "+d.toString(),e);
}
}
public List<Deal> getAllDealsForEmployeeId(Employee employee) throws ServiceException {
try{
return dealRepository.getAllDealsBy_employeeId(employee.getId());
}catch(Exception e){
throw new ServiceException("Could not get deals for employee: "+employee.getId(), e);
}
}
}
And then my repository: 然后我的存储库:
*/ * /
public interface DealRepository extends CrudRepository<Deal, Long>{
public List<Deal> getDealsBy_country(String country);
public List<Deal> getAllDealsBy_employeeId(Long id);
}
My config file looks like this: 我的配置文件如下所示:
@Configuration
@EnableJpaRepositories("com.globati.repository")
@EnableTransactionManagement
public class InfrastructureConfig {
@Bean
public DataSource dataSource() {
HikariConfig config = new HikariConfig();
config.setDriverClassName("com.mysql.jdbc.Driver");
config.setJdbcUrl("jdbc:mysql://localhost:3306/DatabaseProject");
config.setUsername("awesome");
config.setPassword("database");
return new HikariDataSource(config);
}
// @Bean
// public DataSource derbyDataSource(){
// HikariConfig config = new HikariConfig();
// config.setDriverClassName("jdbc:derby:memory:dataSource");
// config.setJdbcUrl("jdbc:derby://localhost:1527/myDB;create=true");
// config.setUsername("awesome");
// config.setPassword("database");
//
// return new HikariDataSource(config);
//
// }
@Bean
public JpaTransactionManager transactionManager(EntityManagerFactory factory) {
return new JpaTransactionManager(factory);
}
@Bean
public JpaVendorAdapter jpaVendorAdapter() {
HibernateJpaVendorAdapter adapter = new HibernateJpaVendorAdapter();
adapter.setDatabase(Database.MYSQL);
adapter.setGenerateDdl(true);
return adapter;
}
@Bean
public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
LocalContainerEntityManagerFactoryBean factory = new LocalContainerEntityManagerFactoryBean();
factory.setDataSource(dataSource()); //Get data source config here!
factory.setJpaVendorAdapter(jpaVendorAdapter());
factory.setPackagesToScan("com.globati.model");
return factory;
}
}
But I get this error. 但是我得到这个错误。
java.lang.IllegalStateException: Failed to load ApplicationContext ...
java.lang.IllegalStateException:无法加载ApplicationContext ...
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean found for dependency [com.globati.repository.DealRepository]: expected at least 1 bean which qualifies as autowire candidate.
由以下原因引起:org.springframework.beans.factory.NoSuchBeanDefinitionException:未找到依赖项的合格bean [com.globati.repository.DealRepository]:期望至少有1个有资格作为自动装配候选的bean。 Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
依赖项注释:{@ org.springframework.beans.factory.annotation.Autowired(required = true)}
Any suggestions for how I can successfully do unit testing with spring data, junit and with my service and repositories would be greatly appreciated. 对于如何使用spring数据,junit以及我的服务和存储库成功进行单元测试的任何建议,将不胜感激。 Thanks!
谢谢!
For a repository bean to be injected, 对于要注入的存储库Bean,
You need to enable Repositories, using one of the spring-data annotations. 您需要使用spring-data批注之一启用存储库。 So add
@Enable*Repositories
to your configuration class 因此,将
@Enable*Repositories
添加到您的配置类中
You also need dB factories and other related beans configured. 您还需要配置dB工厂和其他相关的bean。 I am using Mongo and I have mongoDbFactory bean configured
我正在使用Mongo并且配置了mongoDbFactory bean
And for the most part your test configuration should look like your main configuration except for unnecessary bean replaced by mock implementations 而且在大多数情况下,您的测试配置应该看起来像您的主配置,只是不必要的bean被模拟实现所替代
UPDATE Here is my code (sorry mine is in mongo, I think you can relate) 更新这是我的代码(对不起,我在mongo中,我想你可以联系一下)
@Configuration
@WebAppConfiguration
@ComponentScan(basePackages = "com.amanu.csa",
excludeFilters = @ComponentScan.Filter(type = FilterType.ASSIGNABLE_TYPE, value = WebConfig.class))
@EnableMongoRepositories(repositoryImplementationPostfix = "CustomImpl")
class TestConfig {
@Bean
Mongo mongo() throws Exception {
return new MongoClient("localhost")
}
@Bean
MongoDbFactory mongoDbFactory() throws Exception {
return new SimpleMongoDbFactory(mongo(), "csa_test")
}
@Bean
MongoTemplate mongoTemplate() throws Exception {
MongoTemplate template = new MongoTemplate(mongoDbFactory())
template.setWriteResultChecking(WriteResultChecking.EXCEPTION)
return template
}
}
That is my test config file... As you can see it explicitly excludes my main configuration file. 那是我的测试配置文件...如您所见,它明确排除了我的主配置文件。
@ContextConfiguration(classes = TestConfig)
@RunWith(SpringRunner.class)
class OrganizationServiceTest {
@Autowired
OrganizationService organizationService
@Test
void testRegister() {
def org = new Organization()
//...
organizationService.register(org)
// ...
}
And that is my test class. 那是我的测试课。 It refers to the test config, and I recommend using named config classes.
它指的是测试配置,我建议使用命名的配置类。 You can put common options onto a super class and extend those and use them for your tests.
您可以将通用选项放在一个超类上,并将其扩展并用于测试。
I hope this helps 我希望这有帮助
You can try to add 您可以尝试添加
@ActiveProfiles("your spring profile")
In addition I would suggest to use an embedded test db like flapdoodle ( https://github.com/flapdoodle-oss/de.flapdoodle.embed.mongo ) 另外,我建议使用嵌入式测试数据库,例如flappoodle( https://github.com/flapdoodle-oss/de.flapdoodle.embed.mongo )
You could either : 您可以:
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.