首页 > 解决方案 > javax.persistence.TransactionRequiredException:执行更新/删除查询,不能激活事务

问题描述

我在使用spring mvc和hibernate事务时遇到问题,我尝试使用我的dao和HQL来更新数据库然后服务器抛出一个TransactionRequiredException,我检查了我的事务注释、ComponentScan和事务包,每个方法服务工作正常,但 updateStock 方法。

有人对此有相同或类似的问题吗?

有我的代码:

调度员:

@Controller
public class ProductController {
    @Autowired
    productService pService;
    @Autowired
    ServletContext context;
    @Autowired
    orderService oService;

    @RequestMapping(value = "/ConfirmOrder")
    public String ConfirmOrder(HttpSession session) {
        shoppingCart sc = (shoppingCart) session.getAttribute("shoppingCart");
        orderBean ob = (orderBean) session.getAttribute("orderList");
        Set<orderItemBean> items = new HashSet<orderItemBean>();
        Map<Integer, orderItem> cart = sc.getContent();
        Set<Integer> set = cart.keySet();
        Integer newStock = 0;
        int n = 0;
        productBean mb = null;
        for (Integer k : set) {
            orderItem oi = cart.get(k);
            Integer subtotal = (oi.getiQty() * oi.getpPrice());
            String iDes = oi.getpName() + " 共 " + oi.getiQty().toString() + "個,金額小計:" + subtotal.toString();
            orderItemBean oib = new orderItemBean(null, oi.getpId(), iDes, oi.getiQty(), oi.getpPrice());
            oib.setOrderBean(ob);
            items.add(oib);
            mb = pService.getProduct(oi.getpId());
            newStock = mb.getpInstock() - oi.getiQty();
            n = pService.updateStock(oi.getpId(), newStock); //throw exception from here
        }
        ob.setItemSet(items);
        oService.saveOrder(ob);
        session.removeAttribute("shoppingCart");
        return "redirect:/";
    }
}

道:

import java.util.List;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import config.GlobalService;
import product.Dao.productDao;
import product.model.productBean;

@Repository
public class productDaoImpl implements productDao {
    int pageNo = 0;
    SessionFactory factory;

    public SessionFactory getFactory() {
        return factory;
    }

    @Autowired
    public void setFactory(SessionFactory factory) {
        this.factory = factory;
    }

    public productDaoImpl() {
    }

    @Override
    public int updateStock(int pId, int newStock) {
        int n = 0;
        Session session = factory.getCurrentSession();
        String sql = "UPDATE productBean b SET b.pInstock = :stock WHERE b.pId = :id";
        n = session.createQuery(sql).setParameter("stock", newStock).setParameter("id", pId).executeUpdate();
        return n;
    }

}

服务:

import java.util.List;

import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import config.GlobalService;
import product.Dao.productDao;
import product.model.productBean;
import product.service.productService;

@Transactional
@Service
public class productServiceImpl implements productService {
    productDao pdao;
    SessionFactory factory;

    public productDao getPdao() {
        return pdao;
    }

    public SessionFactory getFactory() {
        return factory;
    }

    @Autowired
    public void setPdao(productDao pdao) {
        this.pdao = pdao;
    }

    @Autowired
    public void setFactory(SessionFactory factory) {
        this.factory = factory;
    }

    public productServiceImpl() {

    }

    @Override
    public List<productBean> getAllProduct() {
        List<productBean> list = null;
        list = pdao.getAllProduct();
        return list;
    }

    @Override
    public int insertNewProduct(productBean pb) {
        int n = 0;
        pdao.insertNewProduct(pb);
        n++;
        return n;
    }

    @Override
    public productBean getProduct(int pId) {
        productBean pb = null;
        pb = pdao.getProduct(pId);
        return pb;
    }

    @Override
    public void setPageNo(int pageNo) {
        pdao.setPageNo(pageNo);

    }

    @Override
    public int getPageNo() {
        return pdao.getPageNo();
    }

    @Override
    public int getTotalPages() {
        int totalPages = (int) (Math.ceil(getDataCount() / (double) GlobalService.dataPerPage));
        return totalPages;
    }

