HTML如何调用JSP操作数据库?JSP连接MySQL数据库教程
- 云服务器
- 2026-07-07
- 8
在传统的 Java Web 开发架构中,HTML 本身是静态标记语言,无法直接执行服务器端逻辑或数据库操作,所谓的“HTML 调用 JSP 操作数据库”,实际上是指通过 HTML 表单(Form)或 AJAX 请求将数据发送给 JSP 页面(或更常见的 Servlet),由 JSP 页面中的 Java 代码(JSP Scriptlet 或 JSTL/EL)连接数据库并执行 CRUD(增删改查)操作。
需要特别指出的是,在现代企业级开发中,直接让 JSP 页面处理数据库逻辑被视为反模式(Anti-pattern),因为它违反了 MVC(模型-视图-控制器)架构原则,导致代码难以维护,最佳实践是使用 Servlet 或 Spring MVC 作为控制器,JSP 仅作为视图层展示数据,但为了回答你的核心问题,以下将详细解析传统方式下的实现流程,并指出其局限性。
前端 HTML 数据提交机制
HTML 页面本身不具备“调用”后端的能力,它主要通过两种机制将数据传递给后端:

- 表单提交(Form Submission):用户填写表单后,点击提交按钮,浏览器会将数据以 GET 或 POST 方式发送到指定的 URL(通常是 JSP 或 Servlet 地址)。
- AJAX 异步请求:通过 JavaScript(如 jQuery 或 Fetch API)发送异步请求,后端返回 JSON 或 HTML 片段,前端再动态更新页面。
示例:HTML 表单结构
<!DOCTYPE html> <html> <head>用户注册</title> </head> <body> <h2>用户注册</h2> <!-action 指向处理数据的 JSP 页面,method 指定提交方式 --> <form action="register.jsp" method="post"> <label>用户名:</label> <input type="text" name="username" required><br><br> <label>密码:</label> <input type="password" name="password" required><br><br> <label>邮箱:</label> <input type="email" name="email" required><br><br> <button type="submit">提交</button> </form> </body> </html>
JSP 页面处理数据库逻辑
在 register.jsp 中,我们需要使用 JSP Scriptlet(<% ... %>)嵌入 Java 代码,以下是标准步骤:
- 获取请求参数:使用 request.getParameter() 获取 HTML 表单提交的数据。
- 加载 JDBC 驱动:加载数据库驱动程序(如 MySQL Connector/J)。
- 建立数据库连接:使用 DriverManager.getConnection() 连接数据库。
- 执行 SQL 语句:使用 Statement 或 PreparedStatement 执行插入操作。
- 处理结果与关闭资源:处理执行结果,并务必关闭 ResultSet、Statement 和 Connection 以释放资源。
示例:JSP 数据库操作代码
<%@ page import="java.sql." %> <%@ page contentType="text/html;charset=UTF-8" language="java" %> <html> <head>注册结果</title> </head> <body> <% // 1. 获取参数 String username = request.getParameter("username"); String password = request.getParameter("password"); String email = request.getParameter("email"); // 2. 数据库配置 String url = "jdbc:mysql://localhost:3306/mydb?useSSL=false&serverTimezone=UTC"; String dbUser = "root"; String dbPass = "123456"; // 3. 执行数据库操作 Connection conn = null; PreparedStatement pstmt = null; try { // 加载驱动 (新版 JDBC 可省略,但旧版需要) Class.forName("com.mysql.cj.jdbc.Driver"); // 建立连接 conn = DriverManager.getConnection(url, dbUser, dbPass); // 预编译 SQL 语句,防止 SQL 载入 String sql = "INSERT INTO users (username, password, email) VALUES (?, ?, ?)"; pstmt = conn.prepareStatement(sql); pstmt.setString(1, username); pstmt.setString(2, password); pstmt.setString(3, email); // 执行更新 int rows = pstmt.executeUpdate(); if (rows > 0) { out.println("<h3 style='color:green'>注册成功!</h3>"); } else { out.println("<h3 style='color:red'>注册失败。</h3>"); } } catch (Exception e) { e.printStackTrace(); out.println("<h3 style='color:red'>发生错误: " + e.getMessage() + "</h3>"); } finally { // 4. 关闭资源 try { if (pstmt != null) pstmt.close(); } catch (SQLException e) {} try { if (conn != null) conn.close(); } catch (SQLException e) {} } %> </body> </html>
关键注意事项与最佳实践对比
虽然上述代码可以工作,但在实际生产环境中存在严重问题,下表对比了传统 JSP 直连数据库与现代 MVC 架构的差异:
| 特性 | 传统 JSP 直连数据库 (上述方法) | 现代 MVC 架构 (Servlet/Spring) |
|---|---|---|
| 代码耦合度 | 极高,HTML、Java 逻辑、SQL 混合在一起。 | 低,视图、控制、模型分离。 |
| 可维护性 | 差,修改业务逻辑需修改 JSP,易出错。 | 好,各层职责清晰,易于重构。 |
| 安全性 | 较低,容易因疏忽导致 SQL 载入或 XSS。 | 较高,可通过框架特性统一处理安全策略。 |
| 性能 | 每次请求都加载驱动、创建连接,效率低。 | 使用连接池(如 HikariCP),复用连接,效率高。 |
| 调试难度 | 困难,错误堆栈可能混杂在 HTML 中。 | 简单,日志系统完善,分层调试。 |
| 推荐程度 | 不推荐,仅用于学习或极简单原型。 | 强烈推荐,行业标准。 |
改进建议:使用 Servlet 作为控制器
为了遵循最佳实践,建议将数据库操作移至 Servlet,JSP 仅负责展示。
- HTML 表单:action 指向 Servlet 的 URL 映射(如 /register)。
- Servlet (RegisterServlet.java):
- 继承 HttpServlet。
- 在 doPost 方法中获取参数。
- 调用 Service 层或直接操作 DAO 层进行数据库交互。
- 将结果存入 request 或 session 属性。
- 使用 request.getRequestDispatcher("success.jsp").forward(request, response) 转发到结果页面。
- JSP (success.jsp):
- 使用 EL 表达式 ${username} 显示数据,不包含任何 Java 代码。

