java - Springboot 测试与 commandLineRunner 给出不同的结果
问题描述
这是 MVCE:https ://github.com/neo4j-examples/movies-java-spring-data-neo4j
我添加到 Person 实体方法:
public void addMovie(Movie movie) {
if (this.movies == null) {
this.movies = new ArrayList<>();
}
this.movies.add(movie);
}
在测试中我添加了:在设置中:
keanu.addMovie(matrix);
personRepository.save(keanu);
在其中一项测试中:
Person p = personRepository.findByName("Keanu Reeves");
在调试模式下,我清楚地看到 p 在获取时具有电影集合。
从 github 测试更改代码后,它看起来像这样:
@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@Transactional
public class MovieRepositoryTest {
@Autowired
private MovieRepository movieRepository;
@Autowired
private PersonRepository personRepository;
@Before
public void setUp() {
Movie matrix = new Movie("The Matrix", 1999, "Welcome to the Real World");
movieRepository.save(matrix);
Person keanu = new Person("Keanu Reeves", 1964);
personRepository.save(keanu);
Role neo = new Role(matrix, keanu);
neo.addRoleName("Neo");
matrix.addRole(neo);
keanu.addMovie(matrix);
personRepository.save(keanu);
movieRepository.save(matrix);
}
/**
* Test of findByTitle method, of class MovieRepository.
*/
@Test
public void testFindByTitle() {
String title = "The Matrix";
Movie result = movieRepository.findByTitle(title);
Person p = personRepository.findByName("Keanu Reeves");
assertNotNull(result);
assertEquals(1999, result.getReleased());
}
/**
* Test of findByTitleContaining method, of class MovieRepository.
*/
@Test
public void testFindByTitleContaining() {
String title = "*Matrix*";
Collection<Movie> result = movieRepository.findByTitleLike(title);
assertNotNull(result);
assertEquals(1, result.size());
}
/**
* Test of graph method, of class MovieRepository.
*/
@Test
public void testGraph() {
Collection<Movie> graph = movieRepository.graph(5);
assertEquals(1, graph.size());
Movie movie = graph.iterator().next();
assertEquals(1, movie.getRoles().size());
assertEquals("The Matrix", movie.getTitle());
assertEquals("Keanu Reeves", movie.getRoles().iterator().next().getPerson().getName());
}
}
但如果我这样做:
@Bean
CommandLineRunner demo(PersonRepository personRepository, MovieRepository movieRepository) {
return args -> {
personRepository.deleteAll();
movieRepository.deleteAll();
Movie matrix = new Movie("The Matrix", 1999, "Welcome to the Real World");
movieRepository.save(matrix);
Person keanu = new Person("Keanu Reeves", 1964);
personRepository.save(keanu);
Role neo = new Role(matrix, keanu);
neo.addRoleName("Neo");
matrix.addRole(neo);
keanu.addMovie(matrix);
personRepository.save(keanu);
movieRepository.save(matrix);
Movie result = movieRepository.findByTitle("The Matrix");
Person p = personRepository.findByName("Keanu Reeves");
};
}
我看到 p 没有任何电影。为什么有区别?代码与测试中的相同。
解决方案
我对 neo4j 不熟悉,但是我猜想这是因为测试在 a 中运行,@Transaction
而命令行运行程序执行的代码却没有。
因此,将命令行运行器中的逻辑删除到可以包装在事务中的某个位置,无论是服务类还是应用程序侦听器。
推荐阅读
- javascript - Mongoose updateMany 文档包含特定的 Array 元素
- c++ - 如何使用 Eigen 求解具有 Neumann 型边界条件的方程组?
- python - 具有数组数据类型的 z3 建模图
- python - 和运营商的不一致
- django - 如何在 Django 中执行数据库中的代码
- javascript - 如何将图像从反应原生应用程序(Expo)上传到 django 服务器
- javascript - Flask/Python - 如何使用运行进度更新进度条
- python - Kymatio 散射变换一维错误“输入必须是连续的。”
- javascript - 使用 async/await 从 mongodb 获取数据时出现问题
- excel - 运行宏 VBA 时数据透视字段消失