ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Java Web实战:JSP宿舍管理系统从部署到MVC重构

Java Web实战:JSP宿舍管理系统从部署到MVC重构 简介这是一套面向Java Web初学者的ServletJSPMySQL宿舍管理系统实战项目适合刚接触Web开发、需要完整练手案例的学生与自学者。项目围绕宿舍信息管理展开涵盖用户注册登录、宿舍数据增删改查等核心业务帮助理解Servlet处理请求、JSP渲染视图、JDBC操作MySQL的完整链路。压缩包共63个文件约10.01MB包含18个java源码与18个class编译文件、5个jsp页面、3个jar依赖以及sql建表脚本、配置说明docx、功能描述txt和演示mp4另附4张png界面截图便于对照运行效果。资源还提供数据库设计、Servlet编写、JSP页面创建、数据库连接与错误处理等开发流程说明并涉及session保持登录状态、MVC分层组织代码等进阶思路。目前已有1160人学习下载可作为课程设计或毕业设计的起步模板帮助快速搭建可运行环境并掌握前后端与数据库协作方式。1. 从一份老派 JSP 宿舍管理系统说起它到底能跑通什么如果你手头正好有一套008_javajspmysql简单宿舍管理系统.zip解压后看到sushe代码目录、nafeng.sql数据脚本、详细配置.docx和几段演示视频那你拿到的不是一份“过时玩具”而是一条完整的 Java Web 请求链路标本。它用最原始的 Servlet JSP MySQL 组合把用户注册、登录、宿舍信息增删改查这些动作串了起来没有 Spring、没有 MyBatis、没有前后端分离所有逻辑都摊在明面上。对刚接触 Java Web 的人来说这种“裸奔式”结构反而最容易看清 HTTP 请求怎么进 Servlet、JDBC 怎么连数据库、JSP 怎么把结果渲染成 HTML。它适合想搞懂 MVC 雏形、需要交课程设计、或者准备面试时被问到“Servlet 生命周期”却答不踏实的人。你不需要先学一堆框架只要装好 JDK、Tomcat 和 MySQL就能把这份代码跑起来亲眼看到数据从表单进、从页面出。2. 把项目跑起来JDK、Tomcat 与 MySQL 的版本咬合2.1 环境选型为什么这套代码挑 Tomcat 8/9 而不是 10这份系统用的是javax.servlet包不是jakarta.servlet。Tomcat 10 之后 Servlet API 的包名整体迁移到了jakarta.*如果你直接把sushe丢进 Tomcat 10 的webapps启动时大概率报ClassNotFoundException: javax.servlet.http.HttpServlet。常见做法是选 Tomcat 8.5 或 9.0这两个版本仍然使用javax.servlet和代码里的import javax.servlet.*完全对得上。JDK 方面代码没有用到模块化特性JDK 8 最稳JDK 11 也能跑但别上 JDK 17 以上老版本 Tomcat 对高版本 JDK 的反射限制会带来额外麻烦。MySQL 用 5.7 或 8.0 都行区别在 JDBC 驱动类名和连接串参数后面会具体说。先确认三个东西的版本java -version # 期望输出java version 1.8.0_xxx 或 11.0.x mysql --version # 期望输出mysql Ver 14.14 Distrib 5.7.xx 或 8.0.xx # Tomcat 解压后查看 RELEASE-NOTES 里的版本号 cat apache-tomcat-9.0.xx/RELEASE-NOTES | head -5这三条命令分别确认 JDK、MySQL 客户端和 Tomcat 的大版本。版本对不上后面连数据库和部署都会出玄学问题。2.2 导入 nafeng.sql建库、建表与字符集确认压缩包里的nafeng.sql是数据库脚本通常包含CREATE DATABASE、USE、CREATE TABLE和若干INSERT初始化数据。导入前先看一眼文件头部确认库名和字符集head -30 nafeng.sql # 关注CREATE DATABASE 后面跟的库名、DEFAULT CHARACTER SET 是什么如果脚本里写的是utf8而不是utf8mb4在 MySQL 8.0 下也能执行但存中文时建议手动改成utf8mb4。导入命令mysql -u root -p nafeng.sql # 输入密码后无报错即导入成功 mysql -u root -p -e SHOW DATABASES; # 确认脚本里创建的库已经出现导入完成后进库看一眼表结构重点确认宿舍信息表的字段名因为后面 Servlet 里的 SQL 语句要和字段严格对应USE nafeng; SHOW TABLES; DESC 宿舍信息表名; -- 常见字段id、dorm_id、room_type、capacity、remark字段名对不上Servlet 里的rs.getString(xxx)就会抛SQLException这是新手最容易卡住的地方。2.3 改 JDBC 配置驱动类名、URL 参数与 MySQL 8 的时区坑代码里连接数据库的配置一般写在一个工具类或db.properties里。你需要改三处驱动类名、URL、账号密码。MySQL 5.7 和 8.0 的驱动类名不同MySQL 版本驱动类名URL 关键参数5.7com.mysql.jdbc.DriveruseUnicodetruecharacterEncodingutf88.0com.mysql.cj.jdbc.Driver追加serverTimezoneAsia/ShanghaiMySQL 8.0 不配serverTimezone会报The server time zone value xxx is unrecognized这是血泪经验里排第一的翻车点。配置示例// DBUtil.java 片段 String driver com.mysql.cj.jdbc.Driver; String url jdbc:mysql://localhost:3306/nafeng?useUnicodetruecharacterEncodingutf8serverTimezoneAsia/ShanghaiuseSSLfalse; String user root; String password 你的密码; Class.forName(driver); Connection conn DriverManager.getConnection(url, user, password);useSSLfalse是为了避开 MySQL 8.0 默认要求 SSL 连接带来的SSL connection error本地开发关掉即可。characterEncodingutf8保证中文不乱码。改完配置把mysql-connector-java的 jar 包放进WEB-INF/lib版本要和 MySQL 服务端匹配8.0 服务端配 8.0 驱动。2.4 部署到 Tomcat 并验证登录页把sushe目录整个复制到 Tomcat 的webapps下启动 Tomcat# Linux/Mac ./apache-tomcat-9.0.xx/bin/startup.sh # Windows apache-tomcat-9.0.xx\bin\startup.bat # 看日志确认无异常 tail -f apache-tomcat-9.0.xx/logs/catalina.out浏览器访问http://localhost:8080/sushe/如果出现登录页说明 JSP 编译和 Servlet 映射都通了。用nafeng.sql里初始化的账号登录能进主页就代表整条链路跑通。如果 404检查web.xml里的url-pattern和访问路径是否一致如果 500看catalina.out里的堆栈八成是 JDBC 配置或字段名问题。3. 拆开 sushe 代码Servlet 请求流转与 JSP 原生界面怎么配合3.1 一个登录请求的完整路径从 form 到 doPost 再到 session登录功能是理解这套代码的最佳入口。JSP 登录页里有一个form actionLoginServlet methodpost提交后 Tomcat 根据web.xml或注解把请求交给LoginServlet的doPost方法。doPost里做三件事取参数、查数据库、写 session。// LoginServlet.java 核心逻辑 protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { request.setCharacterEncoding(UTF-8); String username request.getParameter(username); String password request.getParameter(password); UserDao dao new UserDao(); User user dao.login(username, password); if (user ! null) { HttpSession session request.getSession(); session.setAttribute(currentUser, user); response.sendRedirect(index.jsp); } else { request.setAttribute(msg, 用户名或密码错误); request.getRequestDispatcher(login.jsp).forward(request, response); } }setCharacterEncoding(UTF-8)必须在getParameter之前调用否则中文用户名会乱码。sendRedirect和forward的区别在这里很关键登录成功用重定向防止刷新页面重复提交登录失败用转发保留request域里的错误提示。session.setAttribute把用户对象存进去后续页面用session.getAttribute(currentUser)判断是否登录这就是最原始的登录态保持。3.2 宿舍信息 CRUDDAO 层 SQL 与 JSP 列表渲染的字段对齐宿舍信息的增删改查集中在DormServlet和对应的 DAO 类里。查询列表的 SQL 通常是SELECT * FROM dorm然后在 JSP 里用 JSTL 或脚本片段遍历。原生 JSP 项目里常见的是脚本片段%-- dormList.jsp 片段 --% % page importjava.util.List % % page importcom.sushe.entity.Dorm % % ListDorm list (ListDorm) request.getAttribute(dormList); for (Dorm d : list) { % tr td% d.getDormId() %/td td% d.getRoomType() %/td td% d.getCapacity() %/td td a hrefDormServlet?actioneditid% d.getId() %编辑/a a hrefDormServlet?actiondeleteid% d.getId() % onclickreturn confirm(确认删除)删除/a /td /tr % } %这里actionedit和actiondelete是 Servlet 内部的分支判断依据doGet里根据action参数决定调哪个方法。字段对齐是重点JSP 里d.getDormId()对应实体类属性实体类属性对应数据库字段任何一环名字不一致都会导致页面显示null或直接报错。删除操作加confirm是基本防护避免误点。3.3 原生 JSP 的界面组织include 复用与表单提交路径这套系统的界面没有用任何前端框架页面之间的复用靠% include fileheader.jsp %这种静态包含。头部导航、底部版权信息抽成单独文件每个页面引入改一处全站生效。表单提交路径要特别注意相对路径问题如果 JSP 在子目录里actionDormServlet可能解析到错误位置稳妥做法是用% request.getContextPath() %/DormServlet。form action% request.getContextPath() %/DormServlet?actionadd methodpost 宿舍号input typetext namedormId required 房间类型input typetext nameroomType 容纳人数input typenumber namecapacity input typesubmit value提交 /formrequest.getContextPath()返回项目部署名这里是/sushe拼出来的路径在任何目录层级下都正确。required是 HTML5 原生校验减少空提交。提交后DormServlet的doPost里根据actionadd走插入逻辑插入完重定向回列表页形成闭环。4. 避坑与排查这份老代码最容易翻车的五个地方4.1 中文乱码POST 和 GET 要分开治现象登录页输入中文用户名后台收到的是????或乱码字符串。原因POST 请求体默认编码不是 UTF-8GET 请求的参数编码取决于 Tomcat 的server.xml里Connector的URIEncoding配置。解决POST 在 Servlet 第一行加request.setCharacterEncoding(UTF-8)GET 要么改 Tomcatserver.xml给 Connector 加URIEncodingUTF-8要么在代码里用new String(request.getParameter(xxx).getBytes(ISO-8859-1), UTF-8)手动转。数据库连接串里的characterEncodingutf8也要确认加上。4.2 驱动加载失败ClassNotFoundException 的三种可能现象启动或首次访问时报java.lang.ClassNotFoundException: com.mysql.jdbc.Driver。原因一是 jar 包没放进WEB-INF/lib二是放错了位置放到了 Tomcat 的lib下但版本冲突三是 MySQL 8.0 用了旧驱动类名。解决确认WEB-INF/lib下有mysql-connector-java-x.x.x.jarMySQL 8.0 把类名改成com.mysql.cj.jdbc.Driver。如果项目用了 Maven检查pom.xml里依赖的scope是不是provided那会导致打包时 jar 不进WEB-INF/lib。4.3 时区报错MySQL 8.0 的 serverTimezone 必填现象连接数据库时抛The server time zone value ?D1ú±ê×?ê±?? is unrecognized。原因MySQL 8.0 驱动要求明确指定时区不指定就取系统默认而 Windows 中文系统的时区名驱动识别不了。解决URL 里加serverTimezoneAsia/Shanghai。如果还报错检查 MySQL 服务端的default-time-zone设置或者临时用serverTimezoneUTC先跑通但存时间会有 8 小时偏差生产环境别这么干。4.4 404 与 500路径映射和空指针的快速定位现象访问某个功能页报 404或者提交表单后报 500。原因404 通常是web.xml里url-pattern和表单action不一致或者 JSP 文件放错目录500 多半是 DAO 里rs.getString(字段名)字段名写错或者session.getAttribute取出来是null还直接调方法。解决404 先看 Tomcat 日志里请求的 URI和web.xml对照500 看catalina.out里的完整堆栈定位到具体行号。空指针问题在取 session 属性后加判空或者用拦截器统一处理登录校验。4.5 删除后列表不刷新重定向与浏览器缓存的配合现象点击删除后数据库确实删了但页面列表还是旧数据。原因删除操作后用了forward回列表页或者浏览器缓存了之前的 GET 请求结果。解决删除成功后用response.sendRedirect(dormList.jsp)重定向强制浏览器发起新请求。如果还不行在列表页 JSP 头部加禁用缓存的响应头response.setHeader(Cache-Control, no-cache, no-store, must-revalidate); response.setHeader(Pragma, no-cache); response.setDateHeader(Expires, 0);5. 进阶用法用 MVC 分层重构与 JDBC 工具类收口5.1 把散落的 JDBC 代码抽成工具类原始代码里每个 DAO 方法都写一遍Class.forName、getConnection、close重复且容易漏关连接。我一般会抽一个DBUtil用静态块加载驱动提供getConnection和close方法public class DBUtil { private static final String DRIVER com.mysql.cj.jdbc.Driver; private static final String URL jdbc:mysql://localhost:3306/nafeng?useUnicodetruecharacterEncodingutf8serverTimezoneAsia/ShanghaiuseSSLfalse; private static final String USER root; private static final String PWD 你的密码; static { try { Class.forName(DRIVER); } catch (ClassNotFoundException e) { throw new RuntimeException(驱动加载失败, e); } } public static Connection getConnection() throws SQLException { return DriverManager.getConnection(URL, USER, PWD); } public static void close(Connection conn, PreparedStatement ps, ResultSet rs) { try { if (rs ! null) rs.close(); } catch (SQLException ignored) {} try { if (ps ! null) ps.close(); } catch (SQLException ignored) {} try { if (conn ! null) conn.close(); } catch (SQLException ignored) {} } }静态块保证驱动只加载一次close方法按ResultSet、Statement、Connection顺序关闭避免资源泄漏。DAO 里只写 SQL 和参数绑定代码量能砍掉三分之一。5.2 用 PreparedStatement 替换字符串拼接 SQL原始代码里如果有SELECT * FROM user WHERE username username 这种写法必须换成PreparedStatement。一是防 SQL 注入二是避免用户名里带单引号导致语法错误String sql SELECT * FROM user WHERE username? AND password?; PreparedStatement ps conn.prepareStatement(sql); ps.setString(1, username); ps.setString(2, password); ResultSet rs ps.executeQuery();?是占位符setString按位置绑定驱动会自动处理转义。这是从“能跑”到“能看”的关键一步面试被问到 JDBC 和 Statement 区别时也有实打实的代码支撑。5.3 验证重构是否成功的三个检查点重构完别急着说“好了”按这三步走一遍第一登录、增删改查每个功能点手动点一遍确认页面无报错第二看 Tomcat 日志里有没有SQLException或连接泄漏警告第三把DBUtil里的密码故意改错确认报错信息清晰指向连接失败而不是一堆看不懂的堆栈。从那以后我每次改完 JDBC 相关代码都强制走一遍“错密码测试”确保异常处理没被吞掉。希望这份拆解能帮你把这份 JSP 宿舍管理系统真正跑通、改顺。本文还有配套的精品资源点击获取
返回列表