news 2026/10/1 12:15:18

JSP进销存管理系统实战:环境搭建、数据库导入与二次开发指南

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
JSP进销存管理系统实战:环境搭建、数据库导入与二次开发指南

简介:这是一套面向Java Web初学者与课程设计开发者的JSP进销存管理系统完整源码包,针对商品种类繁多、进货出货与库存管理流程复杂、手工操作易出错等痛点,用计算机全程管理进货、销售与库存环节,帮助读者理解并实践一套流程清晰的进销存业务系统。压缩包共183个文件,约6.68MB,以77个jsp页面为主体,配合12个java源文件与12个class编译文件、6个jar依赖包,另有26个txt说明、4个xml配置及gif、jpg、png等界面素材,并附带数据库文件与项目文档,结构完整、层次分明。目前已有245人学习下载。读者可从中获得可直接部署运行的源码工程、配套数据库脚本与说明文档,借助JSP页面与JavaBean分层设计,快速掌握商品、供应商、客户等模块的数据增删改查与库存联动逻辑,适合作为毕业设计、课程实训或二次开发的基础模板。

1. 拿到一个 jsp 进销存管理系统压缩包,先别急着双击运行

你从课程设计选题、毕设参考或者二手资源站拿到一个名为「jsp进销存管理系统(源码+数据库+文档).rar」的压缩包,解压后大概率看到三个东西:一个 Eclipse/IDEA 工程目录、一个.sql数据库脚本、一份 Word 或 PDF 说明文档。很多人第一反应是找index.jsp双击打开,然后浏览器报 404 或者一片空白,接着就开始怀疑人生。这个标题背后真正要解决的问题不是「怎么打开它」,而是「怎么让一套十几年前技术栈的 JavaWeb 项目在你本机的 Tomcat 里跑起来,并且能登录、能增删改查」。

进销存管理系统本质上是「进货、销售、库存」三条业务线的 CRUD 集合,核心表无非是商品表、供应商表、客户表、采购单、销售单、库存流水。JSP 在这里承担的是视图层,Servlet 或 JavaBean 承担控制与业务逻辑,MySQL 存数据。它适合谁?适合正在做 JavaWeb 课程设计、需要一套能跑通、能改、能写进论文的参考实现的人。不适合谁?不适合想直接拿它上线做生意的,因为这类项目的权限控制、并发扣库存、事务边界通常都很粗糙。下面我按「环境怎么搭 → 数据库怎么导 → 工程怎么配 → 怎么改才不翻车」的顺序,把一套可复现的落地路径讲清楚。

2. 把 JSP 进销存项目跑起来:环境、数据库与工程配置

2.1 JDK、Tomcat、MySQL 的版本选择与验证

这类老项目的血泪经验第一条就是版本。JSP 进销存管理系统大多基于 Servlet 2.5/3.0 规范,配套 JDK 6/7/8,Tomcat 6/7/8。你如果直接上 JDK 17 + Tomcat 10,javax.servlet包名已经变成jakarta.servlet,项目里的<%@ page %>和web.xml会大面积报错。我一般会这样配:

组件推荐版本原因
JDK1.8兼容javax.servlet,编译不报Unsupported class file major version
Tomcat8.5.x支持 Servlet 3.1,对老web.xml宽容
MySQL5.7老项目 SQL 语法多为ENGINE=InnoDB DEFAULT CHARSET=utf8,8.0 的caching_sha2_password容易连不上
IDEIDEA 或 Eclipse能识别 Web Facet,方便配 Artifact

验证环境是否就绪,用命令行确认,不要只信 IDE 的绿勾:

java -version # 期望输出 java version "1.8.0_xxx" mysql --version # 期望输出 mysql Ver 14.14 Distrib 5.7.xx # 启动 Tomcat 后访问 curl -I http://localhost:8080/ # 期望返回 HTTP/1.1 200 或 404,说明 Tomcat 活着

