文档章节

【待解决】SpringMVC+Hibernate4的Session问题

 海岸Thirty
发布于 2017/04/09 17:40
字数 921
阅读 21
收藏 0

写在前面的话:莫名奇妙的问题好了,但是没有按照我的想法来,测试了下最终生效的是

@EnableTransactionManagement。

先看看代码吧,以后有什么突破再更新!或者最好有大神帮我看看吧。

(两次搭项目都这样,哎。。。已经不是人品问题了我觉得)

 

OpenSessionInViewFilter,这个具好用,配置上HTTP就不报下面这个错了

Could not obtain transaction-synchronized Session for current thread

这里给份注解配置吧

/**
 * 所有实现了WebApplicationInitializer接口的类都会在容器启动时自动被加载运行,用@Order注解设定加载顺序
 * 这是servlet3.0+后加入的特性,web.xml中可以不需要配置内容,都硬编码到WebApplicationInitializer的实现类中
  * <ul>
 *  <li>处理URL上下文</li>
 *  <li>定义ServletMapping映射:.do,.json,.jsonp</li>
 *  <li>加载配置文件,相当于引入applicationContext.xml</li>
 * </ul>
 * @author lanxb
 * @create 2016年5月24日
 *
 */
@Order(2)
public class WebInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
	
	/*****  省略无关的内容   *********/
 
    /*
	  * 注册过滤器,映射路径与DispatcherServlet一致,路径不一致的过滤器需要注册到另外的WebApplicationInitializer中
	  */
    @Override
    protected Filter[] getServletFilters() {
        // 请求编码转换
    	CharacterEncodingFilter characterEncodingFilter = new CharacterEncodingFilter();
        characterEncodingFilter.setEncoding("UTF-8");
        characterEncodingFilter.setForceEncoding(true);
        
        // OpenSession
        OpenSessionInViewFilter hibernateSessionInViewFilter = new OpenSessionInViewFilter();
        return new Filter[] {characterEncodingFilter,hibernateSessionInViewFilter};
    }
  
  


}

 

因为有一个启动时到数据库加载配置的过程,由于不经过上面的filter,所以一直报错。

    @OpenSession
	@Transactional(readOnly=true)
	@Override
	public void afterPropertiesSet() throws Exception {
		List<AppConf> list = iwxMsgCryptDao.getListByHQL("from AppConf");
		logger.info("refres app configs begin : {}",mapConfig.size());
		if(list==null || list.isEmpty()){
			synchronized (mapConfig) {
				mapConfig.clear();
			}
		}else{
			Map<String,AppConf> mapConfig = new HashMap<>(); 
			for(AppConf conf:list){
				logger.info("\t add app config:{}",conf.getAppId());
				// 生成下keyData
				conf.setAesKey(conf.getAesKey());
				mapConfig.put(conf.getAppId(), conf);
			}
			this.mapConfig = mapConfig;
		}
		logger.info("refres app configs end : {}",mapConfig.size());
	}

于是查了查增加了下面的配置OpenSessionInterceptor:

想通过AspectJ代理带有@OpenSession注解的方法,在执行的时候获取HibernateSession

主要是:

openSessionPointcut()、openSessionInterceptor()然后openSessionAdvisor()、proxyConfig()


@Configuration
@EnableTransactionManagement
public class DBConfig implements TransactionManagementConfigurer{

	final static Logger logger = LoggerFactory.getLogger(DBConfig.class);
	
	@Value("${hibernate.dialect:org.hibernate.dialect.MySQL5Dialect}")
	String hibernate_dialect;
	
	@Value("${jdbc.driver}")  
    String driverClass;  
    @Value("${jdbc.url}")  
    String url;  
    @Value("${jdbc.username}")  
    String userName;  
    @Value("${jdbc.password}")  
    String passWord;
    
    @Value("${jdbc.initialSize:1}") 
    int initialSize=1; 
	//#定义最大连接数  
    @Value("${jdbc.maxActive:20}") 
	int maxActive=20;
	//#定义最大空闲  
    @Value("${jdbc.maxIdle:20}") 
	int maxIdle=20;
	//#定义最小空闲  
    @Value("${jdbc.minIdle:1}") 
	int minIdle=1;
	//#定义最长等待时间  
    @Value("${jdbc.maxWait:60000}") 
	int maxWait=60000;
	
    
    @Bean(name = "dataSource")  
    public DataSource dataSource() {
    	logger.info("初始化数据源开始……\n{}",url);
    	BasicDataSource dataSource = new BasicDataSource();
        dataSource.setDriverClassName(driverClass);  
        dataSource.setUrl(url);  
        dataSource.setUsername(userName);  
        dataSource.setPassword(passWord);  
        dataSource.setInitialSize(initialSize);
        dataSource.setMaxActive(maxActive);
        dataSource.setMaxIdle(maxIdle);
        dataSource.setMinIdle(minIdle);
        dataSource.setMaxActive(maxActive);
        logger.info("初始化数据源结束");
        return dataSource; 
    } 
    
    
    @Bean(name = "sessionFactory")
	public LocalSessionFactoryBean localSessionFactoryBean()  {
		logger.info("sessionFactory");
		LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();
		sessionFactory.setDataSource(dataSource());
		String[] packagesToScan = new String[] { "pub.thirty.tbk.module.**.domain" };
		sessionFactory.setPackagesToScan(packagesToScan);
		Properties hibernateProperties = new Properties();
		hibernateProperties.setProperty("hibernate.dialect", hibernate_dialect);
		hibernateProperties.setProperty("connection.autocommit", "false");
		
		hibernateProperties.setProperty(
				"hibernate.current_session_context_class",
				"org.springframework.orm.hibernate4.SpringSessionContext"
		);

		sessionFactory.setHibernateProperties(hibernateProperties);
		return sessionFactory;

	}
    
