将 SpringBoot 与 Neo4J 结合使用:更新节点会创建重复节点
Using SpringBoot with Neo4J: Updating node creates duplicate node
我正在尝试更新 Neo4J 上的一个节点,但最终发生的是它创建了一个重复的节点。我读到更新必须在单个事务中进行,我添加了@Transactional,但结果仍然相同。这是我所拥有的。我尝试了读取和删除旧节点并保存新节点的方法,它似乎有效。但是,我认为这不是正确的做法。为什么 @Transactional 注释不起作用。谢谢。
@EnableNeo4JRepositories(com.example.graph.repo)
@EnableTransactionManagement
@org.springframework.contect.annotation.Configuration
public class Neo4JConfig {
@Bean
public Configuration configuration() {
Configuration cfg = new Configuration();
cfg.driverConfiguration()
.setDriverClassName("org.neo4j.ogm.drivers.http.driver.HttpDriver")
.setURI("http://neo4j:neo4j@localhost:7474");
return cfg;
}
@Bean
public SessionFactory sessionFactory() {
return new SessionFactory(configuration(), "com.example");
}
@Bean
public Neo4jTransactionManager transactionManager() {
return new Neo4JTransactionManager(sessionFactory());
}
}
@Service
public class UserService{
@Autowired
UserRepository userRepository;
@Transactional
public void updateUser(User user) {
User existingUser = userRepository.getExistingUser(user.getUserName());
if(existingUser != null ) {
user.setSomeValue(existingUser.getSomeValue());
userRepository.save(user);
}
}
}
Spring AOP默认使用JDK代理机制。这意味着您必须通过接口方法调用@Transactional
方法。
因此您应该将您的服务拆分为接口 UserService
和实现(例如 UserServiceImpl
),将接口自动装配到您当前自动装配实现的代码中,然后通过接口调用事务方法。
P.S。另一种方法是强制 Spring 使用 CGLIB,只要此机制不限于接口即可。两种机制的更多细节 https://docs.spring.io/spring/docs/3.0.0.M3/reference/html/ch08s06.html
我正在尝试更新 Neo4J 上的一个节点,但最终发生的是它创建了一个重复的节点。我读到更新必须在单个事务中进行,我添加了@Transactional,但结果仍然相同。这是我所拥有的。我尝试了读取和删除旧节点并保存新节点的方法,它似乎有效。但是,我认为这不是正确的做法。为什么 @Transactional 注释不起作用。谢谢。
@EnableNeo4JRepositories(com.example.graph.repo)
@EnableTransactionManagement
@org.springframework.contect.annotation.Configuration
public class Neo4JConfig {
@Bean
public Configuration configuration() {
Configuration cfg = new Configuration();
cfg.driverConfiguration()
.setDriverClassName("org.neo4j.ogm.drivers.http.driver.HttpDriver")
.setURI("http://neo4j:neo4j@localhost:7474");
return cfg;
}
@Bean
public SessionFactory sessionFactory() {
return new SessionFactory(configuration(), "com.example");
}
@Bean
public Neo4jTransactionManager transactionManager() {
return new Neo4JTransactionManager(sessionFactory());
}
}
@Service
public class UserService{
@Autowired
UserRepository userRepository;
@Transactional
public void updateUser(User user) {
User existingUser = userRepository.getExistingUser(user.getUserName());
if(existingUser != null ) {
user.setSomeValue(existingUser.getSomeValue());
userRepository.save(user);
}
}
}
Spring AOP默认使用JDK代理机制。这意味着您必须通过接口方法调用@Transactional
方法。
因此您应该将您的服务拆分为接口 UserService
和实现(例如 UserServiceImpl
),将接口自动装配到您当前自动装配实现的代码中,然后通过接口调用事务方法。
P.S。另一种方法是强制 Spring 使用 CGLIB,只要此机制不限于接口即可。两种机制的更多细节 https://docs.spring.io/spring/docs/3.0.0.M3/reference/html/ch08s06.html