zoukankan      html  css  js  c++  java
  • Spring JDBC 和 事务 的基本使用

    Spring JDBC

    一、    作用

    方便我们操作数据库;

    二、    基本使用

    1. 配置

    首先配置数据源(加载数据库驱动类、数据库URL、用户名密码…..);

    1. 注册JDBC模板

    即配置class=” org.springframework.jdbc.core.JdbcTemplate”的bean,我们需要使用该对象来对数据库进行操作;该bean需要配置dataSource属性,ref值为数据源bean;

    1. 通过继承JdbcDaoSupport类来使用jdbc模板

    该类已经编写了JdbcTemplate字段,只要继承该类,并在配置中注入JdbcTemplate字段的JDBC模板bean引用,便可以在JdbcDaoSupport子类中使用jdbc模板了,使用方式为: this.getJdbcTemplate().增删改查方法...;

    1. 直接使用JdbcTemplate对象来操作数据库

    即:JdbcTemplate 对象名 = Ioc容器对象名.getBean(“JDBC模板beanID”);

    这样可以不继承JdbcDaoSupport类;

    1. 单行 增删改

    this.getJdbcTemplate().update(sql语句, 参数1…,参数2,参数3,…..);

    增删改都是使用.update方法,参数列表是可变的,可以有任意个;该方法有返回值,返回受影响的行数

    1. 批量 增删改

    this.getJdbcTemplate().batchUpdate(sql语句, List<Objcet[]>参数);

    其中List<Object[]>保存每行参数值(比如:list对象.add(new Object[]{id,”name”,”phone”}))

    1. 查询一列数据

    一行:this.getJdbcTemplate().queryForObject(sql语句,数据类型.class,参数1,参数2,….);

    多行:this.getJdbcTemplate().queryForList(sql语句,数据类型.class,参数1,参数2,….);

    1. 查询多列数据

    this.getJdbcTemplate().queryForObject(sql, RowMapper对象, 参数1,参数2,….);

    其中RowMapper对象是查询到的列与一个对象的映射;

    创建RowMapper:

    (1)   RowMapper<对象> 实例名 =new BeanPropertyRowMapper<>(对象.class);

    (2)   写一个类,实现RowMapper<T>接口,T为要映射的对象,该接口中有方法mapRow(ResultSet参数,int参数),其中ResultSet参数表示当前行,使用参数名.get基本数据类型(数据库列名/列号)获取到指定列,而第二个参数是当前行号;

    (3)   无论是查询一行还是多行,Rowmapper会自动遍历,所有都用以上方法即可;

    1. 具名参数JDBC模板(NamedParameterJdbcTempate)

    该JDBC模板与JdbcTemplate作用一致,但可以在SQL语句中需要写入的参数名与JDBC模板的增删改查方法中的参数名相对应

    (0)   同样,需要先配置bean,该类的构造器是有参数的,配置时需要通过构造器注入方式把dataSource注入给它;

    (1)   原本JdbcTemplate对象中的增删改查SQL语句需要参数时,就使用?号当作一个占位符,然后在方法中按sql语句参数顺序来写入参数;

    例:sql=”select * from table where id=? and name=? ”

             this.getJdbcTemplate().queryForObject(sql, RowMapper对象,id,name);

             这里id和name参数的顺序要和sql语句中参数顺序一致

    (2)   在具名参数JDBC模板中,用 :参数名 来占位,增删改差方法有一个map,该map键为sql语句中的参数名,值为需要操作的值;

    例:sql=”select * from table where id=:id and name=:name ”

    map.put(“id”,id值);  map.put(“name”,name值);

    具名参数JDBC模板对象.query(sql,map);

    (3)   也可以使用.update(sql语句, SqlParameterSource对象)来操作;

    其中:SqlParameterSource 对象名= new BeanPropertySqlParameterSource(对象实例);

    这样可以将对象封装在一起,方便写入,需要注意的是,该方法sql语句占位符中名字需要和对象里的字段对应;

    Spring 事务

    〇、作用

    1. 事务具有ACID特性;
    2. 用来确保数据的完整性和一致性;
    3. 和数据库的事务是同一个意思;
    4. 其底层实现实质也是Java的动态代理

    基于注解使用事务

    1. 使用事务时,需要引入spring-tx的jar包,配置文件里也要引入tx命名空间

    1.在XML配置文件中配置事务管理器的bean,id随意,

    class=” org.springframework.jdbc.datasource.DataSourceTransactionManager”

    该bean还得配置dataSource属性;

    2.启用事务注解

    <tx:annotation-driven transaction-manager="transactionManager"/>

    3.使用注解

    在类的某一方法上写@Transactional,则该方法就使用了事务,里面的代码要么全部执行成功,要么就失败时回滚;

    1. 事务的传播行为

    (0)   意义:指定一个事务方法被另一个事务方法调用时,应该如何传播;

    (1)   例如:方法A是购买一张电影票;方法B里有个for循环调用方法A实现购买多张电影票;两个方法都实现了事务,当出现问题时(for到第二张时余额不足、电影票不足…),是应该全部失败回滚呢,还是余额不足那部分回滚?

    (2)   默认地,出现问题时,是全部失败(即方法A(被调用方法)的事务挂起,在方法B(调用方法)的事务内运行);

    (3)   也可以在被调用方法上的@Transactional内加上参数:

    propagation=Propagation.REQUIRES_NEW

    实现运行到被调用的方法A时,方法B就挂起(即余额不足那部分回回滚,余额与电影票充足的部分就购买成功);

    (4)   需要注意,使用事务传播行为时,调用方法和被调用方法应在不同的类里;

    1. 事务的隔离级别
      1. 可在@Transactional内加上参数设置该事务方法的隔离级别 isolation=Isolation.级别

    1. ISOLATION_DEFAULT: 这是一个PlatfromTransactionManager默认的隔离级别,使用数据库默认的事务隔离级别.

     另外四个与JDBC的隔离级别相对应

    2. ISOLATION_READ_UNCOMMITTED: 这是事务最低的隔离级别,它充许令外一个事务可以看到这个事务未提交的数据。这种隔离级别会产生脏读,不可重复读和幻像读。

    3. ISOLATION_READ_COMMITTED: 保证一个事务修改的数据提交后才能被另外一个事务读取。另外一个事务不能读取该事务未提交的数据

    4. ISOLATION_REPEATABLE_READ: 这种事务隔离级别可以防止脏读,不可重复读。但是可能出现幻像读。它除了保证一个事务不能读取另一个事务未提交的数据外,还保证了避免下面的情况产生(不可重复读)。

    5. ISOLATION_SERIALIZABLE 这是花费最高代价但是最可靠的事务隔离级别。事务被处理为顺序执行。除了防止脏读,不可重复读外,还避免了幻像读。

    1. 指定回滚
      1. 事务默认回滚异常为运行时异常(即方法运行时异常时,事务就回滚)
      2. 可在@Transactional中加参数,指定哪些异常回滚,哪些异常不回滚
      3. noRollbackFor/ noRollbackForClassNama ,  rollbackFor/ rollbackForClassNama

    前者不回滚,异常也会抛出,但修改了的数据不会回到执行前

    后者指定哪些异常要回滚

    1. 指定超时时间

    在@Transactional 内加入timeout参数(值为整数,单位秒),指定该事务方法执行的时间,当方法执行超时时,会抛出超时异常;

    一、基于XML文件使用事务(AspectJ框架)

    1. bean的配置如常,事务管理器配置如上;
    1. 不需要写 启用事务注解 的标签了;
    1. 配置事务的属性(类似AspectJ AOP的切面)

    <tx:advice id=”id随意”  transaction-manager=”事务管理器的ID”>

      <tx:attributes>

              <tx:method name=”仅方法名(可用*号模糊匹配)”  各属性(比如传递、指定回滚、只读、超时….) propagation=”REQUIRES_NEW” />

              ….

    若仅使用默认属性配置,则<tx:method name=”*” />

    1. 配置事务切入点(同AspectJ AOP),将方法、事务管理器和事务属性关联

    <aop:config>

      写切入点表达式<aop: expression……>

     关联<aop:advisor advice-ref=”事务属性id”  pointcut-ref=”切入点表达式id” />

    二、基于XML文件使用事务(Spring 自带的Aop框架)

    1. bean的配置如常,事务管理器配置如上;
    2. 不需要写 启用事务注解 的标签了;
    3. 生成事务代理:

    <bean id=”随意ID”

    class=”org.springframework.transaction.interceptor.TransactionProxyFactoryBean”>

    事务管理器<property name=”transactionManager” ref=”事务管理器beanID”>

    目标对象<property name=” target” ref=”目标对象beanID” >

    事务参数<property name=”transactionAttributes”>

                           <props>

                                  <prop key=”目标对象里的方法(仅方法名,可用*模糊匹配)”>

                                          各个参数值用逗号隔开(参数值比如PROPAGATION_RREQUIRED…)

                                  </prop>

                           ……

    其它:一个props里可以有多个prop;

    事务属性参数值请查阅API文档;

    -异常类名 表示发生此异常时回滚,+异常类名 表示发生此异常时不回滚。

    ps.请自行查阅开发过程中需要使用的jar包

  • 相关阅读:
    js总结 |数组重复问题
    前端Js自定义相机取景框
    nodejs+mongodb运用
    使用MongoDB
    总结 |异步/非阻塞的处理方式
    npm与依赖包
    js总结 |JS深度拷贝的方法
    js笔记 |整洁代码技巧
    微信支付——介入指引
    2021最全测试资源合集(已更新至2021.03.09,关注测试生财公众号,享受独家爆料)
  • 原文地址:https://www.cnblogs.com/Drajun/p/8278843.html
Copyright © 2011-2022 走看看