java - 添加到表后读取数据返回零

标签 java mysql hibernate transactions hql

当我在事务中向 talbe 添加几行时遇到问题 并从表中读取该数据。 我在添加之前已经测试了数据,以防止重复数据。 我的表没有自动生成的索引。 由于我启用了 hibernate 来显示 sql,我看到插入到表中 在我读取数据后执行,所以我得到了错误的数据。

    sessionFactory.getCurrentSession().flush();

我知道我可以在阅读之前刷新 session ,但这对我来说不是一个好的解决方案,因为如果我的程序创建异常,数据就会被存储 到表中,我就会遇到问题。

我的表已转换为INNODB引擎 更改表 mytable ENGINE=InnoDB;

这是我的项目

我删除了从文件导入 AppInitializer.java

package rs.co.master.config.web;
 import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;
 @ComponentScan(basePackages = { "rs.co" })
 public class AppInitializer  extends AbstractAnnotationConfigDispatcherServletInitializer
 implements WebApplicationInitializer{
    @Override
    protected Class<?>[] getRootConfigClasses() {
        return new Class[] { ApplicationContextConfig.class };
    }
    @Override
    protected Class<?>[] getServletConfigClasses() {
        return null;
    }
    @Override
    protected String[] getServletMappings() {
        return new String[] { "/" };
    }
     @Override
     public void onStartup(ServletContext servletContext) throws ServletException {
        super.onStartup(servletContext);
    AnnotationConfigWebApplicationContext appContext = new AnnotationConfigWebApplicationContext();
    appContext.register(ApplicationContextConfig.class);
    ServletRegistration.Dynamic dispatcher = servletContext.addServlet(
            "test", new DispatcherServlet(appContext));
    dispatcher.setInitParameter("display-name", "test");
    dispatcher.setInitParameter("Version", "dec");
    dispatcher.setLoadOnStartup(1);
    dispatcher.addMapping("/");
}
 }

ApplicationContextConfig

 package rs.co.master.config.web;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Locale;
 @Configuration
 @EnableWebMvc
 @MultipartConfig
 @EnableAspectJAutoProxy
 @ComponentScan(basePackages = { "rs.co" })
 public class ApplicationContextConfig  extends WebMvcConfigurerAdapter{
     @Autowired
      ConfigurationForTiles configurationForTiles;
        @Override
        public void configureViewResolvers(ViewResolverRegistry registry) {
            InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
            viewResolver.setViewClass(JstlView.class);
            viewResolver.setPrefix("/WEB-INF/views/");
            viewResolver.setSuffix(".jsp");
            registry.viewResolver(viewResolver);
        }
        @Override
        public void addResourceHandlers(ResourceHandlerRegistry registry) {
            registry.addResourceHandler("/themes/**").addResourceLocations("/themes/").setCachePeriod(31556926);
            registry.addResourceHandler("/ui/**").addResourceLocations("/ui/").setCachePeriod(31556926);
            registry.addResourceHandler("*.jpg").addResourceLocations("").setCachePeriod(31556926);
        }

        @Override
        public void configurePathMatch(PathMatchConfigurer matcher) {
            matcher.setUseRegisteredSuffixPatternMatch(true);
        }
        @Bean
        public MessageSource messageSource() {
            ResourceBundleMessageSource messageSource = new ResourceBundleMessageSource();
            messageSource.setBasename("messages");
            messageSource.setDefaultEncoding("UTF-8");
            return messageSource;
        }
        @Bean
        public LiteDeviceResolver liteDeviceResolver() {
            List<String> keywords = new ArrayList<String>();
            keywords.add("iphone");
            keywords.add("android");
            return new LiteDeviceResolver(keywords);
        }

        @Bean
        public DeviceResolverHandlerInterceptor deviceResolverHandlerInterceptor() {
            return new DeviceResolverHandlerInterceptor(liteDeviceResolver());
        }

        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            registry.addInterceptor(deviceResolverHandlerInterceptor());
            registry.addInterceptor(localeChangeInterceptor());
        }

    @Bean
    public LocaleResolver localeResolver() {
        CookieLocaleResolver resolver = new CookieLocaleResolver();
        resolver.setDefaultLocale(new Locale("sr_LATN_RS"));
        resolver.setCookieName("localeCookie");
        resolver.setCookieMaxAge(4800);
        return resolver;
    }

    @Bean
    public LocaleChangeInterceptor localeChangeInterceptor() {
        LocaleChangeInterceptor localeChangeInterceptor = new LocaleChangeInterceptor();
        localeChangeInterceptor.setParamName("locale");
        return localeChangeInterceptor;
    }

    @Bean
    public SessionLocaleResolver sessionLocaleResolver() {
        SessionLocaleResolver localeResolver = new SessionLocaleResolver();
        localeResolver.setDefaultLocale(new Locale("sr", "sr_LATN_RS"));
        return localeResolver;
    }


    @Bean(name = "supportedMediaTypes")
    public ByteArrayHttpMessageConverter supportedMediaTypes() {
        ByteArrayHttpMessageConverter supportedMediaTypes = new ByteArrayHttpMessageConverter();
        List<MediaType> suppMedType = new ArrayList<MediaType>();
        suppMedType.add(MediaType.IMAGE_GIF);
        suppMedType.add(MediaType.IMAGE_JPEG);
        suppMedType.add(MediaType.IMAGE_PNG);
        suppMedType.add(MediaType.ALL);

        supportedMediaTypes.setSupportedMediaTypes(suppMedType);
        return supportedMediaTypes;
    }