    @Bean(name = "transactionManager")
	public HibernateTransactionManager hibernateTransactionManager() {
		logger.info("transactionManager");
		HibernateTransactionManager hibernateTransactionManager = new HibernateTransactionManager();
		hibernateTransactionManager.setSessionFactory(localSessionFactoryBean().getObject());
		hibernateTransactionManager.setNestedTransactionAllowed(true);
		return hibernateTransactionManager;
	}

    
    @Bean
    public Pointcut openSessionPointcut(){
    	AspectJExpressionPointcut bean = new AspectJExpressionPointcut(); 
    	bean.setExpression("@annotation(pub.thirty.tbk.config.annotation.OpenSession)");
    	return bean;
    }
    
    @Bean
    public OpenSessionInterceptor openSessionInterceptor(){
    	OpenSessionInterceptor oi = new OpenSessionInterceptor();
    	oi.setSessionFactory(localSessionFactoryBean().getObject());
    	return oi;
    }
    
    @Bean
    public DefaultPointcutAdvisor openSessionAdvisor(){
    	DefaultPointcutAdvisor bean = new DefaultPointcutAdvisor();
    	bean.setAdvice(openSessionInterceptor());
    	bean.setPointcut(openSessionPointcut());
    	return bean;
    }
    @Bean 
   public ProxyConfig proxyConfig(){
	   AnnotationAwareAspectJAutoProxyCreator bean = new AnnotationAwareAspectJAutoProxyCreator();
	   bean.setProxyTargetClass(true);
	   return bean;
   }
    
	@Override
	public PlatformTransactionManager annotationDrivenTransactionManager() {
		return hibernateTransactionManager();
	}
   
}

 

1、目前生效的应该是:

@EnableTransactionManagement

(我的主Config应该时另一个类,这个注解似乎不用写在主Config里,虽然网上有人这么说)

2、OpenSessionInterceptor的想法是通过新建一个针对@OpenSession 切面,

  当调用带有@OpenSession的方法时,openSession或者getCurrentSession();

    bean.setProxyTargetClass(true); 这句时为了指定CGLIB代理,因为方法的接口是InitializingBean,感觉可能代理不到,不知道是不是必须。

PS:奇怪的是上周我加了@EnableTransactionManagement也不起作用,这周写完其他模块,回来重新放开启动模块居然发现神奇的好了,不知道什么鬼!!

     

 

© 著作权归作者所有

共有 人打赏支持
粉丝 3
博文 12
码字总数 4670
作品 0
浦东
高级程序员
私信 提问
springmvc+hibernate4 怎么实现数据层的多租户?

springmvc+hibernate4 怎么实现数据层的多租户?

owenG
2015/05/11
718
4
java,spring,hibernate,oracle

昨天自己搭了一个springmvc+hibernate4的框架,全注解。之前连接mysql的时候是没有任何问题的,但是连oracle这块就有问题了。现在用gecgetcurrentsession的时候数据保存不到数据库了,用get...

魔夜C
2016/09/01
106
0
Hibernate Validator bean-validator-3.0-JBoss-4.0.2

springMVC+hibernate4,配置框架时,用Junit测试时,会出现Hibernate Validator bean-validator-3.0-JBoss-4.0.2, Caused by: org.hibernate.HibernateException: Error applying BeanVali......

阿斯兰
2013/07/16
0
0
架构文摘:分布式系统Session一致性问题解析

一、问题的提出 1. 什么是Session? 用户使用网站的服务,需要使用浏览器与Web服务器进行多次交互。HTTP协议本身是无状态的,需要基于HTTP协议支持会话状态(Session State)的机制。具体的实...

adoryn
03/20
0
0
大型网站之分布式会话管理

随着网站的功能和用户越来越多,单机器服务部署的Web应用已经不能再支持了。这时候就需要优化或调整目前的架构,具体怎么优化,或先优化哪部分,这取决于网站的具体情况, 并非总是一个套路。...

十二缸帕萨特
2015/10/07
694
0

没有更多内容

加载失败,请刷新页面

加载更多

Mariadb二进制包安装,Apache安装

安装mariadb 下载二进制包并解压 [root@test-a src]# wget https://downloads.mariadb.com/MariaDB/mariadb-10.2.6/bintar-linux-glibc_214-x86_64/mariadb-10.2.6-linux-glibc_214-x86_64.t......

野雪球
今天
3
0
ConcurrentHashMap 高并发性的实现机制

ConcurrentHashMap 的结构分析 为了更好的理解 ConcurrentHashMap 高并发的具体实现,让我们先探索它的结构模型。 ConcurrentHashMap 类中包含两个静态内部类 HashEntry 和 Segment。HashEnt...

TonyStarkSir
今天
3
0
大数据教程(7.4)HDFS的java客户端API(流处理方式)

博主上一篇博客分享了namenode和datanode的工作原理,本章节将继前面的HDFS的java客户端简单API后深度讲述HDFS流处理API。 场景:博主前面的文章介绍过HDFS上存的大文件会成不同的块存储在不...

em_aaron
昨天
4
0
聊聊storm的window trigger

序 本文主要研究一下storm的window trigger WindowTridentProcessor.prepare storm-core-1.2.2-sources.jar!/org/apache/storm/trident/windowing/WindowTridentProcessor.java public v......

go4it
昨天
7
0
CentOS 生产环境配置

初始配置 对于一般配置来说,不需要安装 epel-release 仓库,本文主要在于希望跟随 RHEL 的配置流程,紧跟红帽公司对于服务器的配置说明。 # yum update 安装 centos-release-scl # yum ins...

clin003
昨天
11
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部