BaseDao的好处就是减少代码量,看起不会冗余。
关键点设计
-
BaseDao如何得知要处理的具体类型呢?
未来要处理的类型是不确定性的
采用泛型设计 -
BaseDao在内部方法处理时,
如何知道要处理的具体类型?
在实际的运行期间,需要把这个类型给明确化采用反射技术 -
BaseDao完成更新方法的抽取 (增删改)
方法设计的四要素:返回类型 方法名,方法参数,方法体
方法体方法名: update
方法参数:变化的东西,SQL+参数值
方法体:共性的结构 -
BaseDao完成查询方法的抽取
方法设计的四要素: 返回类型 方法名,方法参数,方法体
返回类型:集合List,单个对象,数值 要不要整成一个方法?code review
结论:整成三个方法方法名: getBeanList,getBean,getValue方法参数: SQL+参数列表
配置文件
# 驱动名称(连接Mysql)
driverClassName = com.mysql.cj.jdbc.Driver
# 参数?rewriteBatchedStatements=True表示支持批处理机制
url = jdbc:mysql://localhost:3306/goodsdb?useSSL=false
# 用户名,注意这里是按"userName"来读取的
username = root
# 用户密码(自己改)
password = sasa
Util工具类
主要就是获取连接和关闭连接
import com.alibaba.druid.pool.DruidDataSourceFactory;
import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties;
public class JDBCUtil {
private static final DataSource dataSource;
// 静态代码块,它只在第一次创建对象的时候
// 只执行一次,后面创建对象不会执行
static{
// 配置文件加载类
Properties properties = new Properties();
try {
//配置文件加载,因为他有时相对路径找不到,所以放绝对路径
properties.load(Files.newInputStream(Paths.get("F:\Web\javaWeb2024\src\main\resources\driuid.properties")));
dataSource = DruidDataSourceFactory.createDataSource(properties);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
public static Connection getConnection(){
try {
return dataSource.getConnection();
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
public static void close(AutoCloseable autoCloseable){
if(autoCloseable != null){
try {
autoCloseable.close();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
public static void close(Statement statement,Connection connection){
close(statement);
close(connection);
}
public static void close(Statement statement, Connection connection, ResultSet resultSet){
close(statement);
close(connection);
close(resultSet);
}
}
更新(增删改)
/**
* 增删改方法
* @param sql 执行的sql
* @param args sql参数
* @return 影响行数
*/
public int update(String sql, Object... args) {
Connection connection = null;
PreparedStatement preparedStatement = null;
int row = 0;
try {
connection = JDBCUtil.getConnection();
preparedStatement = connection.prepareStatement(sql);
for (int i = 0; i < args.length; i++) {
preparedStatement.setObject(i + 1, args[i]);
}
return preparedStatement.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
} finally {
JDBCUtil.close(preparedStatement, connection);
}
return row;
}
查询单个对象
/**
*查询单个对象
*/
public T getBean(String sql, Object... args) {
PreparedStatement preparedStatement = null;
ResultSet resultSet = null;
Connection connection = JDBCUtil.getConnection();
T t = null;
try {
preparedStatement = connection.prepareStatement(sql);
for (int i = 0; i < args.length; i++) {
preparedStatement.setObject(i + 1, args[i]);
}
resultSet = preparedStatement.executeQuery();
//获取到ResultSetMetaData元数据,获取到实际查询有几列
ResultSetMetaData metaData = resultSet.getMetaData();
int columnCount = metaData.getColumnCount();
if (resultSet.next()) {
t = targetClass.newInstance();
//将每条数据库记录转换为每个对象
//难点一:要获取到实际处理的类型的属性
//难点二:按需赋值
for (int i = 0; i < columnCount; i++) {
//获取到属性名
String columnLabel = metaData.getColumnLabel(i + 1);
//获取到属性值
Object object = resultSet.getObject(columnLabel);
//得到对象属性给属性赋值
Field field = targetClass.getDeclaredField(
underToCamel(columnLabel));
String type = null;
if (object != null) {
type = object.getClass().getName();
/*
* 时间类型特殊处理
* 获取到mysql时间类型的值,转为其真正类型通过debug发现mysql
* 在java中储存时间是用java.time.LocalDateTime类型存储的
* 而不是java.sql.Timestamp类型或者直接使用java.time.LocalDateTime
*/
if ("java.time.LocalDateTime".equalsIgnoreCase(type)) {
Timestamp timestamp = Timestamp.valueOf


1369

被折叠的 条评论
为什么被折叠?



