.Net转Java自学之路—Spring框架篇三(JdbcTemplate、管理事务)

Spring对不同持久化技术都进行封装了不同的模板类。模板类有:
  JDBC:org.springframework.jdbc.core.JdbcTemplate
  Hibernate5.0:org.springframework.orm.hibernate5.HibernateTemplate
  IBatis(MyBatis):org.springframework.orm.ibatis.SqlMapClientTemplate
  JPA:org.springframework.orm.jpa.JpaTemplate

Spring的JdbcTemplate模板类实现crud操作:

  导入JdbcTemplate模板jar包:spring-jdbc.release.jar、spring-tx.release.jar

//创建对象,设置数据库信息
DriverManagerDataSource dataSource=new DriverManagerDataSource();
dataSource.setDirverClassName("");
dataSource.setUrl("");
dataSource.setUsername("");
dataSource.setPassword("");
//创建jdbcTemplate模板对象,设置数据源
JdbcTemplate jdbcTemplate=new JdbcTemplate(dataSource);
//调用jdbcTemplate对象中的方法实现操作。

//新增
String strSql="insert into tablename value(?,?)";
int count = jdbcTemplate.update(sql,"第一个?号的值","第二个?号的值");

//修改
String strSql="udpate tablename set cloumn1=? where column2=?";
int count = jdbcTemplate.update(sql,"第一个?号的值","第二个?号的值");

//删除
String strSql="delete from tablename where column2=?";
int count = jdbcTemplate.update(sql,"第一个?号的值");
Crud操作

  针对于查询而言,在dbutils时,存在有接口ResultSetHandler,dbutils提供了针对不同的结果实现类。在JdbcTemplate针对这个接口没有提供实现类,得到不同的类型数据需要进行自定义的数据封装。

//查询返回某一个值:第二个参数是返回类型的class
//    如:Integer.class、String.class......
String strSql="select count(*) from tablename";
int count = jdbcTemplate.queryForObject(strSql,Integer.class);

//查询返回对象:
/**
* 第二个参数:RowMapper接口; 可使用匿名内部类/自定义类实现。
*第三个:可变参数
*/
String strSql="select * from tablename where column=?";
//自定义类形式
Test test = jdbcTemplate.queryForObject(strSql,new TestRowMapper(),"第一个?号的值");
//匿名内部类形式
Test test = jdbcTemplate.queryForObject(strSql,new RowMapper<Test>(){
    public Test mapRow(ResultSet rs,int num) throws SQLException {
        String strColumn1=rs.getString("column1");
        String strColumn2=rs.getString("column2");
        ......
        Test test=new Test();
        test.setXXX(strColumn1);
        test.setXXX(strColumn2);
        ......
        return test;
    }
},"第一个?号的值");

//查询返回list对象
String strSql="select * from tablename";
List<Test> list = jdbcTemplate.query(strSql,new TestRowMapper());

class TestRowMapper implements RowMapper<Test>{
    public Test mapRow(ResultSet rs,int num) throws SQLException {
        String strColumn1=rs.getString("column1");
        String strColumn2=rs.getString("column2");
        ......
        Test test=new Test();
        test.setXXX(strColumn1);
        test.setXXX(strColumn2);
        ......
        return test;
    }
}

Spring配置连接池:

  配置c3p0连接池:
    需要jar包:c3p0.jar、mchange-commons-java.jar
    在jdbc的c3p0连接池的原始的写法:一种时在c3p0-config.xml中配置。另一种时直接代码实现。如下:

ComboPooledDataSource dataSource = new ComboPooledDataSource();
dataSource.setDriverClass("");
dataSource.setJdbcUrl("");
dataSource.setUser("");
dataSource.setPassword("");

    而在Spring中利用ioc类配置c3p0连接池创建对象和属性注入来将上述代码封装。如下:

<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
    <!-- 属性值注入 -->
    <property name="driverClass" value=""></property>
    <property name="jdbcUrl" value=""></property>
    <property name="user" value=""></property>
    <property name="password" value=""></property>
</bean>
<!-- 或者 使用下面这种方式 -->
<!-- 加载属性文件 -->
<context:property-placeholder location="classpath:db.properties(配置文件路径)"/>
<!-- db.properties配置文件的内容: 
    jdbc.driverClass=值 
    jdbc.jdbcUrl=值
    jdbc.user=值
    jdbc.password=值 -->

<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
    <!-- 属性值注入 -->
    <property name="driverClass" value="${jdbc.driverClass}"></property>
    <property name="jdbcUrl" value="${jdbc.jdbcUrl}"></property>
    <property name="user" value="${jdbc.user}"></property>
    <property name="password" value="${jdbc.password}"></property>
</bean>

  dao层使用JdbcTemplate模板:

public class TestService{

    private TestDao testDao;
    public void setTestDao(TestDao testDao){
        this.testDao=testDao;
    }
    
