您好我正在使用带有spring和mongodb的hibernate JPA,我在Glassfish-4.0上运行我的应用程序。
我的服务类是:
@Component
public class Test {
@PersistenceContext
EntityManager em;
EntityManagerFactory emf;
@Transactional
public String persist(Details details) {
details.getUsername();
details.getPassword();
Query query = em.createNativeQuery("db.details.find(username="+details.getUsername()+"&password="+details.getPassword());
em.getTransaction().begin();
em.persist(details);
em.getTransaction().commit();
em.flush();
em.clear();
em.close();
query.executeUpdate();
System.out.println("Sucessful!");
return "persist";
}
}
我的spring-context.xml是:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:tx="http://www.springframework.org/schema/tx"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">
<context:component-scan base-package="com.javapapers.spring.mvc" />
<context:annotation-config />
<mvc:annotation-driven />
<tx:annotation-driven transaction-manager="txManager" />
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/view/" />
<property name="suffix" value=".jsp" />
</bean>
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalEntityManagerFactoryBean">
<property name="persistenceUnitName" value="ogmTest"/>
</bean>
<bean id="txManager" class="org.springframework.transaction.jta.JtaTransactionManager">
</bean>
</beans>
我在代码中应用了一些更改,但它们没有效果。 任何人都可以帮我解决这个问题。 提前谢谢。
答案 0 :(得分:46)
我不确定这是否会对您的情况有所帮助(即如果它仍然存在),但是,在网上搜索类似的问题之后。
我正在从持久性EntityManager创建本机查询以执行更新。
Query query = entityManager.createNativeQuery(queryString);
我收到以下错误:
由以下原因引起:javax.persistence.TransactionRequiredException:正在执行 更新/删除查询
许多解决方案建议在您的方法中添加@Transactional。 这样做并没有改变错误。
有些解决方案建议向EntityManager询问EntityTransaction
,以便您可以自己调用begin和commit。
这引发了另一个错误:
由引起的:java.lang.IllegalStateException:不允许创建 共享EntityManager上的事务 - 使用Spring事务或EJB 而不是CMT
然后我尝试了一种方法,大多数网站都说是使用应用程序管理的实体管理器而不是容器管理(我相信Spring是),那是joinTransaction()
。
让@Transactional
装饰方法然后在调用joinTransaction()
之前调用EntityManager对象上的query.executeUpdate()
并且我的本机查询更新有效。
我希望这有助于其他人遇到此问题。
答案 1 :(得分:24)
作为配置xml的形式,很明显你将使用基于spring的事务。请确保您用于@Transactional的导入是&#34; org.springframework.transaction.annotation.Transactional&#34;
在你的情况下,它可能是&#34; javax.transaction.Transactional&#34;
欢呼Chetan Verma
答案 2 :(得分:21)
在我的情况下,我导入了错误的@Transaction
。正确的是:
org.springframework.transaction.annotation.Transactional
和不 javax.transaction.Transactional
。
答案 3 :(得分:10)
当我使用Hibernate和Spring Jpa Data Repository时,我也面临同样的问题。我忘了将@Transactional
放在spring数据存储库方法上。
在使用@Transactional
注释后,它为我工作。
答案 4 :(得分:4)
如何将@Transactional
从方法级别移动到类级别?
在类似的情况下为我工作,虽然我不是100%肯定为什么。
答案 5 :(得分:4)
使用@Modifying和@Transaction修复了我
@修改 @Query(value =“从WHERE user_id =?1”删除锁,nativeQuery = true) void deleteByUserId(Long userId);
@服务 @Transactional
答案 6 :(得分:2)
我遇到了同样的错误。
我刚刚在方法上添加了 @Transactional 注释 javax.transaction.Transactional 。
答案 7 :(得分:2)
当我尝试在Java SE的非JTA(即资源本地)实体管理器中运行批量UPDATE查询时,收到此异常。 我只是忘记了将JPQL代码包装在
中em.getTransaction().begin();
和
em.getTransaction().commit();
答案 8 :(得分:1)
在我意识到我的方法被声明为public final
而不仅仅是public
之前,似乎没有什么对我有用。该错误是由final
关键字引起的。删除它会使错误消失。
答案 9 :(得分:1)
您无需担心开始和结束交易。您已经应用了@Transactional注释,它在您的方法开始时在内部打开事务,并在您的方法结束时结束。因此,只需将此对象保存在数据库中即可。
@Transactional(readOnly = false, isolation = Isolation.DEFAULT, propagation = Propagation.REQUIRED, rollbackFor = {Exception.class})
public String persist(Details details){
details.getUsername();
details.getPassword();
Query query = em.createNativeQuery("db.details.find(username= "+details.getUsername()+"& password= "+details.getPassword());
em.persist(details);
System.out.println("Sucessful!");
return "persist";
}
编辑:问题似乎与您的配置文件有关。如果您使用的是JPA,那么您的配置文件应该具有以下配置
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"
p:entityManagerFactory-ref="entityManagerFactory" />
<bean id="jpaAdapter"
class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter"
p:database="ORACLE" p:showSql="true" />
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean"
p:persistenceUnitName="YourProjectPU"
p:persistenceXmlLocation="classpath*:persistence.xml"
p:dataSource-ref="dataSource" p:jpaVendorAdapter-ref="jpaAdapter">
<property name="loadTimeWeaver">
<bean
class="org.springframework.instrument.classloading.InstrumentationLoadTimeWeaver" />
</property>
<property name="persistenceProvider" ref="interceptorPersistenceProvider" />
</bean>
答案 10 :(得分:1)
只需在方法级别或类级别添加 @Transactional 。当您更新或删除记录时,必须保持Transaction的持久状态,@Transactional
对此进行管理。
和导入 org.springframework.transaction.annotation.Transactional;
答案 11 :(得分:1)
如下所示,将@PersistenceContext与@Modifying一起使用可修复使用createNativeQuery时的错误
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.transaction.annotation.Transactional;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;
@PersistenceContext
private EntityManager entityManager;
@Override
@Transactional
@Modifying
public <S extends T> S save(S entity) {
Query q = entityManager.createNativeQuery(...);
q.setParameter...
q.executeUpdate();
return entity;
}
答案 12 :(得分:0)
在某种不同的情况下,我发生了相同的例外。 由于我一直在这里寻找答案,因此也许会对某人有所帮助。
我的情况是发生了异常,因为我从 SERVICE CONSTRUCTOR ... 中调用了(正确注释的)@Transactional方法。 由于我的想法只是使该方法从一开始就运行,因此我将其注释为以下内容,并停止以错误的方式进行调用。异常消失了,代码更好了:)
@EventListener(ContextRefreshedEvent.class)
@Transactional
public void methodName() {...}
@事务导入:import org.springframework.transaction.annotation.Transactional;
答案 13 :(得分:0)
如果先前的答案失败,请确保对在存储库中调用update方法的类使用 @Service 构造型。我最初使用的是 @Component ,但是它不起作用,对@Service的简单更改使其可以工作。
答案 14 :(得分:0)
我在springboot项目中也遇到了这个问题,并在我的课程中添加了@Transactional,它正在工作。
import org.springframework.transaction.annotation.Transactional;
@Transactional
public class SearchRepo {
---
}
答案 15 :(得分:0)
运行代码时出现错误消息: javax.persistence.TransactionRequiredException:执行更新/删除查询
开始entityManager事务-> createNativeQuery->执行更新-> EntityManager事务提交以将其保存在数据库中。 Hibernate和postgresql对我来说很好用。
entityManager.getTransaction().begin();
Query query = entityManager.createNativeQuery("UPDATE tunable_property SET tunable_property_value = :tunable_property_value WHERE tunable_property_name = :tunable_property_name");
query.setParameter("tunable_property_name", tunablePropertyEnum.eEnableJobManager.getName());
query.setParameter("tunable_property_value", tunable_property_value);
query.executeUpdate();
entityManager.getTransaction().commit();
答案 16 :(得分:0)
面对同样的问题,我只是忘记了使用@EnableTransactionManagement
注释来激活事务管理。
参考:
答案 17 :(得分:0)
尽管在类级别添加@Transactional注释并导入org.springframework.transaction.annotation.Transactional,我仍然遇到相同的错误。
然后我意识到,由于我使用的是休眠查询,因此我导入了javax.persistence.Query而不是import org.hibernate.query.Query。 因此,添加了导入org.hibernate.query.Query。为我解决了这个问题。
我希望这个主意能对某人有所帮助。
答案 18 :(得分:0)
我遇到了同样的异常“ TransactionRequiredException执行更新/删除查询”但对我来说原因是我在spring中创建了另一个bean applicationContext.xml 名为“ transactionManager ”的文件引用“ org.springframework.jms.connection.JmsTransactionManage r”,但是有另一个同名的bean“ transactionManager < / strong>“引用” org.springframework.orm.jpa.JpaTransactionManager “。所以 JPA bean被 JMS bean压倒了。
重命名Jms的bean名称后,问题就解决了。
答案 19 :(得分:0)
在我的项目中将Spring 4与Hibernate 5集成并遇到此问题后,我发现通过更改会话从sessionFactory.openSession()
到sessionFactory.getCurrentSession()
的方式,我可以防止出现错误。
解决这个错误的正确方法可能是继续使用相同的会话进行绑定事务。开始时,会始终创建一个新的会话,这个会话不像前者那样持有一个事务的configed.using getCurrentSession并添加其他属性<property name="current_session_context_class">org.springframework.orm.hibernate5.SpringSessionContext</property>
的工作原理对我好。
答案 20 :(得分:-1)
if (android.os.Build.VERSION.SDK_INT >= 11) {
setLayerType(View.LAYER_TYPE_SOFTWARE, null);
}