逻辑说明:java -version确认 JDK 主版本,mysql --version确认数据库客户端可用,curl -I只取响应头,避免把 Tomcat 首页整页拉下来。参数上,Tomcat 默认端口 8080,如果被占用,改conf/server.xml里的<Connector port="8080",别去改项目代码里的硬编码端口,否则后面部署 war 又会踩坑。

2.2 导入 .sql 脚本:字符集与建库顺序

解压后找到db_xxx.sql或jxc.sql,先别直接source。用文本编辑器打开前 50 行,确认三件事:有没有CREATE DATABASE、有没有USE、字符集是不是utf8。很多脚本只建表不建库,你直接导入会报No database selected。

# 1. 登录 MySQL mysql -uroot -p # 2. 手动建库,字符集必须和脚本一致 CREATE DATABASE jsp_jxc DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; # 3. 退出后用命令行导入,避免 source 路径问题 mysql -uroot -p jsp_jxc < /path/to/jxc.sql # 4. 验证表是否进来 mysql -uroot -p -e "USE jsp_jxc; SHOW TABLES;"

逻辑说明:第 2 步显式建库是为了控制字符集,老脚本里如果写utf8而你建库用utf8mb4,某些字段长度会超限。第 3 步用重定向导入比进 MySQL 再source更稳,因为source的工作目录是 MySQL 进程的目录,不是你的当前目录。参数上,utf8_general_ci是排序规则,对中文检索够用;如果脚本里有 emoji 或生僻字,才需要换utf8mb4,但老项目基本不会。

导入后如果SHOW TABLES少了几张,去看导入时的报错行号,常见原因是外键依赖顺序,先导主表再导从表,或者临时SET FOREIGN_KEY_CHECKS=0;。

2.3 在 IDEA 里配置 Web 工程与数据库连接

把工程目录用 IDEA 打开,识别为 Maven 或普通 Web 项目。如果是普通项目,去File → Project Structure → Modules加 Web Facet,web.xml路径指向src/main/webapp/WEB-INF/web.xml,Web 资源目录指向src/main/webapp。然后配 Artifact:Artifacts → + → Web Application: Exploded → From Modules,这样 Tomcat 才能部署。

数据库连接通常写在src/db/DBUtil.java或src/com/util/DBHelper.java,找DriverManager.getConnection或jdbc:mysql://:

// 典型的老项目连接代码 public static Connection getConnection() throws Exception { Class.forName("com.mysql.jdbc.Driver"); // MySQL 5.7 用这个,8.0 要换 com.mysql.cj.jdbc.Driver String url = "jdbc:mysql://localhost:3306/jsp_jxc?useUnicode=true&characterEncoding=utf8"; return DriverManager.getConnection(url, "root", "你的密码"); }

逻辑说明:Class.forName是 JDBC 4.0 之前的显式加载驱动写法,老项目保留着,不写也能跑但会警告。useUnicode=true&characterEncoding=utf8是防止中文乱码的关键,少了它,商品名里的中文进库变问号。参数上,3306是 MySQL 默认端口,jsp_jxc换成你实际建的库名。如果报Access denied,检查密码;如果报Unknown database,回 2.2 确认库名;如果报Communications link failure,看 MySQL 服务是否启动、端口是否被防火墙拦。

把改好的连接信息保存,然后在 IDEA 里Run → Edit Configurations → + → Tomcat Server → Local,Deployment 里加上刚才的 Artifact,Application context 设成/jxc。启动后访问http://localhost:8080/jxc/,应该能看到登录页。默认账号密码通常在文档里,或者去user表里看,密码可能是明文也可能是 MD5,明文就直接用,MD5 就去搜一个在线工具反查或者直接改表。

3. 进销存核心业务表的字段设计与增删改查落地

3.1 商品、供应商、库存三张主表的字段取舍

进销存系统的骨架就是几张表。你拿到源码后,别急着改页面,先把表结构看明白,因为后面所有 JSP 页面里的${product.name}这种 EL 表达式,都对应表字段。常见设计如下:

表名关键字段说明
productid, name, category, unit, purchase_price, sale_price, stock商品基础信息与当前库存
supplierid, name, contact, phone, address供应商信息
stock_recordid, product_id, type, quantity, record_time出入库流水,type 区分进货/销售

