网站后端连接数据库知识点大全(一)

简介: 教程来源:https://dnuhf.cn/article/162.html 本文系统梳理Web后端数据库连接核心知识:涵盖JDBC原理、主流驱动配置、PreparedStatement防注入、批处理;深入解析HikariCP、Druid、Tomcat JDBC三大连接池;详解Spring中数据源配置、JdbcTemplate及多数据源实践,助开发者构建高效、安全、稳定的数据库访问体系。

在 Web 开发中,后端与数据库的连接是核心环节之一。无论是简单的博客系统还是复杂的企业级应用,都离不开高效、安全、稳定的数据库连接。本文将系统全面地梳理网站后端连接数据库的核心知识点,从连接原理到最佳实践,涵盖 JDBC、连接池、ORM 框架、事务管理、性能优化等各个方面,帮助开发者建立完整的知识体系。
7a473eda-a084-4614-8113-45f48ec7980b.png

一、数据库连接基础

1.1 数据库连接原理

应用服务器 → 数据库驱动 → 网络连接 → 数据库服务器
     ↓            ↓           ↓           ↓
  连接请求 → 建立连接 → 传输数据 → 执行SQL → 返回结果

连接过程:
加载数据库驱动
建立网络连接(TCP/IP)
进行身份认证
创建会话
执行 SQL 语句
返回结果
关闭连接(释放资源)

1.2 数据库驱动
常用 JDBC 驱动:

xml
<!-- Maven 依赖 -->
<!-- MySQL -->
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>8.0.33</version>
</dependency>

<!-- PostgreSQL -->
<dependency>
    <groupId>org.postgresql</groupId>
    <artifactId>postgresql</artifactId>
    <version>42.6.0</version>
</dependency>

<!-- Oracle -->
<dependency>
    <groupId>com.oracle.database.jdbc</groupId>
    <artifactId>ojdbc8</artifactId>
    <version>21.9.0.0</version>
</dependency>

<!-- SQL Server -->
<dependency>
    <groupId>com.microsoft.sqlserver</groupId>
    <artifactId>mssql-jdbc</artifactId>
    <version>12.4.0.jre11</artifactId>
</dependency>

<!-- H2(内存数据库) -->
<dependency>
    <groupId>com.h2database</groupId>
    <artifactId>h2</artifactId>
    <version>2.2.220</version>
</dependency>

1.3 JDBC 基础连接

java
import java.sql.*;

public class JDBCDemo {

    // 数据库连接参数
    private static final String URL = "jdbc:mysql://localhost:3306/mydb?useSSL=false&serverTimezone=UTC";
    private static final String USERNAME = "root";
    private static final String PASSWORD = "123456";