ConfigurationForTiles.java

 package rs.co.master.config.web;

 import org.springframework.context.annotation.Bean;
 import org.springframework.context.annotation.Configuration;
 @Configuration
 public class ConfigurationForTiles {
     @Bean
     public TilesConfigurer tilesConfigurer() {
         final TilesConfigurer configurer = new TilesConfigurer();
         configurer.setDefinitions(new String[] { 
                "/WEB-INF/config/tiles.xml"
                });
         configurer.setCheckRefresh(true);
         return configurer;
     }
     @Bean
     public TilesViewResolver tilesViewResolver() {
         final TilesViewResolver resolver = new TilesViewResolver();
         resolver.setViewClass(TilesView.class);
         return resolver;
     }
 }

HibernateConfiguration.java

 package rs.co.master.config.web;
 @Configuration
 @EnableTransactionManagement
 @ComponentScan({ "rs.co" })
 @PropertySource(value = { "classpath:database.properties" })
 public class HibernateConfiguration {
     @Autowired
     private Environment environment;
     @Bean
     public LocalSessionFactoryBean sessionFactory() {
         LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();
         sessionFactory.setDataSource(dataSource());
         sessionFactory.setPackagesToScan(new String[] { "rs.co" });
         sessionFactory.setHibernateProperties(hibernateProperties());
         return sessionFactory;
      }

     @Bean
     public DataSource dataSource() {
         DriverManagerDataSource dataSource = new DriverManagerDataSource();
         dataSource.setDriverClassName(environment.getRequiredProperty("database.driver"));
         dataSource.setUrl(environment.getRequiredProperty("database.url"));
         dataSource.setUsername(environment.getRequiredProperty("database.user"));
         dataSource.setPassword(environment.getRequiredProperty("database.password"));
        return dataSource;
     }

     private Properties hibernateProperties() {
         Properties properties = new Properties();
         properties.put("hibernate.dialect", environment.getRequiredProperty("hibernate.dialect"));
         properties.put("hibernate.show_sql", environment.getRequiredProperty("hibernate.show_sql"));
         properties.put("hibernate.format_sql", environment.getRequiredProperty("hibernate.format_sql"));
         properties.put("hibernate.hbm2ddl.auto", environment.getRequiredProperty("hibernate.hbm2ddl.auto"));
         properties.put("hibernate.connection.useUnicode", environment.getRequiredProperty("hibernate.connection.useUnicode"));
         properties.put("hibernate.connection.characterEncoding", environment.getRequiredProperty("hibernate.connection.characterEncoding"));
         properties.put("hibernate.connection.charSet", environment.getRequiredProperty("hibernate.connection.charSet"));
         return properties;        
     }

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

IndexController.java

 package rs.co.webController;
 @Controller
 @RequestMapping("")
 public class IndexController {
    private static final Logger logger = 
            LoggerFactory.getLogger(IndexController.class);
    @Autowired
    private DataService dataService;
    @RequestMapping(value = {"", "/"}, method = RequestMethod.GET, produces = "text/plain;charset=UTF-8")
    public @ResponseBody
    ModelAndView index(
            Locale locale, 
            HttpServletRequest request, HttpServletResponse response){

        ModelAndView model = new ModelAndView("index");
        model.addObject("welcome", "werew rew");
        return model;
    }

    @RequestMapping(value = "/fillData", method = RequestMethod.GET, produces = "text/plain;charset=UTF-8")
    public @ResponseBody
    ModelAndView fillData(
            Locale locale, 
            HttpServletRequest request, HttpServletResponse response){
        ModelAndView model = new ModelAndView("index");
        Random number = new Random();
        Integer x = number.nextInt(100)+1;
        if (x < 0) x = x * - 1;
            try{    
                 Integer result = dataService.fillData(x);
                 model.addObject("resultSum", result);
        }
         catch (Exception e) {
             logger.error("Error {}.", e.getMessage());
             e.printStackTrace();
         }
         finally {
         }  
        return model;
    }
 }

DataModel.java

 package rs.co.webModel;
 @Entity
 @Table(name = "mytable")
 public class DataModel implements Serializable {
    @Id
    // @GeneratedValue(strategy=GenerationType.AUTO)
    @NotNull
    @Column(name = "idtable")
    private Integer idtable;
    @NotNull
    @Column(name = "number")
    private Integer number;
    private static final long serialVersionUID = -729870310313L;
    public static long getSerialversionuid() {
        return serialVersionUID;
    }
    public DataModel() {
        super();
    }
    public DataModel(Integer idtable, Integer number) {
        super();
        this.idtable = idtable;
        this.number = number;
    }
    public void updateModel(DataModel inModel) {
        this.idtable = inModel.getIdtable();
        this.number = inModel.getNumber();

    }
 }

DataService.java

DataServiceImpl.java

 package rs.co.webService;
 @Service("DataService")
 @Transactional
 public class DataServiceImpl implements DataService{

    @Autowired
    DataDao dataDao;

 // @Override
    public Integer fillData(Integer number) throws Exception {
        return dataDao.fillData(number);
    }   
 }

DataDao.java

DataDaoImp.java

 package rs.co.webDao;
 import rs.co.webModel.DataModel;

 @Repository("DataDao")
 @Transactional
 public class DataDaoImpl  implements DataDao {

    @Autowired
    private SessionFactory sessionFactory;

    @Transactional(readOnly = false, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public Integer fillData(Integer number) throws Exception{
        Session sess = sessionFactory.openSession();
         Transaction tx = null;
            try{    
                 tx = sess.beginTransaction();
                    emptyTable();
                     for(int i = 0; i < number; i++){
                            Random n = new Random();
                            Integer x = n.nextInt(100)+1;
                         DataModel dm = new DataModel(i+1, x);
                         addData(dm);
                     }

            tx.commit(); 
        }
         catch (Exception e) {

             if (tx!=null && tx.getLocalStatus() != LocalStatus.ROLLED_BACK) 
                    tx.rollback();
             e.printStackTrace();
         }
         finally {
             sess.close();
         }  
         Integer sumNumbers = getSumNumber();
         return sumNumbers;
    }
    @Transactional(readOnly = true, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public DataModel getData(Integer idtable) {
        DataModel tmp = null;
        Query query;
        String sql = 
                  " from DataModel t"
                + " where idtable = :idtable "
            ;
            query = sessionFactory
                    .getCurrentSession().createQuery(sql);
            tmp = (DataModel) 
                        query
                        .setInteger("idtable", idtable)
                        .uniqueResult();
        return tmp;
    }
    @Transactional(readOnly = false, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public void emptyTable() throws Exception {
        sessionFactory
        .getCurrentSession()
        .createQuery(
                "DELETE FROM DataModel t"
                    )
                    .executeUpdate();       
    }
    @Transactional(readOnly = true, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    private Integer getSumNumber() {
        Long tmp = null;
        Query query;
        String sql = " select COALESCE(sum(t.number), 0) as number"
                + " from DataModel t";
            query = sessionFactory
                    .getCurrentSession().createQuery(sql);
            tmp = (Long) query.uniqueResult();
        if (null == tmp) return 0;
        return tmp.intValue();
    }
    @Transactional(readOnly = false, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public DataModel addData(DataModel inModel) throws Exception {
        DataModel model = null;
        model = getData( inModel.getIdtable());
        if (null == model){
            model = inModel;
            sessionFactory.getCurrentSession().save(model);
        } else {
            model.updateModel(inModel);
            sessionFactory.getCurrentSession().saveOrUpdate(model);
        }
        return model;
    }
    @Transactional(readOnly = false, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public void deleteData(Integer idtable) throws Exception{
        sessionFactory.getCurrentSession().createQuery(
                        "DELETE FROM DataModel "
                                + " where idtable = :idtable ")
                .setInteger("idtable", idtable).executeUpdate();
    }
 }

资源数据库.properties

          database.driver=com.mysql.jdbc.Driver
          database.url=jdbc:mysql://localhost:3306/test??characterEncoding=UTF-8&zeroDateTimeBehavior=convertToNull&characterEncoding=UTF-8&characterSetResults=UTF-8
          database.user=test
          database.password=test
          hibernate.dialect=org.hibernate.dialect.MySQLDialect
          hibernate.format_sql=true
          hibernate.show_sql=true
          hibernate.hbm2ddl.auto=update
          hibernate.connection.useUnicode=true
          hibernate.connection.characterEncoding=UTF-8
          hibernate.connection.charSet=UTF-8

tiles.xml

 <?xml version="1.0" encoding="UTF-8" ?>
 <!DOCTYPE tiles-definitions PUBLIC
        "-//Apache Software Foundation//DTD Tiles Configuration 3.0//EN"
        "http://tiles.apache.org/dtds/tiles-config_3_0.dtd">

 <tiles-definitions>
     <definition name="base.definition" template="/WEB-INF/tiles-templates/mainTemplate.jsp">
         <put-attribute name="title" value="test"></put-attribute>
         <put-attribute name="header" value=""></put-attribute>
         <put-attribute name="menu" value=""></put-attribute>
         <put-attribute name="body" value=""></put-attribute>
         <put-attribute name="footer" value=""></put-attribute>
     </definition>

ma​​inTemplate.jsp

 <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
 <%@taglib uri="http://www.springframework.org/tags/form" prefix="form"%>
 <%@ taglib uri="http://tiles.apache.org/tags-tiles" prefix="tiles"%>
 <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
 <%@ taglib uri="http://www.springframework.org/tags" prefix="spring" %>
 <%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
 <%@ taglib prefix="security" uri="http://www.springframework.org/security/tags" %>
 <c:import url="/WEB-INF/tiles-templates/homeHead.jsp"></c:import>  
 <body>

 <div id="main">

    <div id="header" >
        <tiles:insertAttribute name="header"></tiles:insertAttribute>
    </div>
    <div id="main1">
        <div id="menu1">
            <tiles:insertAttribute name="menu"></tiles:insertAttribute>
        </div>
        <div id="middle">
            <div id="b1">
                <tiles:insertAttribute name="body"></tiles:insertAttribute>
            </div>
        </div>
    </div>
    <div id="footer">
        <tiles:insertAttribute name="footer"></tiles:insertAttribute>
    </div>

 </div>
 </body>
 </html>

homeHead.jsp

 <%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
 <%@taglib uri="http://www.springframework.org/tags/form" prefix="form"%>
 <%@ taglib uri="http://tiles.apache.org/tags-tiles" prefix="tiles"%>
 <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
 <%@ taglib uri="http://www.springframework.org/tags" prefix="spring"%>
 <%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt"%>
 <%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions"  %>
 <!DOCTYPE html>

 <html lang="sr_RS">
 <head>
  <%@ page isELIgnored="false" %> 
   <meta name="_csrf" content="${_csrf.token}"/>
   <meta name="_csrf_header" content="${_csrf.headerName}"/>

 <title>
    <tiles:insertAttribute name="title" ignore="true"></tiles:insertAttribute>
 </title>
 </head>
     <definition name="index" extends="base.definition">
         <put-attribute name="title" value="test"></put-attribute>
         <put-attribute name="body" value="/WEB-INF/views/index.jsp"></put-attribute>
     </definition>
 </tiles-definitions>

index.jsp

 <%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
 <%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
 <%@ taglib prefix="tiles" uri="http://tiles.apache.org/tags-tiles"%>
 <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
 <%@ taglib prefix="spring" uri="http://www.springframework.org/tags"%>
 <%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt"%>
 <%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>
 <%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>
 <script type="text/javascript">
 <!--
 function fillData(){
    window.open("/test/fillData"
        ,
        "_self");
     ;
  }
 //-->
 </script>
 <h2>Hello World!</h2>
 <input type = "button" value="Click me" onclick="fillData()">Click to fill data and sum
 <br>
  <c:if test="${resultSum > 0 }">
      Result = ${resultSum }
  </c:if> 
  Result = <c:out value="${resultSum }"/>

最佳答案

我解决了问题 在主 Controller 中,我打开新的 session 和事务。 在 DataImplementation 中,我获取当前 session 并在同一 session 中打开事务

@RequestMapping(value = "/fillData", method = RequestMethod.GET, produces = "text/plain;charset=UTF-8")
public @ResponseBody
ModelAndView fillData(
        Locale locale, 
        HttpServletRequest request, HttpServletResponse response){


    ModelAndView model = new ModelAndView("index");
    Random number = new Random();
    Integer x = number.nextInt(3)+1;
    if (x < 0) x = x * - 1;
    Session sess = sessionFactory.openSession();
     Transaction tx = null;
        try{    
             tx = sess.beginTransaction();
             Integer result = dataService.fillData(x);
             model.addObject("resultSum", result);

        tx.commit(); 
    }
     catch (Exception e) {

         if (tx!=null && tx.getLocalStatus() != LocalStatus.ROLLED_BACK) 
                tx.rollback();
         logger.error("Error {}.", e.getMessage());
         e.printStackTrace();
     }
     finally {
         sess.close();
     }  

    return model;
}

不要在 dao 实现中关闭 session 。它将在 Controller 中关闭

@Transactional(readOnly = false, propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
public Integer fillData(Integer number) throws Exception{
    Session sess = sessionFactory.getCurrentSession();
    Integer sumNumbers = -1;
     Transaction tx = null;
        try{    
             tx = sess.beginTransaction();
                emptyTable();
                 for(int i = 0; i < number; i++){
                        Random n = new Random();
                        Integer x = n.nextInt(100)+1;
                     DataModel dm = new DataModel(i+1, x);
                     addData(dm);
                 }
                 sumNumbers = getSumNumber();

        tx.commit(); 
    }
     catch (Exception e) {

         if (tx!=null && tx.getLocalStatus() != LocalStatus.ROLLED_BACK) 
                tx.rollback();
         e.printStackTrace();
     }
     finally {
 //will be closed in controller          sess.close();
     }  
     return sumNumbers;
}

关于java - 添加到表后读取数据返回零,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40956911/

相关文章:

php - DATE_FORMAT 省略秒

java - HQL:条件查询内的划分

java - Hibernate 映射异常无法确定 : java. nio.file.Path 的类型

java - 如何用Java打印Dijkstra算法的完整路径

java - 从 Java 进行 HART-IP 通信

java.lang.IllegalStateException : Target host is null

mysql - SQL 多表查询

mysql - 评论系统查询拉父+x号。 child 评论

java - Hibernate ConfigurationException : Could not locate cfg. xml 资源 [hibernate.cfg.xml] IntelliJ

Java ISBN 格式