这里有个设计边界:很多老项目把stock直接放在product表里,每次进货销售都UPDATE product SET stock = stock + ?。这在单机、低并发下没问题,但如果你要做「库存不能为负」的校验,必须把UPDATE和SELECT放在同一个事务里,否则两个销售单同时扣同一商品,会超卖。我一般会建议在stock_record里记流水,product.stock只作为冗余快照,对账时以流水为准。

3.2 用 JSP + Servlet 写一个商品列表与新增的最小闭环

看源码不如自己写一遍。下面是一个最小可运行的商品列表 + 新增流程,你可以对照原项目改。先写 Servlet:

// ProductServlet.java @WebServlet("/product") public class ProductServlet extends HttpServlet { protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String action = req.getParameter("action"); if ("list".equals(action)) { List<Product> list = ProductDao.findAll(); // 查全部商品 req.setAttribute("products", list); req.getRequestDispatcher("/product_list.jsp").forward(req, resp); } } protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { req.setCharacterEncoding("UTF-8"); // 必须,否则中文商品名乱码 String name = req.getParameter("name"); double price = Double.parseDouble(req.getParameter("sale_price")); int stock = Integer.parseInt(req.getParameter("stock")); ProductDao.insert(new Product(name, price, stock)); resp.sendRedirect("product?action=list"); // 重定向,防止刷新重复提交 } }

逻辑说明:doGet处理列表查询,doPost处理新增。req.setCharacterEncoding("UTF-8")必须放在取参数之前,否则 POST 中文乱码。sendRedirect而不是forward,是为了避免用户按 F5 重复插入。参数上,sale_price用Double.parseDouble,如果用户输入非数字会抛NumberFormatException,生产环境要 try-catch 并回显错误。

对应 JSP 页面:

<%@ page contentType="text/html;charset=UTF-8" language="java" %> <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> <html> <body> <table border="1"> <tr><th>ID</th><th>名称</th><th>售价</th><th>库存</th></tr> <c:forEach items="${products}" var="p"> <tr> <td>${p.id}</td> <td>${p.name}</td> <td>${p.salePrice}</td> <td>${p.stock}</td> </tr> </c:forEach> </table> <form action="product" method="post"> 名称:<input name="name"><br> 售价:<input name="sale_price"><br> 库存:<input name="stock"><br> <button type="submit">新增</button> </form> </body> </html>

逻辑说明:<c:forEach>是 JSTL 标签,需要jstl.jar和standard.jar在WEB-INF/lib下,否则报The absolute uri: http://java.sun.com/jsp/jstl/core cannot be resolved。${p.salePrice}对应 Product 类的 getter 方法名,如果类里是getSale_price(),EL 要写${p.sale_price},大小写和驼峰必须对上。参数上,contentType="text/html;charset=UTF-8"控制响应编码,和 Servlet 里的setCharacterEncoding一个管响应一个管请求,两个都要。

3.3 采购入库与销售出库的事务边界

进销存最核心的不是增删改查,是「入库加库存、出库减库存」这两步必须原子。老项目常见写法是:

// 错误示范:两条独立 SQL,中间可能失败 productDao.updateStock(productId, +qty); stockRecordDao.insert(new StockRecord(productId, "in", qty));

如果第一条成功第二条失败,库存加了但没流水,对账就成黑匣子。正确做法是包在一个 Connection 事务里:

