package com.csy.dao; import com.csy.config.ConfigMng; import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; import java.sql.*; import java.time.LocalDateTime; import java.util.ArrayList; import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; /** * @Description: 管理数据库的连接与释放 * @Author: windStop * @Date: 2024/5/20 16:38 */ public class BaseDao { public Connection connection = null; public PreparedStatement pStatement = null; public ResultSet resultSet = null; //使用配置文件的方式进行解耦合,可以在无需重新编译的基础上进行修改内容 public boolean getConnection() { try { ConfigMng configMng = ConfigMng.getInstance(); Class.forName(configMng.getString("jdbc.driver")); String url = configMng.getString("jdbc.url"); connection = DriverManager.getConnection(url, configMng.getString("jdbc.username"), configMng.getString("jdbc.password")); } catch (Exception e) { e.printStackTrace(); return false; } return true; } public boolean closeResource() { try { if (resultSet != null) resultSet.close(); if (pStatement != null) pStatement.close(); if (connection != null) connection.close(); } catch (SQLException e) { e.printStackTrace();//把异常信息打印在控制台中 return false; } return true; } /** * 封装增删改操作 * @param sql sql语句 * @param params 参数占位符 ?的填充的内容 * @return 影响了多少条数据 */ public int executeUpdate(String sql, Object[] params) { if (getConnection()) { //1.执行sql语句 try { pStatement = connection.prepareStatement(sql); //2.填充占位符 for (int i = 0; i < params.length; i++) { pStatement.setObject(i + 1,params[i]); } return pStatement.executeUpdate(); } catch (SQLException e) { throw new RuntimeException(e); }finally { closeResource(); } } return 0; } /** * 通过拆解出where条件后面跟的条件,然后遍历javabean的属性找到相应的进行插入。最后将结果ResultSet映射到javabean中返回 * @param sql sql语句 * @param obj 调用者传来的javabean * @return 查询到的javabean集合 * @paramjavabean的泛型 */ public List executeQuery(String sql, T obj) throws IllegalAccessException, SQLException { List resultList = new ArrayList<>(); if (getConnection()) { pStatement = connection.prepareStatement(sql); // 使用反射获取对象的属性值 Class> clazz = obj.getClass(); //获取该对象中的所有属性(包括私有)所有字段 Field[] fields = clazz.getDeclaredFields(); List conditionFields = extractConditionFields(sql); for (int i = 0; i < conditionFields.size(); i++) { // 填充占位符内容 for (Field field : fields) { //私有暴力反射 设置可访问私有字段 field.setAccessible(true); if (field.getName().equals(conditionFields.get(i))){//找到相等的了 //接受一个对象实例作为参数,返回该对象实例中对应字段的值。 Object value = field.get(obj); pStatement.setObject(i + 1,value); break; } } } resultSet = pStatement.executeQuery(); while (resultSet.next()) { // 根据泛型类型创建对象并填充数据 T resultObj = (T)createObjectFromResultSet(resultSet, clazz); resultList.add(resultObj); } } return resultList; } //将resultSet的返回值封装到泛型对象中,并且返回(这里我没有处理表名映射下划线和驼峰) private T createObjectFromResultSet(ResultSet resultSet, Class clazz) throws SQLException { T obj; try { obj = clazz.getDeclaredConstructor().newInstance(); Field[] fields = clazz.getDeclaredFields(); for (Field field : fields) { field.setAccessible(true); String fieldName = field.getName(); Class> fieldType = field.getType(); // 根据字段类型从结果集中获取相应的值 if (fieldType == String.class) { String value = resultSet.getString(fieldName); field.set(obj, value); } else if (fieldType == Integer.class || fieldType == int.class) { int value = resultSet.getInt(fieldName); field.set(obj, value); } else if (fieldType == Date.class) { Date value = resultSet.getDate(fieldName); field.set(obj, value); } else if (fieldType == LocalDateTime.class) { Timestamp timestamp = resultSet.getTimestamp(fieldName); LocalDateTime value = timestamp.toLocalDateTime(); field.set(obj, value); } else { // 其他类型的处理... 想到在写 } } } catch (InstantiationException | IllegalAccessException | NoSuchMethodException | InvocationTargetException e) { throw new SQLException("Error creating object from ResultSet", e); } return obj; } //截取出where条件中的所有字段条件的名称 public List extractConditionFields(String sql) { List conditionFields = new ArrayList<>(); // 使用正则表达式匹配 WHERE 子句 Pattern wherePattern = Pattern.compile("where(.*)", Pattern.CASE_INSENSITIVE); Matcher whereMatcher = wherePattern.matcher(sql); if (whereMatcher.find()) { String whereClause = whereMatcher.group(1).trim(); // 使用正则表达式匹配条件字段 Pattern conditionPattern = Pattern.compile("(\\w+)\\s?=\\s?"); Matcher conditionMatcher = Pattern.compile("and", Pattern.CASE_INSENSITIVE).matcher(whereClause); int lastIndex = 0; while (conditionMatcher.find()) { String condition = whereClause.substring(lastIndex, conditionMatcher.start()).trim(); Matcher fieldMatcher = conditionPattern.matcher(condition); if (fieldMatcher.find()) { conditionFields.add(fieldMatcher.group(1)); } lastIndex = conditionMatcher.end(); } // 处理最后一个条件 String lastCondition = whereClause.substring(lastIndex).trim(); Matcher lastFieldMatcher = conditionPattern.matcher(lastCondition); if (lastFieldMatcher.find()) { conditionFields.add(lastFieldMatcher.group(1)); } } return conditionFields; } }