引言
数据存储是当今商业运行必不可少的一部分,数据库相关的开发工作更是计算机软件开发人员在日常工作中最频繁涉及的内容。数据库开发的技术经过这么多年的发展已经相当成熟,特别是应用spring+mybaies的方案后业务开发同学仅需要做很少的工作就可以正常执行数据库的增删改查,把业务同学从繁琐的数据库链接维护等工作中解放出来可以专注于业务开发。但提供方便的同时也把很多技术细节封闭起来,导致很多同学对数据库访问技术知其然不知其所以然,典型的情况就是出了问题不知从何排查、只定义了一个接口和xml配置文件为何就能查出数据了。
阅读完本文你可以掌握以下知识:
- SpringJpa/Springboot+mybatis的运行原理,通常包含启动过程和查询(增删改查)过程两部分
- 部分阅读源代码的经验,特别是在springboot开发模式下
本文使用的开发环境和工具:
- 开发工具:idea
- 数据库:mysql
- JDK:JDK8
- 应用形式:springboot
- springboot版本:2.6.4
你可以在这里下载到调试源代码: https://github.com/hzgeyule/lean.git
另外本文假设你已经有了数据库开发的经验且用过springjpa+mybatis
Java访问数据库的方式
当前访问数据库最流行的方式是springJpa+mybaties。几年前有很多只使用springJpa的方式。更早之前就是最原始的方式,需要自己链接数据库驱动维护数据库链。最推荐的方式是第一种,在本文之所以提到后面的两种是为了追本溯源把第一种的原理讲清楚。
在介绍具体的使用方法之前先建一张表供测试使用
CREATE TABLE `t_user` (
`userid` varchar(10) NOT NULL,
`username` varchar(255) DEFAULT NULL,
`sex` varchar(2) DEFAULT NULL,
`age` int DEFAULT NULL,
PRIMARY KEY (`userid`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci
原始方式
最原始的数据库访问分为有几个步骤:
1、 加载数据库驱动 2、 创建并获取数据库链接 3、 创建jdbcstatement对象 4、 设置sql语句 5、 设置sql语句中的参数(使用preparedStatement) 6、 通过statement执行sql并获取结果 7、 对sql执行结果进行解析处理 8、 释放资源(resultSet、preparedstatement、connection)
代码一般如下:
try {
// 加载数据库驱动
Class.forName("com.mysql.jdbc.Driver");
// 通过驱动管理类获取数据库链接
connection = DriverManager
.getConnection(
"jdbc:mysql://localhost:3306/mybatistest?characterEncoding=utf-8",
"root", "1234");
// 定义sql语句 ?表示占位符
String sql = "select * from user where username = ?";
// 获取预处理statement
preparedStatement = connection.prepareStatement(sql);
// 设置参数,第一个参数为sql语句中参数的序号(从1开始),第二个参数为设置的参数值
preparedStatement.setString(1, "赵六");
// 向数据库发出sql执行查询,查询出结果集
resultSet = preparedStatement.executeQuery();
// 遍历查询结果集
while (resultSet.next()) {
System.out.println(resultSet.getString("id") + " "
+ resultSet.getString("username"));
}
} catch (Exception e) {
e.printStackTrace();
} finally {
// 释放资源
if (resultSet != null) {
try {
resultSet.close();
} catch (SQLException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
if (preparedStatement != null) {
try {
preparedStatement.close();
} catch (SQLException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
if (connection != null) {
try {
connection.close();
} catch (SQLException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
}
springjpa
该方式有以下几部分代