【问题标题】:SpringBoot + Hibernate JPA No EntityManager with actuall transaction in @Service LayerSpring Boot + Hibernate JPA No EntityManager 与@Service 层中的实际事务
【发布时间】:2020-06-13 01:31:52
【问题描述】:

我正在自己配置 Spring Boot 应用程序以使用两个数据库运行(两个 transactionManager 相同)。 MariaDB 和 MongoDB。在@Repository 中,我有@Autowired 和@PersistenceContext,注释@Transactional 正在正确使用TransactionManager。 但对我来说最有用的是在@Services 层上使用@Transacional。但是当我这样做时,我遇到了问题

No EntityManager with actual transaction available for current thread

这是 @Repository 和 JpaRepository 的配置(我将编写两种方式的抽象代码以扩展我的知识:))

    package com.kamil.serwis.config;


@Configuration
@EnableJpaRepositories(entityManagerFactoryRef = "entityManagerFactoryMySQL",
        basePackages = "com.kamil.serwis.repository",
        transactionManagerRef = "MySQLTransactionManager")
@EnableTransactionManagement
@ComponentScan(basePackages = {"com.kamil.serwis.repository.dao.SQL"})
public class HibernateConfiguration {

    private final String URLDatabase = "jdbc:mariadb://localhost:3306/SerwisDB";
    private final String User = "test";
    private final String Password = "password";
    private final String SQLDatabase = "org.mariadb.jdbc.Driver";


    @Bean(name ="entityManagerFactoryMySQL")
    @Primary
    LocalContainerEntityManagerFactoryBean entityManagerFactory() {
        LocalContainerEntityManagerFactoryBean emf =
                new LocalContainerEntityManagerFactoryBean();
        emf.setPackagesToScan("com.kamil.serwis.model.SQL");
        emf.setDataSource(createDataSource());
        emf.setJpaVendorAdapter(createJpaVendorAdapter());
        emf.setJpaProperties(createHibernateProperties());
        emf.setPersistenceUnitName("MySQLPersistence");
//        emf.afterPropertiesSet();
        System.out.println("Data source do bazy" + emf.getDataSource().toString() + " " +emf.getPersistenceUnitName());
        return emf;
    }
    @Primary
    private DataSource createDataSource() {
        DataSource dataSource= DataSourceBuilder.create()
                .url(this.URLDatabase)
                .username(User)
                .password(Password)
                .driverClassName(SQLDatabase)
                .build();
        return dataSource;
    }
    @Primary
    private JpaVendorAdapter createJpaVendorAdapter() {
        return new HibernateJpaVendorAdapter();
    }
    @Primary
    private Properties createHibernateProperties() {
        Properties properties = new Properties();
        properties.setProperty("hibernate.hbm2ddl.auto", "create");
        properties.setProperty(
                "hibernate.dialect", "org.hibernate.dialect.MySQL55Dialect");
        properties.setProperty("hibernate.show_sql","true");
        /*properties.setProperty("com.mysql.cj.jdbc.Driver","");*/
        return properties;
    }

    @Bean(name = "MySQLTransactionManager")
    @Primary
    PlatformTransactionManager transactionManager(@Qualifier("entityManagerFactoryMySQL") EntityManagerFactory emf) {
        return new JpaTransactionManager(emf);
    }

}

在@Service 中,我遇到了“没有实际事务的 EntityManager ...”的问题层是吗?因为在@Repository 中添加@Transactional 时一切正常。

如何配置?你能帮我解决这个问题吗?

还有简单的@repository,它与@transactional 配合得很好,但我更喜欢在服务层使用@transactional(但现在它对我不起作用)。

@Repository 示例:

@Repository
public class UserRepository {

    @PersistenceContext(name = "MySQLPersistence")
    @Autowired
    private EntityManager entityManager;


    public User addUserToDB(User newUser){
        entityManager.persist(newUser);
        return newUser;
    }

    public User findUserByName(String userName){
        User user = (User)entityManager.createQuery( "select u from User u").getResultStream().findFirst().get();
        return user;
    }

    public boolean deleteUser(User userToDelete){
        entityManager.remove(userToDelete);
        return entityManager.find(User.class,userToDelete.getId()).equals(userToDelete);
    }
}

编辑 我为 jpa 和 Spring 上下文尝试了@transactional

    import org.springframework.stereotype.Service;
    import org.springframework.transaction.annotation.Transactional;

    import javax.annotation.PostConstruct;
    import javax.transaction.TransactionManager;

    @Service
    public class UserService {

        private UserRepository userRepository;

        @Autowired
        public UserService(UserRepository userRepository){
            this.userRepository = userRepository;
        }

        @Transactional(transactionManager = "entityManagerFactoryMySQL")
        //@javax.transaction.Transactional
        @PostConstruct
        public void createUser(){
            User newUser = new User("test");
            User usersaved = userRepository.addUserToDB(newUser);
        }
    }

【问题讨论】:

  • 请同时添加服务层代码。
  • 好的,编辑后添加
  • 试试这个:@Transactional("MySQLTransactionManager").Tell 使用这个后会发生什么?
  • 注意:MySQLTransactionManager - 这是您提到的事务管理器的名称,而不是entityManagerFactoryMySQLentityManagerFactoryMySQL - 这是EntityManagerFactory Bean 的名称。

标签: java spring hibernate spring-boot


【解决方案1】:

将服务层更新为:

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.PostConstruct;

@Service
public class UserService {

    private UserRepository userRepository;

    @Autowired
    public UserService(UserRepository userRepository){
        this.userRepository = userRepository;
    }

    @Transactional("MySQLTransactionManager")
    @PostConstruct
    public void createUser(){
        User newUser = new User("test");
        User usersaved = userRepository.addUserToDB(newUser);
    }
}

【讨论】:

  • 我在“MySQLTransactionManager”上进行了更改,但仍然无法正常工作。发生了同样的错误。也许 SpringBoot 的一些配置应该做更多?在存储库事务中工作正常。 @Angish B。你对我有更多的想法吗?我在 Spring Boot 文档中搜索,但没有看到更多配置。
  • 你应该把@Transactional放在服务中而不是在dao中。
  • 检查您的 HibernateConfiguration 类。它有错误。请检查
  • 是的,我将@Transactional 用于服务而不是 dao。并且仍然无法正常工作。只有在我投入使用时才有效
【解决方案2】:

好的。问题已经解决了。哪里错了? 如果我删除了@PostConstruct,它现在正在工作。但是我可以阅读文档为什么 @PostConstruct 不能与 @Transactional 一起使用?也许是该类型的一些条件或配置? 因为如果我想在应用程序启动后与数据库进行事务?这怎么可能?只有@PostConstruct?

感谢您花时间解决我的问题 :)

【讨论】:

    猜你喜欢
    • 2015-09-16
    • 2020-03-16
    • 2015-10-20
    • 1970-01-01
    • 1970-01-01
    • 2017-09-08
    • 2018-02-04
    • 2020-09-30
    • 2017-04-07
    相关资源
    最近更新 更多