    @Override
    public Long getDataCount() {

        return pdao.getDataCount();
    }

    @Override
    public int updateStock(int pId, int newStock) {
        return pdao.updateStock(pId, newStock);
    }

}

网络应用配置:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;

import org.springframework.web.multipart.commons.CommonsMultipartResolver;
import org.springframework.web.servlet.ViewResolver;
import org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;
import org.springframework.web.servlet.view.InternalResourceViewResolver;
import org.springframework.web.servlet.view.JstlView;

@Configuration
@EnableWebMvc
@ComponentScan(basePackages = "dispatcherController, register, product, cart, checkout")
public class WebAppConfig extends WebMvcConfigurerAdapter {
    @Bean
    public ViewResolver internalResourceViewResolver() {
        InternalResourceViewResolver resolver = new InternalResourceViewResolver();
        resolver.setViewClass(JstlView.class);
        resolver.setPrefix("/WEB-INF/views/");
        resolver.setSuffix(".jsp");
        return resolver;
    }

    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/css/**").addResourceLocations("/WEB-INF/resource/css/");
        registry.addResourceHandler("/img/**").addResourceLocations("/WEB-INF/resource/img/");
    }

    public WebAppConfig() {

    }

    @Bean
    public CommonsMultipartResolver multipartResolver() {
        CommonsMultipartResolver resolver = new CommonsMultipartResolver();
        resolver.setDefaultEncoding("UTF-8");
        resolver.setMaxUploadSize(81920000);
        return resolver;
    }

    @Override
    public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
        configurer.enable();
    }

}

根应用配置:

import java.beans.PropertyVetoException;
import java.util.Properties;

import javax.sql.DataSource;

import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.orm.hibernate5.HibernateTransactionManager;
import org.springframework.orm.hibernate5.LocalSessionFactoryBean;
import org.springframework.transaction.annotation.EnableTransactionManagement;

import com.mchange.v2.c3p0.ComboPooledDataSource;

@Configuration
@EnableTransactionManagement
public class RootAppConfig {

    @Bean
    public DataSource dataSource() {
        ComboPooledDataSource ds = new ComboPooledDataSource();
        ds.setUser("sa");
        ds.setPassword("sa123456");
        try {
            ds.setDriverClass("com.microsoft.sqlserver.jdbc.SQLServerDriver");
        } catch (PropertyVetoException e) {
            e.printStackTrace();
        }
        ds.setJdbcUrl("jdbc:sqlserver://localhost:1433;databaseName=PDB");
        ds.setInitialPoolSize(4);
        ds.setMaxPoolSize(8);
        return ds;
    }

    @Bean
    public LocalSessionFactoryBean sessionFactory() {
        LocalSessionFactoryBean factory = new LocalSessionFactoryBean();
        factory.setDataSource(dataSource());
        factory.setPackagesToScan(new String[] { "product.model","register.model","cart.model" });
        factory.setHibernateProperties(additionalProperties());
        return factory;
    }

    @Bean(name="transactionManager")
    @Autowired
    public HibernateTransactionManager transactionManager(SessionFactory sessionFactory) {
        HibernateTransactionManager txManager = new HibernateTransactionManager();
        txManager.setSessionFactory(sessionFactory);
        return txManager;
    }

    private Properties additionalProperties() {
        Properties properties = new Properties();
        properties.put("hibernate.dialect", org.hibernate.dialect.SQLServer2012Dialect.class);
        properties.put("hibernate.show_sql", Boolean.TRUE);
        properties.put("hibernate.format_sql", Boolean.TRUE);
        properties.put("default_batch_fetch_size", 10);
        properties.put("hibernate.hbm2ddl.auto", "update");
        return properties;
    }
}

网络初始化器:

import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;

public class WebAppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {

    @Override
    protected Class<?>[] getRootConfigClasses() {
        return new Class[] { RootAppConfig.class };
    }

    @Override
    protected Class<?>[] getServletConfigClasses() {
        return new Class[] { WebAppConfig.class };
    }

    @Override
    protected String[] getServletMappings() {
        return new String[] { "/" };
    }

}

标签: javahibernatespring-mvc

解决方案


推荐阅读