搭建基于springmvc,ibatis的工程实现读写分离,配置分离
实现读写分离:
1.spring配置如下:spring-dataResource.xml
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans xmlns="http://www.springframework.org/schema/beans" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tx="http://www.springframework.org/schema/tx" 4 xmlns:context="http://www.springframework.org/schema/context" 5 xmlns:mvc="http://www.springframework.org/schema/mvc" 6 xsi:schemaLocation="http://www.springframework.org/schema/beans 7 http://www.springframework.org/schema/beans/spring-beans-3.0.xsd 8 http://www.springframework.org/schema/tx 9 http://www.springframework.org/schema/tx/spring-tx-3.0.xsd 10 http://www.springframework.org/schema/context 11 http://www.springframework.org/schema/context/spring-context-3.0.xsd 12 http://www.springframework.org/schema/mvc 13 http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd"> 14 <!-- 主数据源 --> 15 <bean id="myDataSourceMaster" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> 16 <property name="driverClassName" value="${jdbc.driverClassName}" /> 17 <property name="url" value="${jdbc.url}" /> 18 <property name="username" value="${jdbc.username}" /> 19 <property name="password" value="${jdbc.password}" /> 20 </bean> 21 <!--从数据源--> 22 <bean id="myDataSourceSlave" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> 23 <property name="driverClassName" value="${jdbc.driverClassName}" /> 24 <property name="url" value="${jdbc.url}" /> 25 <property name="username" value="${jdbc.username}" /> 26 <property name="password" value="${jdbc.password}" /> 27 </bean> 28 29 <bean id="sqlMapClientReader" class="org.springframework.orm.ibatis.SqlMapClientFactoryBean"> 30 <property name="configLocation" value="classpath:sql-map-config.xml" /> 31 <property name="dataSource" ref="myDataSourceSlave" /> 32 </bean> 33 34 <bean id="sqlMapClientWriter" class="org.springframework.orm.ibatis.SqlMapClientFactoryBean"> 35 <property name="configLocation" value="classpath:sql-map-config.xml" /> 36 <property name="dataSource" ref="myDataSourceMaster" /> 37 </bean> 38 39 <!-- 操作数据库的基类 --> 40 <bean id="ibatisBaseDao" class="com.zzcm.ad.common.dao.impl.IbatisBaseDaoImpl"> 41 <property name="ibatisDaoReader"> 42 <bean id="ibatisDaoReader" class="com.zzcm.ad.common.dao.impl.IbatisDaoReaderImpl"></bean> 43 </property> 44 <property name="ibatisDaoWriter"> 45 <bean id="ibatisDaoWriter" class="com.zzcm.ad.common.dao.impl.IbatisDaoWriterImpl"/> 46 </property> 47 </bean> 48 </beans>
2.将此配置文件加载到主配置文件 spring-applicationContext.xml
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans 3 xmlns="http://www.springframework.org/schema/beans" 4 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 5 xmlns:tx="http://www.springframework.org/schema/tx" 6 xmlns:context="http://www.springframework.org/schema/context" 7 xmlns:mvc="http://www.springframework.org/schema/mvc" 8 xmlns:util="http://www.springframework.org/schema/util" 9 xsi:schemaLocation="http://www.springframework.org/schema/beans 10 http://www.springframework.org/schema/beans/spring-beans-3.0.xsd 11 http://www.springframework.org/schema/tx 12 http://www.springframework.org/schema/tx/spring-tx-3.0.xsd 13 http://www.springframework.org/schema/context 14 http://www.springframework.org/schema/context/spring-context-3.0.xsd 15 http://www.springframework.org/schema/util 16 http://www.springframework.org/schema/util/spring-util-3.0.xsd 17 http://www.springframework.org/schema/mvc 18 http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd"> 19 <!-- Root Context: defines shared resources visible to all other web components --> 20 <!-- 加载属性文件 --> 21 <bean id="propertyConfig" class="com.zzcm.ad.util.spring.PropertyAnnotationPlaceholderConfigurer"> 22 <property name="locations"> 23 <list> 24 <value>file:${global_config_path}/4gad/jdbc.properties</value> 25 <value>file:${global_config_path}/4gad/support.properties</value> 26 </list> 27 </property> 28 </bean> 29 30 <import resource="spring/spring-dataResources.xml"/> 31 <context:component-scan base-package="com.zzcm.ad"/> 32 33 <!-- 添加注解驱动 --> 34 <mvc:annotation-driven/> 35 <!-- 允许对静态资源文件的访问 --> 36 <mvc:default-servlet-handler/> 37 <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"> 38 <property name="viewClass" value="org.springframework.web.servlet.view.JstlView"/> 39 <property name="prefix" value="/WEB-INF/jsp/"/> 40 <property name="suffix" value=".jsp"/> 41 </bean> 42 </beans>
3.基本思想:
将读写数据库操作包装到一个基本操作类中,这样子对外操作就是一个基本操作类
因此如下:
基本操作接口:IbatisBaseDao
1 package com.zzcm.ad.common.dao; 2 public interface IbatisBaseDao extends IbatisDaoReader,IbatisDaoWriter{ 3 }
读操作接口:IbatisDaoReader
1 package com.zzcm.ad.common.dao; 2 import java.util.List; 3 import java.util.Map; 4 public interface IbatisDaoReader{ 5 /** 6 * 根据statementName查询,返回对象 7 * @param statementName 8 * @return 9 */ 10 public abstract <T> T queryForObject(String statementName); 11 /** 12 * 根据statementName,参数obj查询,返回对象 13 * @param statementName 14 * @param obj 15 * @return 16 */ 17 public abstract <T> T queryForObject(String statementName, Object obj); 18 /** 19 * 根据statementName查询,返回对象集合List 20 * @param statementName 21 * @return 22 */ 23 public abstract <T> List<T> queryForList(String statementName); 24 /** 25 * 根据statementName,参数obj查询,返回对象集合List 26 * @param statementName 27 * @param obj 28 * @return 29 */ 30 public abstract <T> List<T> queryForList(String statementName, Object obj); 31 /** 32 * 根据statementName,参数obj,返回Map key值查询,返回Map 33 * @param statementName 34 * @param obj 35 * @param keyProperty 36 * @return 37 */ 38 public abstract <T> Map queryForMap(String statementName,Object obj, String keyProperty); 39 /** 40 * 根据statementName、参数obj、返回Map key值、返回map value查询,返回Map 41 * @param statementName 42 * @param obj 43 * @param keyProperty 44 * @param valueProperty 45 * @return 46 */ 47 public abstract <T> Map queryForMap(String statementName,Object obj, String keyProperty,String valueProperty); 48 }
写操作接口:IbatisDaoWriter
1 package com.zzcm.ad.common.dao; 2 import com.zzcm.ad.common.exception.JdbcException; 3 public interface IbatisDaoWriter{ 4 /** 5 * 保存一个实体对象 6 * @param statementName 7 * @param entity 8 * @return 9 * @throws JdbcException 10 */ 11 public abstract Integer save(String statementName,Object obj) throws JdbcException; 12 /** 13 * 保存 14 * @param statementName 15 * @return 16 * @throws JdbcException 17 */ 18 public abstract Integer save(String statementName) throws JdbcException; 19 /** 20 * 更新一个实体对象 21 * @param statementName 22 * @param entity 23 * @return 24 * @throws JdbcException 25 */ 26 public abstract int update(String statementName,Object obj) throws JdbcException; 27 /** 28 * 更新 29 * @param statementName 30 * @param entity 31 * @return 32 * @throws JdbcException 33 */ 34 public abstract int update(String statementName) throws JdbcException; 35 /** 36 * 按照条件删除记录 37 * @param statementName 38 * @param paramObj 39 * @return 40 * @throws JdbcException 41 */ 42 public abstract int delete(String statementName,Object obj) throws JdbcException; 43 /** 44 * 按照条件删除记录 45 * @param statementName 46 * @return 47 * @throws JdbcException 48 */ 49 public abstract int delete(String statementName) throws JdbcException; 50 51 }
读操作实现类:IbatisDaoReaderImpl
1 package com.zzcm.ad.common.dao.impl; 2 import java.util.List; 3 import java.util.Map; 4 import javax.annotation.PostConstruct; 5 import javax.annotation.Resource; 6 import org.slf4j.Logger; 7 import org.slf4j.LoggerFactory; 8 import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport; 9 import org.springframework.util.Assert; 10 import com.ibatis.sqlmap.client.SqlMapClient; 11 import com.zzcm.ad.common.dao.IbatisDaoReader; 12 import com.zzcm.ad.common.exception.JdbcException; 13 /** 14 * 对数据库读操作的实现类 15 * @author shunyang 16 * 17 */ 18 public final class IbatisDaoReaderImpl extends SqlMapClientDaoSupport implements IbatisDaoReader { 19 private static final Logger logger = LoggerFactory.getLogger(IbatisDaoReaderImpl.class); 20 @Resource(name="sqlMapClientReader") 21 private SqlMapClient sqlMapClientReader; 22 @PostConstruct 23 public void initSqlMapClient(){ 24 super.setSqlMapClient(sqlMapClientReader); 25 } 26 27 @SuppressWarnings("unchecked") 28 @Override 29 public <T> T queryForObject(String statementName) throws JdbcException{ 30 Assert.notNull(statementName); 31 try { 32 return (T) this.getSqlMapClientTemplate().queryForObject(statementName); 33 } catch (Exception e) { 34 logger.error("Something's wrong when query :"); 35 logger.error("statementName:"+statementName); 36 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 37 } 38 } 39 @Override 40 public <T> T queryForObject(String statementName, Object obj) { 41 Assert.notNull(statementName); 42 Assert.notNull(obj); 43 try { 44 return (T) this.getSqlMapClientTemplate().queryForObject(statementName,obj); 45 } catch (Exception e) { 46 logger.error("Something's wrong when query :"); 47 logger.error("param:"+obj.getClass().getName()); 48 logger.error("statementName:"+statementName); 49 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 50 } 51 } 52 @Override 53 public <T> List<T> queryForList(String statementName) { 54 Assert.notNull(statementName); 55 try { 56 return (List<T>) this.getSqlMapClientTemplate().queryForList(statementName); 57 } catch (Exception e) { 58 logger.error("Something's wrong when query :"); 59 logger.error("statementName:"+statementName); 60 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 61 } 62 } 63 @Override 64 public <T> List<T> queryForList(String statementName, Object obj) { 65 Assert.notNull(statementName); 66 Assert.notNull(obj); 67 try { 68 return (List<T>) this.getSqlMapClientTemplate().queryForList(statementName,obj); 69 } catch (Exception e) { 70 logger.error("Something's wrong when query :"); 71 logger.error("statementName:"+statementName); 72 logger.error("param:"+obj.getClass().getName()); 73 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 74 } 75 } 76 @Override 77 public <T> Map queryForMap(String statementName, Object obj,String keyProperty) { 78 Assert.notNull(statementName); 79 Assert.notNull(obj); 80 try { 81 return this.getSqlMapClientTemplate().queryForMap(statementName, obj, keyProperty); 82 } catch (Exception e) { 83 logger.error("Something's wrong when query :"); 84 logger.error("statementName:"+statementName); 85 logger.error("param:"+obj.getClass().getName()+"--->keyProperty:"+keyProperty); 86 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 87 } 88 } 89 @Override 90 public <T> Map queryForMap(String statementName, Object obj,String keyProperty, String valueProperty) { 91 Assert.notNull(statementName); 92 Assert.notNull(obj); 93 try { 94 return this.getSqlMapClientTemplate().queryForMap(statementName, obj, keyProperty, valueProperty); 95 } catch (Exception e) { 96 logger.error("Something's wrong when query :"); 97 logger.error("statementName:"+statementName); 98 logger.error("param:"+obj.getClass().getName()+"--->keyProperty:"+keyProperty+"-->valueProperty:"+valueProperty); 99 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 100 } 101 } 102 }
写操作实现类:IbatisDaoWriterImpl
1 package com.zzcm.ad.common.dao.impl; 2 import javax.annotation.PostConstruct; 3 import javax.annotation.Resource; 4 import org.slf4j.Logger; 5 import org.slf4j.LoggerFactory; 6 import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport; 7 import org.springframework.util.Assert; 8 import com.ibatis.sqlmap.client.SqlMapClient; 9 import com.zzcm.ad.common.dao.IbatisDaoWriter; 10 import com.zzcm.ad.common.exception.JdbcException; 11 /** 12 * 对数据库写操作的实现类 13 * @author shunyang 14 * 15 */ 16 public final class IbatisDaoWriterImpl extends SqlMapClientDaoSupport implements IbatisDaoWriter { 17 private static final Logger logger = LoggerFactory.getLogger(IbatisDaoReaderImpl.class); 18 @Resource(name = "sqlMapClientWriter") 19 private SqlMapClient sqlMapClientWriter; 20 @PostConstruct 21 public void initSqlMapClient(){ 22 super.setSqlMapClient(sqlMapClientWriter); 23 } 24 25 public Integer save(String statementName,Object obj) { 26 Assert.notNull(statementName); 27 Assert.notNull(obj); 28 try { 29 return (Integer) this.getSqlMapClientTemplate().insert(statementName, obj); 30 } catch (Exception e) { 31 logger.error("Something's wrong when save Object:"); 32 logger.error(obj.getClass().getName()); 33 logger.error("statementName:"+statementName); 34 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 35 } 36 } 37 @Override 38 public Integer save(String statementName) throws JdbcException { 39 Assert.notNull(statementName); 40 try { 41 return (Integer) this.getSqlMapClientTemplate().insert(statementName); 42 } catch (Exception e) { 43 logger.error("Something's wrong when save Object:"); 44 logger.error("statementName:"+statementName); 45 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 46 } 47 } 48 49 @Override 50 public int update(String statementName, Object obj) 51 throws JdbcException { 52 Assert.notNull(statementName); 53 Assert.notNull(obj); 54 try { 55 return (Integer) this.getSqlMapClientTemplate().update(statementName, obj); 56 } catch (Exception e) { 57 logger.error("Something's wrong when update Object:"); 58 logger.error(obj.getClass().getName()); 59 logger.error("statementName:"+statementName); 60 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 61 } 62 } 63 @Override 64 public int update(String statementName) throws JdbcException { 65 Assert.notNull(statementName); 66 try { 67 return (Integer) this.getSqlMapClientTemplate().update(statementName); 68 } catch (Exception e) { 69 logger.error("Something's wrong when update Object:"); 70 logger.error("statementName:"+statementName); 71 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 72 } 73 } 74 @Override 75 public int delete(String statementName) throws JdbcException { 76 Assert.notNull(statementName); 77 try { 78 return this.getSqlMapClientTemplate().delete(statementName); 79 } catch (Exception e) { 80 logger.error("Something's wrong when delete Object:"); 81 logger.error("statementName:"+statementName); 82 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 83 } 84 } 85 @Override 86 public int delete(String statementName, Object obj) 87 throws JdbcException { 88 Assert.notNull(statementName); 89 try { 90 return this.getSqlMapClientTemplate().delete(statementName,obj); 91 } catch (Exception e) { 92 logger.error("Something's wrong when delete Object:"); 93 logger.error(obj.getClass().getName()); 94 logger.error("statementName:"+statementName); 95 throw new JdbcException(this.getClass() + "->" + e.getMessage(), e); 96 } 97 } 98 }
基本的操作实现类:IbatisBaseDaoImpl
1 package com.zzcm.ad.common.dao.impl; 2 import java.util.List; 3 import java.util.Map; 4 import com.zzcm.ad.common.dao.IbatisBaseDao; 5 import com.zzcm.ad.common.dao.IbatisDaoReader; 6 import com.zzcm.ad.common.dao.IbatisDaoWriter; 7 import com.zzcm.ad.common.exception.JdbcException; 8 /** 9 * 对数据库操作的基础类,实现了读写分离 10 * @author shunyang 11 * 12 */ 13 public class IbatisBaseDaoImpl implements IbatisBaseDao { 14 private IbatisDaoReader ibatisDaoReader; 15 private IbatisDaoWriter ibatisDaoWriter; 16 17 public IbatisDaoReader getIbatisDaoReader() { 18 return ibatisDaoReader; 19 } 20 public void setIbatisDaoReader(IbatisDaoReader ibatisDaoReader) { 21 this.ibatisDaoReader = ibatisDaoReader; 22 } 23 public IbatisDaoWriter getIbatisDaoWriter() { 24 return ibatisDaoWriter; 25 } 26 public void setIbatisDaoWriter(IbatisDaoWriter ibatisDaoWriter) { 27 this.ibatisDaoWriter = ibatisDaoWriter; 28 } 29 @Override 30 public Integer save(String statementName, Object obj)throws JdbcException { 31 return ibatisDaoWriter.save(statementName, obj); 32 } 33 @Override 34 public Integer save(String statementName) throws JdbcException { 35 return ibatisDaoWriter.save(statementName); 36 } 37 @Override 38 public int update(String statementName, Object obj) throws JdbcException { 39 return ibatisDaoWriter.update(statementName, obj); 40 } 41 @Override 42 public int update(String statementName) throws JdbcException { 43 return ibatisDaoWriter.update(statementName); 44 } 45 @Override 46 public int delete(String statementName, Object obj)throws JdbcException { 47 return ibatisDaoWriter.delete(statementName,obj); 48 } 49 @Override 50 public int delete(String statementName) throws JdbcException { 51 return ibatisDaoWriter.delete(statementName); 52 } 53 @Override 54 public <T> T queryForObject(String statementName) { 55 return ibatisDaoReader.queryForObject(statementName); 56 } 57 @Override 58 public <T> T queryForObject(String statementName, Object obj) { 59 return ibatisDaoReader.queryForObject(statementName, obj); 60 } 61 @Override 62 public <T> List<T> queryForList(String statementName) { 63 return ibatisDaoReader.queryForList(statementName); 64 } 65 @Override 66 public <T> List<T> queryForList(String statementName, Object obj) { 67 return ibatisDaoReader.queryForList(statementName, obj); 68 } 69 @Override 70 public <T> Map queryForMap(String statementName, Object obj, 71 String keyProperty) { 72 return ibatisDaoReader.queryForMap(statementName, obj, keyProperty); 73 } 74 @Override 75 public <T> Map queryForMap(String statementName, Object obj, 76 String keyProperty, String valueProperty) { 77 return ibatisDaoReader.queryForMap(statementName, obj, keyProperty, valueProperty); 78 } 79 }
对外提供的类就是IbatisBaseDaoImpl
配置分离的工程:
jdbc.properties
1 #数据库连接的方式,请根据你的项目中现有的情况配置 2 jdbc.driverClassName=com.mysql.jdbc.Driver 3 4 #数据连接URL,请根据你的项目中现有的情况配置 5 jdbc.url=jdbc:mysql://idctest.mysql.xxx.com:3306/zzsupport 6 7 #数据库连接的用户名,请根据你的项目中现有的情况配置 8 jdbc.username=zzmanager 9 10 #数据库连接的密码(带“.encrypt”与否都可以,但是带“.encrypt”的密码必须加密),请根据你的项目中现有的情况配置 11 #jdbc.password.encrypt=2dUGTjehnpU. 12 jdbc.password=iadMOB-2013@0622)
support.properties
1 #开发环境 2 upload.path=D:/apache-tomcat-6.0.30/webapps/zzupload-main 3 upload.url=http://192.168.0.88:8080/zzupload-main
工程源码详见github:https://github.com/shunyang/4gad
欢迎大家交流学习
----------------------------------------------------------------------------------------
如果您觉得阅读本文对您有帮助,请微信扫码关注作者,与我进行交流!欢迎各位转载,转载文章之后须在文章页面明显位置给出作者和原文连接,谢谢。
如果您觉得阅读本文对您有帮助,请微信扫码关注作者,与我进行交流!欢迎各位转载,转载文章之后须在文章页面明显位置给出作者和原文连接,谢谢。
![](https://o8ci6tgz8.qnssl.com/zsxq.png)