    public void add(){
        testDao.add();
    }
}

public class TestDao{
    
    //得到JdbcTemplate模板对象
    private JdbcTemplate jdbcTemplate;
    public void setJdbcTemplate(JdbcTemplate jdbcTemplate){
        this.jdbcTemplate=jdbcTemplate;
    }

    public void add(){
        String strSql="insert into tablename value(?,?)";
        int num = jdbcTemplate.update(strSql,"值1","值2");
    }
}
<bean id="testService" class="TestService全路径">
    <!-- 注入dao对象 -->
    <property name="testDao(类的属性名称)" ref="testDao(TestDao配置的id属性值)"></property>
</bean>
<bean id="testDao" class="TestDao全路径">
    <!-- 注入JdbcTemplate对象 -->
    <property id="jdbcTemplate" ref="jdbcTemp"></property>
</bean>
<!-- 创建JdbcTemplate对象 -->
<bean id="jdbcTemp" class="org.springframework.jdbc.core.JdbcTemplate">
    <!-- 将dataSource传递到JdbcTemplate模板对象中 -->
    <property name="dataSource" ref="dataSource"></property>
</bean>

Spring事务管理:

  Spring事务管理的两种方式:1、编程式事务管理。2、声明式事务管理。

  Spring进行事务管理API:

    Spring事务管理高层抽象主要包含3个接口:
      PlatformTransactionManager:事务管理器
        Spring为不同的持久化框架提供了该接口不同的实现类:
          org.springframework.jdbc.datasource.DataSourceTransactionManager:使用Spring JDBC或iBatis进行持久化数据时使用。
          org.springframework.orm.hibernate5.HibernateTransactionManager:使用Hibernate5.0版本进行持久化数据时使用。
          org.springframework.orm.jpa.JpaTransactionManager:使用JPA进行持久化时使用。
          org.springframework.jdo.JdoTransactionManager:当持久化机制时Jdo时使用。
          org.springframework.transaction.jta.JtaTransactionManager:使用一个JTA实现来管理事务,在一个事务跨越多个资源时必须使用。
        无论是xml配置文件方式还是注解方式做事务操作,首先都要做配置事务管理器操作。就是创建上述实现类的对象即可。

      TransactionDefinition:事务定义信息(隔离、传播、超时、只读)

      TransactionStatus:事务具体运行状态。

  Spring声明式事务管理进行事务配置:

<?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:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" 
       xmlns:tx="http://www.springframework.org/schema/tx"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
   
   <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <!-- 属性值注入 -->
        <property name="driverClass" value=""></property>
        <property name="jdbcUrl" value=""></property>
        <property name="user" value=""></property>
        <property name="password" value=""></property>
    </bean>
        
   <!-- 配置事务管理器 -->
   <bean id="dataSourceTransactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <!-- 注入datasource -->
        <property name="dataSource" ref="dataSource"></property>
   </bean>
   
   <!-- 配置事务增强 -->
   <tx:advice id="txadvice" transaction-manager="dataSourceTransactionManager(配置事务管理器id值)">
        <!-- 做事务操作 -->
        <tx:attributes>
            <!-- 设置进行事务操作的方法匹配规则 
                <tx:method name="要用到事务的方法名称"/> 
                如:-->
            <tx:method name="txSave" propagation="REQUIRED(隔离级别,不设置时为默认值)"/>
            <tx:method name="tx*"/>
        </tx:attributes>
   </tx:advice>
   
   <!-- 配置切面 -->
   <aop:config>
        <!-- 切入点 -->
        <aop:pointcut expression="execution(* 类全路径.*(..))" id="pt"/>
        <!-- 切面
            advice-ref:配置事务增强的id值
            pointcut-ref:切入点id值 
            作用:把指定的增强用在指定的切入点上 -->
        <aop:advisor advice-ref="txadvice" pointcut-ref="pt"/>
   </aop:config>
   
</beans>
基于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:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" 
       xmlns:tx="http://www.springframework.org/schema/tx"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
   
   <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <!-- 属性值注入 -->
        <property name="driverClass" value=""></property>
        <property name="jdbcUrl" value=""></property>
        <property name="user" value=""></property>
        <property name="password" value=""></property>
    </bean>
        
   <!-- 配置事务管理器 -->
   <bean id="dataSourceTransactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <!-- 注入datasource -->
        <property name="dataSource" ref="dataSource"></property>
   </bean>
   
   <!-- 开启注解事务扫描 
        transaction-manager:配置事务管理器id值-->
   <tx:annotation-driven transaction-manager="dataSourceTransactionManager">

</beans>
基于注解方式

    在需要用事务的方法所在类上方添加注解@Transactional 。添加注解后,会对该类的所有方法进行事务操作。

@Transactional
public class TestService{

}

 

posted @ 2019-03-11 15:51  水痕灬  阅读(187)  评论(0编辑  收藏  举报