儿童学做彩泥的网站,江门网站建设外包,跨境电商网站开发公司,网站群 主要功能基本介绍#xff1a;通过 Spring 框架可以配置数据源#xff0c;从而完成对数据表的操作。JdbcTemplate 是 Spring 提供的访问数据库的技术。将 JDBC 的常用操作封装为模板方法
1 JdbcTemplate 使用前需进行如下配置 1.1 在maven项目的pom文件加入以下依赖 dependencies…基本介绍通过 Spring 框架可以配置数据源从而完成对数据表的操作。JdbcTemplate 是 Spring 提供的访问数据库的技术。将 JDBC 的常用操作封装为模板方法
1 JdbcTemplate 使用前需进行如下配置
1.1 在maven项目的pom文件加入以下依赖 dependencies!--加入c3p0数据源包--dependencygroupIdcom.mchange/groupIdartifactIdc3p0/artifactIdversion0.9.5.2/version/dependency!--加入mysql连接--dependencygroupIdmysql/groupIdartifactIdmysql-connector-java/artifactIdversion8.0.31/version/dependency!--加入spring新增的依赖 spring-jdbc这个依赖中有JdbcTemplate--dependencygroupIdorg.springframework/groupIdartifactIdspring-jdbc/artifactIdversion5.3.8/version/dependency!--加入spring开发的基本包--dependencygroupIdorg.springframework/groupIdartifactIdspring-context/artifactIdversion5.3.8/version/dependency!--加入spring开发切面编程需要的包--dependencygroupIdorg.springframework/groupIdartifactIdspring-aspects/artifactIdversion5.3.8/version/dependency
/dependencies 1.2 创建配置文件 resources/jdbc.properties #配置用户名
jdbc.userNameroot
#密码
jdbc.password123456
jdbc.driverClasscom.mysql.cj.jdbc.Driver
#指定要连接的数据库这里连接spring数据库
jdbc.urljdbc:mysql://localhost:3306/spring 1.3 创建配置文件 resources/JdbcTemplate_ioc.xml ?xml version1.0 encodingUTF-8?
beans xmlnshttp://www.springframework.org/schema/beansxmlns:xsihttp://www.w3.org/2001/XMLSchema-instancexmlns:contexthttp://www.springframework.org/schema/contextxsi:schemaLocationhttp://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd!--引入外部的jdbc.properties配置文件--context:property-placeholder locationclasspath:jdbc.properties/!--配置数据源对象-DataSource--bean classcom.mchange.v2.c3p0.ComboPooledDataSource iddataSourceproperty nameuser value${jdbc.userName}/property namepassword value${jdbc.password}/property namedriverClass value${jdbc.driverClass}/property namejdbcUrl value${jdbc.url}//bean!--配置JdbcTemplate对象--bean idjdbcTemplate classorg.springframework.jdbc.core.JdbcTemplate!--给jdbcTemplate对象配置dataSource属性--property namedataSource refdataSource//bean
/beans 接下来就可以开始使用JdbcTemplate对象来操作数据库了 2 JdbcTemplate对象常用操作
为成功演示以下操作需提前进行如下准备
执行如下sql语句
-- 创建数据库
CREATE DATABASE spring;
USE spring
-- 创建表 monster
CREATE TABLE monster(
id INT PRIMARY KEY, name VARCHAR(64) NOT NULL DEFAULT ,
skill VARCHAR(64) NOT NULL DEFAULT )CHARSETutf8mb4
INSERT INTO monster VALUES(100, 青牛怪, 吐火);
INSERT INTO monster VALUES(200, 黄袍怪, 吐烟);
INSERT INTO monster VALUES(300, 蜘蛛怪, 吐丝);
创建Monster.java
package com.spring.bean;public class Monster {private Integer monsterId;private String name;private String skill;//全参构造器public Monster(Integer monsterId, String name, String skill) {this.monsterId monsterId;this.name name;this.skill skill;}//无参构造器一定要写Spring反射创建对象时需要使用public Monster() {}public Integer getMonsterId() {return monsterId;}public void setMonsterId(Integer monsterId) {this.monsterId monsterId;}public String getName() {return name;}public void setName(String name) {this.name name;}public String getSkill() {return skill;}public void setSkill(String skill) {this.skill skill;}Overridepublic String toString() {return Monster{ monsterId monsterId , name name \ , skill skill \ };}
}2.1 添加单条数据
2.1.3 方式1使用 void execute(final String sql) 方法
//测试通过JdbcTemplate对象完成添加数据
Test
public void addDataByJdbcTemplate(){//获取到容器ApplicationContext ioc new ClassPathXmlApplicationContext(jdbcTemplate_ioc.xml);JdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);//添加方式1String sql INSERT INTO monster VALUES(400, 红孩儿, 枪法);jdbcTemplate.execute(sql);
}
2.1.3 方式2使用 int update(String sql, Nullable Object... args) 方法 //测试通过JdbcTemplate对象完成添加数据Testpublic void addDataByJdbcTemplate(){//获取到容器ApplicationContext ioc new ClassPathXmlApplicationContext(jdbcTemplate_ioc.xml);JdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);//添加方式2String sql INSERT INTO monster VALUES(?, ?, ?);int affected jdbcTemplate.update(sql, 500, 红孩儿2, 枪法2);System.out.println(add ok affected affected);}
2.2 修改数据
方法public int update(String sql, Nullable Object... args)
//测试通过JdbcTemplate对象完成修改数据
Test
public void updateDataByJdbcTemplate(){//获取到容器ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//获取JdbcTemplate对象JdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);//组织sqlString sql UPDATE monster SET skill ? WHERE id ?;int affected jdbcTemplate.update(sql, 美人计, 300);System.out.println(update ok affected affected);
}
2.3 批量添加数据
方法public int[] batchUpdate(String sql, ListObject[] batchArgs)
//测试通过JdbcTemplate对象完成批量添加数据
Test
public void addBatchDataByJdbcTemplate(){//获取到容器ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//获取JdbcTemplate对象JdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);String sql INSERT INTO monster VALUES(?, ?, ?);ListObject[] batchArgs new ArrayList();batchArgs.add(new Object[]{600, 红孩儿3, 枪法3});batchArgs.add(new Object[]{700, 红孩儿4, 枪法4});batchArgs.add(new Object[]{800, 红孩儿5, 枪法5});jdbcTemplate.batchUpdate(sql,batchArgs);System.out.println(batch add ok...);
}
2.4 将单条查询数据封装到对象
方法public T T queryForObject(String sql, RowMapperT rowMapper, Object... args)
//查询id100的monster并封装到Monster实体对象
Test
public void selectDataByJdbcTemplate() {ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//得到JdbcTemplate beanJdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);//组织SQL//通过BeanPropertyRowMapper获取,rowmapper 是一个接口可以将查询的结果封装到你指定的Monster对象中.//1. 确定API queryForObject()//public T T queryForObject(String sql, RowMapperT rowMapper, Nullable Object... args)//2.准备参数String sql SELECT id AS monsterId, NAME, skill FROM monster WHERE id ?;//使用RowMapper 接口来对返回的数据进行一个封装-》底层使用的反射-setter//这里有一个细节: 你查询的记录的表的字段需要和 Monster的对象字段名保持一致RowMapperMonster rowMapper new BeanPropertyRowMapper(Monster.class);//jdbcTemplateMonster monster jdbcTemplate.queryForObject(sql, rowMapper, 100);System.out.println(monster monster);System.out.println(查询ok);
}
2.5 封装多条查询数据
方法public T T query(String sql, RowMapperT rowMapper, Object... args)
//查询id200的monster并封装到Monster实体对象
/*** 查询多条记录*/
Test
public void selectMulDataByJdbcTemplate() {ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//得到JdbcTemplate beanJdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);//组织SQL//通过BeanPropertyRowMapper获取rowmapper 是一个接口可以将查询的结果封装到你指定的Monster对象中.//1. 确定API//public T T query(String sql, RowMapperT rowMapper, Object... args){}//2. 组织参数String sql SELECT id AS monsterId, NAME, skill FROM monster WHERE id ?;RowMapperMonster rowMapper new BeanPropertyRowMapper(Monster.class);//3. 调用ListMonster monsterList jdbcTemplate.query(sql, rowMapper, 100);for (Monster monster : monsterList) {System.out.println(monster monster);}
}
2.6 查询返回结果只有一行一列的值
方法public T T queryForObject(String sql, ClassT requiredType)
//查询返回结果只有一行一列的值比如查询id100的怪物名
/*** 查询返回结果只有一行一列的值*/
Test
public void selectScalarByJdbcTemplate() {ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//得到JdbcTemplate beanJdbcTemplate jdbcTemplate ioc.getBean(JdbcTemplate.class);//1. 确定API//public T T queryForObject(String sql, ClassT requiredType)//2. 提供参数String sql SELECT NAME FROM monster WHERE id 100;//ClassT requiredType 表示你返回的单行单列的数据类型String name jdbcTemplate.queryForObject(sql, String.class);System.out.println(返回name name);
}
2.7 使用具名参数完成操作
在resources/JdbcTemplate_ioc.xml配置文件中增加如下配置
!--配置NameParameterJdbcTemplate支持具名参数--
bean classorg.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplateidnamedParameterJdbcTemplate!--这里需要使用构造器关联数据源--constructor-arg namedataSource refdataSource/
/bean
方法public int update(String sql, MapString, ? paramMap)
/*** 使用Map传入具名参数完成操作比如添加*/
Test
public void testDataByNamedParameterJdbcTemplate() {ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//得到NamedParameterJdbcTemplate beanNamedParameterJdbcTemplate namedParameterJdbcTemplate ioc.getBean(NamedParameterJdbcTemplate.class);//1. 确定使用API//public int update(String sql, MapString, ? paramMap)//2. 准备参数 [:my_id, :name, :skill] 要求按照规定的名字来设置参数String sql INSERT INTO monster VALUES(:id, :name, :skill);MapString, Object paramMap new HashMap();//给paramMap填写数据paramMap.put(id, 900);paramMap.put(name, 蚂蚁精);paramMap.put(skill, 喜欢打洞);//3. 调用int affected namedParameterJdbcTemplate.update(sql, paramMap);System.out.println(add ok affected affected);
}
2.8 使用sqlparametersoruce 来封装具名参数
方法public int update(String sql, SqlParameterSource paramSource)
//使用sqlparametersoruce 来封装具名参数,还是添加一个Monster 狐狸精
Test
public void operDataBySqlparametersoruce() {ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);//得到NamedParameterJdbcTemplate beanNamedParameterJdbcTemplate namedParameterJdbcTemplate ioc.getBean(NamedParameterJdbcTemplate.class);//确定API//public int update(String sql, SqlParameterSource paramSource)//public BeanPropertySqlParameterSource(Object object)//准备参数String sql INSERT INTO monster VALUES(:monsterId, :name, :skill);Monster monster new Monster(1000, 大象精, 搬运木头);SqlParameterSource sqlParameterSource new BeanPropertySqlParameterSource(monster);//调用int affected namedParameterJdbcTemplate.update(sql, sqlParameterSource);System.out.println(add ok affected affected);
}
2.9 Dao 对象中使用 JdbcTemplate 完成对数据的操作
创建 MonsterDao.java
package com.spring.dao;import com.spring.bean.Monster;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Repository;import javax.annotation.Resource;public class MonsterDao {private JdbcTemplate jdbcTemplate;//完成保存任务public void save(Monster monster){//组织sqlString sql INSERT INTO monster VALUES(?,?,?);jdbcTemplate.update(sql, monster.getMonsterId(), monster.getName(), monster.getSkill());}public JdbcTemplate getJdbcTemplate() {return jdbcTemplate;}public void setJdbcTemplate(JdbcTemplate jdbcTemplate) {this.jdbcTemplate jdbcTemplate;}
}在resources/JdbcTemplate_ioc.xml配置文件中增加如下配置
!--配置monsterDao对象--
bean classcom.spring.dao.MonsterDao idmonsterDaoproperty namejdbcTemplate refjdbcTemplate/
/bean
编写测试代码
//测试MonsterDAO
Test
public void monsterDaoSave() {ApplicationContext ioc new ClassPathXmlApplicationContext(JdbcTemplate_ioc.xml);MonsterDao monsterDao ioc.getBean(MonsterDao.class);Monster monster new Monster(1100, 小鸭精, 吃鱼);monsterDao.save(monster);System.out.println(MonsterDAO保存 ok ..);
}
3 声明式事务
3.1 声明式事务的基本使用
1在xml文件中加入以下配置
!--配置事务管理器-对象
1. DataSourceTransactionManager 这个对象是进行事务管理-debug源码
2. 一定要配置数据源属性这样指定该事务管理器 是对哪个数据源进行事务控制
--
bean classorg.springframework.jdbc.datasource.DataSourceTransactionManager idtransactionManagerproperty namedataSource refdataSource/
/bean!--配置启动基于注解的声明式事务管理功能--
tx:annotation-driven transaction-managertransactionManager/
2在方法上添加注解Transaction 即可将该方法作为一个事务来处理前提是该方法所在的类被注入到了容器中
/*** Transactional 注解解读* 1. 使用Transactional 可以进行声明式事务控制* 2. 即将标识的方法中的对数据库的操作作为一个事务管理* 3. Transactional 底层使用的仍然是AOP机制* 4. 底层是使用动态代理对象来调用buyGoodsByTx* 5. 在执行buyGoodsByTx() 方法 先调用 事务管理器的 doBegin() , 调用 buyGoodsByTx()* 如果执行没有发生异常则调用 事务管理器的 doCommit(), 如果发生异常 调用事务管理器的 doRollback()进行回调*/
Transactional
public void buyGoodsByTx(int userId, int goodsId, int amount) {//输出购买的相关信息System.out.println(用户购买信息 userId userId goodsId goodsId 购买数量 amount);//1.得到商品的价格Float price goodsDao.queryPriceById(userId);//2. 减少用户的余额goodsDao.updateBalance(userId, price * amount);//3. 减少库存量goodsDao.updateAmount(goodsId, amount);System.out.println(用户购买成功~);
}
3.2 事务的传播机制
当有多个事务处理并存时可以使用事务的传播机制去控制比如用户去购买两次商品(使用不同的方法), 每个方法都是一个事务
1事务传播机制种类 REQUIRED 和 REQUIRED_NEW 传播机制示意图 事务的传播机制的设置方法 REQUIRES_NEW 和 REQUIRED 在处理事务的策略 1如果设置为 REQUIRES_NEW buyGoods2 如果错误不会影响到 buyGoods() 反之亦然即它们的事务是独立的 . 2 如果设置为 REQUIRED buyGoods2 和 buyGoods 是一个整体只要有方法的事务错误那么两个方法都不 会执行成功 3.3 事务隔离级别
3.3.1 事务隔离级别种类(事务相关知识点这篇有详细介绍mysql基础知识汇总) 3.3.2 事务隔离级别的设置
Transactional(propagation Propagation.REQUIRES_NEW, isolation Isolation.DEFAULT)
public void buyGoodsByTx2(int userId, int goodsId, int amount) {
在默认情况下 声明式事务的隔离级别是 REPEATABLE_READ . 我们将buyGoodsByTxISOLATION的隔离级别设置为 Isolation.READ_COMMITTED ,表示只要是提交的数据在当前事务是可以读取到最新数据
Transactional(isolation Isolation.READ_COMMITTED)
public void buyGoodsByTxISOLATION() {
3.4 事务的超时回滚
介绍如果一个事务执行的时间超过某个时间限制就让该事务回滚。
设置方式如下 timeout 2 表示 buyGoods如果执行时间超过了2秒 , 该事务就进行回滚. 如果没有设置 timeout, 默认是 -1表示使用事务的默认超时时间, 或者不支持