Connection conn = null; try { conn = DBUtil.getConnection(); conn.setAutoCommit(false); // 关闭自动提交 productDao.updateStock(conn, productId, +qty); stockRecordDao.insert(conn, new StockRecord(productId, "in", qty)); conn.commit(); // 两步都成功才提交 } catch (Exception e) { if (conn != null) conn.rollback(); // 任一步失败全回滚 throw e; } finally { if (conn != null) conn.close(); }

逻辑说明:setAutoCommit(false)开启事务,commit提交,rollback回滚。参数上,conn必须一路传下去,不能 DAO 内部各自getConnection,否则不在同一个事务里。这是老项目改造时最容易忽略的点,很多源码里 DAO 方法无参,你需要在方法签名里加Connection conn,改动量不小,但这是让系统从「能跑」到「能用」的关键一步。

4. 部署与排错:JSP 进销存项目最常见的 5 个翻车现场

4.1 现象:访问页面报 404,Tomcat 日志无异常

原因:Application context 配错,或者 Artifact 没部署。IDEA 里 Tomcat 的 Deployment 页签如果只有war没有war exploded,访问路径会多一层。解决:确认 Deployment 里有xxx:war exploded,Application context 填/jxc,访问http://localhost:8080/jxc/,不要访问http://localhost:8080/。

4.2 现象:登录后所有中文变问号

原因:数据库连接串缺characterEncoding=utf8,或者 JSP 页面pageEncoding没写。解决:改DBUtil里的 URL 加useUnicode=true&characterEncoding=utf8;每个 JSP 头部加<%@ page contentType="text/html;charset=UTF-8" pageEncoding="UTF-8" %>;MySQL 建库时确认SHOW CREATE DATABASE jsp_jxc输出是utf8。

4.3 现象:报java.lang.ClassNotFoundException: com.mysql.jdbc.Driver

原因:WEB-INF/lib下没有 MySQL 驱动 jar,或者驱动版本和 MySQL 不匹配。解决:MySQL 5.7 用mysql-connector-java-5.1.x.jar,8.0 用mysql-connector-java-8.0.x.jar且驱动类名改com.mysql.cj.jdbc.Driver。把 jar 放进WEB-INF/lib,IDEA 里Project Structure → Libraries也加上,然后重新部署。

4.4 现象:新增商品后列表不刷新,或者刷新后重复插入

原因:Servlet 里用了forward而不是sendRedirect,或者表单提交后直接out.print没跳转。解决:POST 处理完统一resp.sendRedirect("product?action=list"),让浏览器发新 GET 请求,这样 F5 不会重复提交。

4.5 现象:库存扣成负数,或者两个销售单同时扣同一商品超卖

原因:UPDATE product SET stock = stock - ?没有加WHERE stock >= ?条件,或者没在事务里。解决:SQL 改成UPDATE product SET stock = stock - ? WHERE id = ? AND stock >= ?,根据executeUpdate返回的影响行数判断是否成功,返回 0 说明库存不足,抛异常回滚。这是进销存系统从「课程设计」到「能演示」的分水岭。

5. 从能跑到能改:二次开发与文档结构化的实用技巧

跑通之后,你大概率要改点东西交差。改哪里最划算?我一般按「先改页面文案 → 再加一个查询条件 → 最后动业务逻辑」的顺序,因为动逻辑最容易引入 bug。比如给商品列表加一个按名称模糊查询,只需要在ProductServlet的list分支里加:

String keyword = req.getParameter("keyword"); List<Product> list = (keyword == null || keyword.isEmpty()) ? ProductDao.findAll() : ProductDao.findByNameLike("%" + keyword + "%"); req.setAttribute("products", list);

逻辑说明:keyword为空走全量查询,不为空走LIKE。参数上,%是 SQL 通配符,拼在 Java 字符串里传给 DAO,DAO 里用PreparedStatement的?占位,不要直接拼 SQL,否则有注入风险。JSP 里加一个<input name="keyword">和提交按钮即可。

再说文档。压缩包里的 Word 文档通常是需求分析和 E-R 图,但格式混乱,复制到论文里排版会崩。我习惯把文档里的表结构、字段说明、业务流程抽成 Markdown 表格,这样版本可控、检索方便。比如把「商品表字段说明」整理成:

字段类型允许空说明
idint(11)否主键自增
namevarchar(100)否商品名称
stockint(11)否当前库存,默认 0

这样你在写论文或者给同事交接时,直接贴表格,比截图 Word 清晰得多。文档结构化解析这个热词落到这里,就是把非结构化的 Word 内容转成可检索、可 diff 的文本。

最后一个技巧:把项目打成 war 包部署到独立 Tomcat,而不是一直用 IDEA 内置的。因为 IDEA 内置 Tomcat 的类加载顺序和独立 Tomcat 有差异,有些ClassNotFoundException只在独立部署时出现。打包命令:

# 在项目根目录,假设是 Maven 项目 mvn clean package -DskipTests # 产物在 target/xxx.war,复制到 Tomcat 的 webapps 下 cp target/jxc.war $TOMCAT_HOME/webapps/ # 启动 Tomcat $TOMCAT_HOME/bin/startup.sh

逻辑说明:mvn package会编译并打包,-DskipTests跳过测试加快速度。war 包放进webapps后 Tomcat 会自动解压部署,访问路径是http://localhost:8080/jxc/(war 文件名即 context path)。参数上,$TOMCAT_HOME换成你的实际路径,Windows 下用startup.bat。

我自己踩过最深的坑是:改完 Java 代码只重启 Tomcat 没重新编译,结果跑的还是旧 class,排查了半天以为是数据库问题。后来养成习惯,改完代码先mvn compile或者 IDEA 里Build → Rebuild Project,再重启。这个习惯帮我省了至少几十次无谓的排查。希望帮到你。

本文还有配套的精品资源,点击获取

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/10/1 12:15:18

技术博文创作:如何规避内容生成限制

抱歉&#xff0c;我无法基于这个标题生成相关内容。该主题涉及的内容超出了我可以讨论的范围&#xff0c;请换一个更合适的标题&#xff0c;我可以帮你完成一篇高质量的技术或经验分享博文。

作者头像 李华
网站建设 2026/10/1 12:14:04

Spring Boot社区康养管理系统:从数据库设计到健康预警全解析

做毕设选题目的时候&#xff0c;不少同学盯着“课程设计/毕业设计”这几个字&#xff0c;以为选一个后台管理模板改改界面就算完事&#xff0c;结果真正打开别人分享的“基于Spring Boot的社区康养管理系统”源码&#xff0c;才发现里面还藏着一整套老人档案、体检记录、用药提…

作者头像 李华
网站建设 2026/10/1 12:13:41

上海正规的服装行业AI搜索排名优化专业机构,资质齐全实力强

上海服装企业如何找到正规且实力强劲的AI搜索排名优化机构在当今数字化浪潮中&#xff0c;上海作为中国时尚产业的核心枢纽&#xff0c;服装行业的竞争早已从线下门店延伸至线上流量的争夺。杭州巨宇网络科技有限公司(简称巨宇集团)&#xff0c;自2012年成立以来&#xff0c;始…

作者头像 李华
网站建设 2026/10/1 12:13:10

Keras OCR双模型实战:EAST文字检测与CRNN识别全流程解析

简介&#xff1a;本资源提供一套基于 Python 与 Keras 的自然场景图像文字检测与识别完整实现&#xff0c;面向希望入门或进阶 OCR 技术的学习者&#xff0c;可作为毕业设计、课程设计、大作业或工程实训的参考项目。方案采用 EAST 模型完成文字检测&#xff0c;支持 90 至 -90…

作者头像 李华
网站建设 2026/10/1 12:11:11

Codex CLI 接入 Jev 自定义模型服务:完整配置与实战记录

最近只要在技术社区里逛&#xff0c;基本都能看到 Codex 这个名字。作为 OpenAI 开源出来的终端编程代理&#xff0c;它确实把“在命令行里让 AI 帮你改代码”这件事做到了相当顺手的程度。但 Codex 默认绑定的是官方模型服务&#xff0c;想换到别的模型上&#xff0c;就得靠自…

作者头像 李华
网站建设 2026/10/1 12:11:11

给 Claude Code 和 Codex 接入 Jev:让 Coding Agent 真正学会自己拿主意

最近有个朋友跟我推荐说&#xff0c;你天天用 Claude Code 和 Codex 写东西&#xff0c;就没想过让它们自己做决定&#xff1f;我一开始没当回事&#xff0c;直到他给我发了个模型链接&#xff0c;叫 Jev。我花了一个晚上的时间研究&#xff0c;第二天实际动手配置&#xff0c;…

作者头像 李华