    // 1. 基础连接示例
    public void basicConnection() {
        Connection conn = null;
        Statement stmt = null;
        ResultSet rs = null;

        try {
            // 加载驱动(可选,JDBC 4.0+ 自动加载)
            Class.forName("com.mysql.cj.jdbc.Driver");

            // 建立连接
            conn = DriverManager.getConnection(URL, USERNAME, PASSWORD);
            System.out.println("数据库连接成功");

            // 创建 Statement
            stmt = conn.createStatement();

            // 执行查询
            rs = stmt.executeQuery("SELECT * FROM users");

            // 处理结果
            while (rs.next()) {
                int id = rs.getInt("id");
                String name = rs.getString("username");
                System.out.println("ID: " + id + ", Name: " + name);
            }

        } catch (ClassNotFoundException e) {
            System.err.println("驱动加载失败: " + e.getMessage());
        } catch (SQLException e) {
            System.err.println("数据库连接失败: " + e.getMessage());
        } finally {
            // 关闭资源(顺序:ResultSet → Statement → Connection)
            try {
                if (rs != null) rs.close();
                if (stmt != null) stmt.close();
                if (conn != null) conn.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
    }

    // 2. PreparedStatement(防止 SQL 注入)
    public void preparedStatementExample() {
        String sql = "SELECT * FROM users WHERE username = ? AND age > ?";

        try (Connection conn = DriverManager.getConnection(URL, USERNAME, PASSWORD);
             PreparedStatement pstmt = conn.prepareStatement(sql)) {

            // 设置参数
            pstmt.setString(1, "张三");
            pstmt.setInt(2, 18);

            // 执行查询
            try (ResultSet rs = pstmt.executeQuery()) {
                while (rs.next()) {
                    System.out.println(rs.getString("username"));
                }
            }

        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    // 3. 批处理操作
    public void batchExample() {
        String sql = "INSERT INTO users (username, age) VALUES (?, ?)";

        try (Connection conn = DriverManager.getConnection(URL, USERNAME, PASSWORD);
             PreparedStatement pstmt = conn.prepareStatement(sql)) {

            // 关闭自动提交
            conn.setAutoCommit(false);

            // 添加批处理
            for (int i = 0; i < 1000; i++) {
                pstmt.setString(1, "user" + i);
                pstmt.setInt(2, 20 + i % 50);
                pstmt.addBatch();
            }

            // 执行批处理
            int[] results = pstmt.executeBatch();

            // 提交事务
            conn.commit();

            System.out.println("批量插入完成: " + results.length);

        } catch (SQLException e) {
            e.printStackTrace();
        }
    }
}

二、连接池技术

2.1 为什么需要连接池
不使用连接池的问题:
每次请求都需要创建和关闭连接,开销大
高并发时数据库连接数爆炸
资源浪费,性能低下
连接池的优势:
复用连接,减少创建/销毁开销
限制最大连接数,保护数据库
管理连接生命周期
提供连接健康检查

2.2 HikariCP(推荐)

xml
<!-- Maven 依赖 -->
<dependency>
    <groupId>com.zaxxer</groupId>
    <artifactId>HikariCP</artifactId>
    <version>5.0.1</version>
</dependency>
java
import com.zaxxer.hikari.HikariConfig;
import com.zaxxer.hikari.HikariDataSource;
import javax.sql.DataSource;

public class HikariCPDemo {

    // 配置方式1:编程式配置
    public DataSource createDataSource() {
        HikariConfig config = new HikariConfig();

        // 基础配置
        config.setJdbcUrl("jdbc:mysql://localhost:3306/mydb?useSSL=false&serverTimezone=UTC");
        config.setUsername("root");
        config.setPassword("123456");

        // 连接池大小配置
        config.setMaximumPoolSize(10);           // 最大连接数
        config.setMinimumIdle(5);                // 最小空闲连接
        config.setIdleTimeout(600000);            // 空闲超时(10分钟)
        config.setConnectionTimeout(30000);       // 连接超时(30秒)
        config.setMaxLifetime(1800000);           // 连接最大生命周期(30分钟)

        // 验证配置
        config.setConnectionTestQuery("SELECT 1");
        config.setValidationTimeout(5000);

        // 其他配置
        config.setPoolName("MyHikariPool");
        config.setRegisterMbeans(true);

        return new HikariDataSource(config);
    }

    // 配置方式2:配置文件方式
    // hikari.properties
    /*
    dataSourceClassName=com.mysql.cj.jdbc.MysqlDataSource
    dataSource.url=jdbc:mysql://localhost:3306/mydb
    dataSource.user=root
    dataSource.password=123456
    maximumPoolSize=10
    minimumIdle=5
    connectionTimeout=30000
    idleTimeout=600000
    maxLifetime=1800000
    */

    public DataSource createDataSourceFromFile() {
        HikariConfig config = new HikariConfig("/hikari.properties");
        return new HikariDataSource(config);
    }
}

2.3 Druid(阿里)

xml
<dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>druid</artifactId>
    <version>1.2.20</version>
</dependency>
java
import com.alibaba.druid.pool.DruidDataSource;
import javax.sql.DataSource;
import java.util.Properties;

public class DruidDemo {

    public DataSource createDataSource() {
        DruidDataSource dataSource = new DruidDataSource();

        // 基础配置
        dataSource.setUrl("jdbc:mysql://localhost:3306/mydb?useSSL=false");
        dataSource.setUsername("root");
        dataSource.setPassword("123456");

        // 连接池配置
        dataSource.setInitialSize(5);           // 初始化连接数
        dataSource.setMinIdle(5);               // 最小空闲连接
        dataSource.setMaxActive(20);             // 最大活跃连接
        dataSource.setMaxWait(60000);            // 获取连接最大等待时间

        // 连接保持配置
        dataSource.setTimeBetweenEvictionRunsMillis(60000);  // 检查空闲连接的间隔
        dataSource.setMinEvictableIdleTimeMillis(300000);    // 连接最小空闲时间
        dataSource.setMaxEvictableIdleTimeMillis(600000);    // 连接最大空闲时间

        // 验证配置
        dataSource.setValidationQuery("SELECT 1");
        dataSource.setTestWhileIdle(true);
        dataSource.setTestOnBorrow(false);
        dataSource.setTestOnReturn(false);

        // 监控配置
        dataSource.setFilters("stat,wall,log4j");  // 开启监控和防火墙

        return dataSource;
    }

    // 配置文件方式
    public DataSource createFromProperties() {
        Properties props = new Properties();
        props.setProperty("url", "jdbc:mysql://localhost:3306/mydb");
        props.setProperty("username", "root");
        props.setProperty("password", "123456");
        props.setProperty("initialSize", "5");
        props.setProperty("maxActive", "20");
        props.setProperty("minIdle", "5");

        return DruidDataSourceFactory.createDataSource(props);
    }
}

2.4 Tomcat JDBC Pool

xml
<dependency>
    <groupId>org.apache.tomcat</groupId>
    <artifactId>tomcat-jdbc</artifactId>
    <version>10.1.15</version>
</dependency>
java
import org.apache.tomcat.jdbc.pool.DataSource;
import org.apache.tomcat.jdbc.pool.PoolProperties;

public class TomcatPoolDemo {

    public DataSource createDataSource() {
        PoolProperties p = new PoolProperties();

        p.setUrl("jdbc:mysql://localhost:3306/mydb");
        p.setUsername("root");
        p.setPassword("123456");
        p.setDriverClassName("com.mysql.cj.jdbc.Driver");

        p.setInitialSize(5);
        p.setMaxActive(20);
        p.setMinIdle(5);
        p.setMaxIdle(10);
        p.setMaxWait(30000);

        p.setValidationQuery("SELECT 1");
        p.setTestOnBorrow(true);
        p.setTestWhileIdle(true);

        p.setTimeBetweenEvictionRunsMillis(60000);
        p.setMinEvictableIdleTimeMillis(300000);

        return new DataSource(p);
    }
}

三、Spring 框架中的数据库连接

3.1 配置数据源
application.yml 配置:

spring:
  datasource:
    # 基础配置
    url: jdbc:mysql://localhost:3306/mydb?useSSL=false&serverTimezone=UTC
    username: root
    password: 123456
    driver-class-name: com.mysql.cj.jdbc.Driver

    # HikariCP 配置
    hikari:
      maximum-pool-size: 10
      minimum-idle: 5
      connection-timeout: 30000
      idle-timeout: 600000
      max-lifetime: 1800000
      connection-test-query: SELECT 1
      pool-name: MyHikariPool

    # Druid 配置
    type: com.alibaba.druid.pool.DruidDataSource
    druid:
      initial-size: 5
      max-active: 20
      min-idle: 5
      max-wait: 60000
      filters: stat,wall,slf4j
      stat-view-servlet:
        enabled: true
        url-pattern: /druid/*
        login-username: admin
        login-password: admin

Java 配置:

@Configuration
public class DataSourceConfig {

    @Bean
    @ConfigurationProperties(prefix = "spring.datasource")
    public DataSource dataSource() {
        return DataSourceBuilder.create().build();
    }

    // 自定义 HikariCP 配置
    @Bean
    public DataSource customDataSource() {
        HikariConfig config = new HikariConfig();
        config.setJdbcUrl("jdbc:mysql://localhost:3306/mydb");
        config.setUsername("root");
        config.setPassword("123456");
        config.setMaximumPoolSize(20);
        config.setMinimumIdle(5);
        config.setConnectionTimeout(30000);
        config.setIdleTimeout(600000);
        config.setMaxLifetime(1800000);
        return new HikariDataSource(config);
    }

    // 多数据源配置
    @Bean
    @Primary
    @ConfigurationProperties(prefix = "spring.datasource.primary")
    public DataSource primaryDataSource() {
        return DataSourceBuilder.create().build();
    }

    @Bean
    @ConfigurationProperties(prefix = "spring.datasource.secondary")
    public DataSource secondaryDataSource() {
        return DataSourceBuilder.create().build();
    }
}

3.2 JdbcTemplate 使用

@Repository
public class UserDao {

    @Autowired
    private JdbcTemplate jdbcTemplate;

    @Autowired
    private NamedParameterJdbcTemplate namedParameterJdbcTemplate;

    // 查询单条记录
    public User findById(Long id) {
        String sql = "SELECT id, username, age FROM users WHERE id = ?";
        return jdbcTemplate.queryForObject(sql, new BeanPropertyRowMapper<>(User.class), id);
    }

    // 查询列表
    public List<User> findAll() {
        String sql = "SELECT id, username, age FROM users";
        return jdbcTemplate.query(sql, (rs, rowNum) -> {
            User user = new User();
            user.setId(rs.getLong("id"));
            user.setUsername(rs.getString("username"));
            user.setAge(rs.getInt("age"));
            return user;
        });
    }

    // 插入并返回主键
    public long insert(User user) {
        String sql = "INSERT INTO users (username, age) VALUES (?, ?)";
        KeyHolder keyHolder = new GeneratedKeyHolder();

        jdbcTemplate.update(connection -> {
            PreparedStatement ps = connection.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS);
            ps.setString(1, user.getUsername());
            ps.setInt(2, user.getAge());
            return ps;
        }, keyHolder);

        return keyHolder.getKey().longValue();
    }

    // 批量插入
    public int[] batchInsert(List<User> users) {
        String sql = "INSERT INTO users (username, age) VALUES (?, ?)";
        return jdbcTemplate.batchUpdate(sql, users, 100, (ps, user) -> {
            ps.setString(1, user.getUsername());
            ps.setInt(2, user.getAge());
        });
    }

    // 命名参数查询
    public List<User> findByCondition(String username, Integer age) {
        String sql = "SELECT * FROM users WHERE username = :username AND age > :age";
        MapSqlParameterSource params = new MapSqlParameterSource();
        params.addValue("username", username);
        params.addValue("age", age);

        return namedParameterJdbcTemplate.query(sql, params, new BeanPropertyRowMapper<>(User.class));
    }
}

来源:
https://dnuhf.cn/category/food.html

相关文章
|
9天前
|
人工智能 JSON 机器人
让龙虾成为你的“公众号分身” | 阿里云服务器玩Openclaw
本文带你零成本玩转OpenClaw:学生认证白嫖6个月阿里云服务器,手把手配置飞书机器人、接入免费/高性价比AI模型(NVIDIA/通义),并打造微信公众号“全自动分身”——实时抓热榜、AI选题拆解、一键发布草稿,5分钟完成热点→文章全流程!
11089 95
让龙虾成为你的“公众号分身” | 阿里云服务器玩Openclaw
|
8天前
|
人工智能 IDE API
2026年国内 Codex 安装教程和使用教程:GPT-5.4 完整指南
Codex已进化为AI编程智能体,不仅能补全代码,更能理解项目、自动重构、执行任务。本文详解国内安装、GPT-5.4接入、cc-switch中转配置及实战开发流程,助你从零掌握“描述需求→AI实现”的新一代工程范式。(239字)
5197 132
|
5天前
|
人工智能 自然语言处理 供应链
【最新】阿里云ClawHub Skill扫描:3万个AI Agent技能中的安全度量
阿里云扫描3万+AI Skill,发现AI检测引擎可识别80%+威胁,远高于传统引擎。
1366 3
|
7天前
|
人工智能 并行计算 Linux
本地私有化AI助手搭建指南:Ollama+Qwen3.5-27B+OpenClaw阿里云/本地部署流程
本文提供的全流程方案,从Ollama安装、Qwen3.5-27B部署,到OpenClaw全平台安装与模型对接,再到RTX 4090专属优化,覆盖了搭建过程的每一个关键环节,所有代码命令可直接复制执行。使用过程中,建议优先使用本地模型保障隐私,按需切换云端模型补充功能,同时注重显卡温度与显存占用监控,确保系统稳定运行。
1788 5
|
15天前
|
人工智能 JavaScript API
解放双手!OpenClaw Agent Browser全攻略(阿里云+本地部署+免费API+网页自动化场景落地)
“让AI聊聊天、写代码不难,难的是让它自己打开网页、填表单、查数据”——2026年,无数OpenClaw用户被这个痛点困扰。参考文章直击核心:当AI只能“纸上谈兵”,无法实际操控浏览器,就永远成不了真正的“数字员工”。而Agent Browser技能的出现,彻底打破了这一壁垒——它给OpenClaw装上“上网的手和眼睛”,让AI能像真人一样打开网页、点击按钮、填写表单、提取数据,24小时不间断完成网页自动化任务。
2970 6

热门文章

最新文章