Bil*_*hah 2 hibernate jpa spring-data spring-data-jpa
I have a db code jar which I use in different application for accessing db. I am using spring data jpa. I need to call refresh to check for change in row in db from some other application. Here How I implement it.
My StudentRepository interface:
public interface StudentRepository extends JpaRepository<StudentEntity, Integer>, StudentRepositoryCustom {}
Run Code Online (Sandbox Code Playgroud)
My StudentRespositoryCustom interface
public interface StudentRepositoryCustom {
void detach(StudentEntity studentEntity);
void refresh(StudentEntity studentEntity);}
Run Code Online (Sandbox Code Playgroud)
My StudentRepositoryCustomImpl class
public class StudentRepositoryImpl implements StudentRepositoryCustom {
@PersistenceContext
EntityManager entityManager;
@Override
@Transactional
public void detach(StudentEntity studentEntity) {
entityManager.detach(studentEntity);
}
@Override
@Transactional
public void refresh(StudentEntity studentEntity) {
entityManager.refresh(studentEntity);
}}
Run Code Online (Sandbox Code Playgroud)
My Test
@Test
public void refreshTest(){
StudentEntity studentEntity = studentRepository.findOne(6);
studentRepository.refresh(studentEntity);
}
Run Code Online (Sandbox Code Playgroud)
But it throws this exception:
org.springframework.dao.InvalidDataAccessApiUsageException: Entity not managed; nested exception is java.lang.IllegalArgumentException: Entity not managed
at org.springframework.orm.jpa.EntityManagerFactoryUtils.convertJpaAccessExceptionIfPossible(EntityManagerFactoryUtils.java:384)
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.translateExceptionIfPossible(AbstractEntityManagerFactoryBean.java:492)
at org.springframework.dao.support.ChainedPersistenceExceptionTranslator.translateExceptionIfPossible(ChainedPersistenceExceptionTranslator.java:59)
Run Code Online (Sandbox Code Playgroud)
This line in hibernate-core-5.2.1.final SessionImpl class return null
EntityEntry entry = persistenceContext.getEntry( object );
Run Code Online (Sandbox Code Playgroud)
It should return entity I think.
My persistence.xml file is
<persistence-unit name="testPersitanceUnit" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<class>com.sample.dao.gen.StudentEntity</class>
<properties>
<property name="hibernate.archive.autodetection" value="class"/>
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hbm2ddl.auto" value="update"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect" />
<property name="hibernate.enable_lazy_load_no_trans" value="true" />
</properties>
</persistence-unit>
Run Code Online (Sandbox Code Playgroud)
My spring db config file is
<jpa:repositories base-package="com.sample.dao.repos"
entity-manager-factory-ref="entityManagerFactory" transaction-manager-ref="transactionManager"/>
<!-- Enable the component scan (auto wiring etc) for the following package -->
<context:component-scan base-package="com.sample.dao" />
<!-- Make sure the following is specified to enable transaction -->
<tx:annotation-driven />
<bean class="org.springframework.orm.jpa.JpaTransactionManager" id="transactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
<!-- This defines the entity manager factory with some custom properties -->
<bean id='entityManagerFactory' primary="true" class='org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean'>
<property name="persistenceUnitName" value="testPersitanceUnit"/>
<property name='dataSource' ref='dataSource' />
<property name="packagesToScan" value="com.sample.dao" />
enter code here
Run Code Online (Sandbox Code Playgroud)
小智 6
尝试在刷新之前使用合并。
public void refresh(T entity) {
this.entityManager.refresh(this.entityManager.merge(entity));
}
Run Code Online (Sandbox Code Playgroud)
尝试
public StudentEntity refresh(StudentEntity studentEntity) {
StudentEntity managedEntity = entityManager.find(StudentEntity.class, studentEntity.getId());
entityManager.refresh(managedEntity);
return managedEntity;
}}
Run Code Online (Sandbox Code Playgroud)
您遇到问题的原因是在您的测试中,您的 studentEntity 在事务 (findOne) 之外传递,因此不再管理。当它被传递到一个新事务(刷新)时,它不受管理,因此会引发此错误。
或者,如果原始刷新是所需的行为,您可以将整个测试包装在一个事务中,这应该维护您的测试对象的管理。
| 归档时间: |
|
| 查看次数: |
6414 次 |
| 最近记录: |