相关问题与解答
问题 1:在 JSP 中直接操作数据库时,如何防止 SQL 载入攻破?
解答:
SQL 载入是 Web 安全中最常见的漏洞之一,在 JSP 中,绝对禁止使用字符串拼接的方式构建 SQL 语句("SELECT FROM users WHERE name = '" + name + "'")。
正确做法是使用 PreparedStatement:
- 使用占位符 代替具体的值。
- 通过 PreparedStatement 的 setString()、setInt() 等方法设置参数值。
- 数据库驱动会自动对输入进行转义和处理,从而有效防止 SQL 载入。
示例:
// 错误做法 (易受攻破) String sql = "SELECT FROM users WHERE username = '" + username + "'"; Statement stmt = conn.createStatement(); ResultSet rs = stmt.executeQuery(sql); // 正确做法 (安全) String sql = "SELECT FROM users WHERE username = ?"; PreparedStatement pstmt = conn.prepareStatement(sql); pstmt.setString(1, username); ResultSet rs = pstmt.executeQuery();
问题 2:为什么现代开发不推荐在 JSP 中使用 <% %> 脚本片段(Scriptlets)?
解答:
在 JSP 中使用 <% %> 嵌入 Java 代码(Scriptlets)存在以下主要缺陷:
- 违反关注点分离(Separation of Concerns):JSP 的设计初衷是作为视图层(View),负责 HTML 渲染,将业务逻辑(Java 代码)和数据访问(SQL)混入视图层,导致代码难以阅读、测试和维护。
- 编译开销:JSP 页面在第一次访问时会被编译成 Servlet 类,如果包含大量复杂逻辑,会增加服务器启动和首次请求的延迟。
- 缺乏类型安全:Scriptlet 中的代码在编译前无法进行严格的类型检查,容易在运行时抛出异常。
- 替代方案更优:
- JSTL (JSP Standard Tag Library):提供标签库来处理逻辑(如循环、条件判断),使 JSP 更接近纯 HTML。
- EL (Expression Language):用于简洁地访问数据,如 ${user.name}。
- MVC 框架:如 Spring MVC,彻底将视图与逻辑分离,JSP 仅作为纯模板引擎使用,甚至逐渐被 Thymeleaf、Freemarker 或前后端分离(Vue/React)所取代。
现代 Java Web 开发中,JSP 中的 Scriptlet 已被视为过时技术,应尽量避免使用。
