
简介这是一套基于SpringBoot后端与Vue前端技术栈开发的垃圾分类管理系统源码面向计算机专业本科生及初学者适用于毕业设计、课程设计与期末大作业等实践场景切实解决生活垃圾分类知识普及、垃圾识别查询与用户互动管理等现实需求。压缩包共1325个文件涵盖352个Java后端逻辑类、159个Vue组件页面、134个JS交互脚本、94个编译后Class文件、62个XML配置及YML配置文件以及SQL数据库脚本、SVG图标、PNG界面素材等完整支撑前后端分离架构的本地部署与功能验证整体大小为101.96MB。已有207人学习下载资源已通过高校高分答辩验证包含可直接运行的完整工程结构、清晰的模块划分如用户管理、垃圾查询、分类知识库、后台审核等、配套MySQL数据库及初始化脚本开箱即用无需二次重构即可快速演示核心业务流程。1. 项目概述与选题思路1.1 为什么垃圾分类系统适合做毕业设计很多同学找我咨询毕业设计选题时都会问一个问题做什么题目既方便实现、又容易拿高分、答辩时还能讲得清楚。我一般会建议考虑类似垃圾分类系统这样的应用型题目。原因很简单垃圾分类这个业务场景贴近生活、规则清晰、模块边界明确天然适合用“Web后端 前端页面 关系型数据库”这套经典组合来实现而 Spring Boot Vue 正好是当前最主流、就业市场上需求量最大的技术栈之一。这类题目的好处在于业务逻辑不会过于复杂——无非是用户管理、分类查询、积分记录、公告信息、留言反馈这些模块但又不是完全的小 demo因为垃圾分类本身有“四分类规则”这样的领域知识可以挖比如干垃圾、湿垃圾、可回收物、有害垃圾怎么区分怎么根据名称检索垃圾类别怎么按积分激励用户参与分类。这些都能在论文里写出“业务分析”和“需求分析”的厚度而不是只堆技术名词。另外这套系统前后端分离的架构本身也是加分项。Spring Boot 负责 RESTful APIVue 负责页面渲染和交互数据库用 MySQL 存储业务数据。答辩时老师问“你用了什么设计模式”“怎么处理跨域”“怎么保证数据一致性”你都能从实际代码里找到对应答案不会答得很空。1.2 系统的整体功能与角色划分这套垃圾分类系统我按毕业设计的常见标准来设计包含三类角色普通用户、垃圾分类管理员、系统管理员。普通用户能注册登录、查询垃圾类别、参与在线分类答题或模拟投放、获取积分、在积分商城兑换、给平台留言反馈管理员能维护垃圾基础数据比如垃圾名称属于哪一类、发布环保资讯、处理用户留言、审核积分兑换记录、管理用户信息。从功能模块上切分大概可以分成七个部分登录注册模块、首页与资讯模块、分类查询模块、积分管理模块、留言反馈模块、后台管理模块、个人中心模块。每个模块在答辩时都能单独拿出来讲清楚“前端调了什么接口、后端怎么处理、数据库表结构怎么支撑”这也是这套题做得扎实的关键。提示一个毕业设计想拿高分重点不是你功能做得有多花哨而是每一次前后端交互都有清晰的数据链路支撑每一个功能点都能回答“为什么这么设计”。后面我会逐渐展开讲这套链路。2. 技术选型解析为什么是 Spring Boot Vue2.1 后端选 Spring Boot 的核心理由Spring Boot 在 Java Web 领域几乎属于事实标准。哪怕是没学过 Spring 的同学照着教程也能把项目跑起来因为它的自动化配置把大量繁琐的 XML 配置砍掉了。做毕业设计用 Spring Boot最直接的好处是你的项目能快速搭建、快速演示而且 Spring Boot 本身的特性在面试和答辩中都是加分项。你可能听说过“起步依赖”和“自动配置”这两个概念。起步依赖就是你在 pom.xml 里引入一个spring-boot-starter-web依赖Tomcat、Spring MVC、Jackson 这些相关的包全都自动带过来了。自动配置则是 Spring Boot 根据你引入的依赖自动帮你创建好默认配置的 Bean比如配了 mysql 驱动就会自动配置 DataSource。你在答辩时能说清楚这两点老师通常就会认可你对框架是有理解的。核心技术点方面我建议在系统里重点突出以下内容技术点在项目里的应用场景答辩价值Spring Boot 自动配置项目零 XML 配置启动体现对框架原理的了解Spring MVC 注解RestController 接收前端请求RESTful 接口的规范设计MyBatis Plus自定义 SQL 分页查询、条件构造器简化数据库操作的常用方案JWT 登录校验前端登录后保存 token 访问受保护接口前后端分离的安全处理方式AOP 日志切面统一记录用户操作日志体现对横向关注点的理解LambdaQueryWrapper按条件拼接查询语句MyBatis Plus 的典型写法当然实际项目中不一定所有技术都用得上但至少要有两三个亮点。比如我在这个项目里就重点用了 MyBatis Plus 的条件构造器来实现垃圾名称的模糊查询比手写 SQL 拼接干净得多。2.2 前端选 Vue 的原因与版本选择Vue 在国内前端圈子里的热度一直很高最大的优势是入门门槛低、生态完善、中文文档友好。本科阶段做过 Web 前端的同学基本都能在一两周内上手 Vue。做毕业设计选 Vue 2 还是 Vue 3取决于你自己熟悉的程度。如果想减少踩坑直接用 Vue 2 Element UI 这套组合最稳妥Vue 2 的教程最多Element UI 的组件也全遇到问题基本都能搜到解决方案。Vue 3 的生态现在也成熟了Element Plus 组件也没问题只是个别库的兼容性需要留意比如某些图表库早期对 Vue 3 的支持不够好。前端重点要写清楚这几个部分路由vue-router怎么定义和管理页面跳转、Vuex 或 Pinia 怎么管理用户登录状态、Axios 怎么封装请求并统一处理响应、Element UI 怎么快速搭建后台管理界面。这套系统的前台页面面向普通用户风格可以活泼一点后台管理页面面向管理员直接组件化布局就好。特别注意一点项目前后端分离之后一定会有跨域问题。前端页面运行在 8080 端口后端接口在 8081 端口甚至放在云服务器上浏览器默认会拦截跨域请求。解决办法通常是后端配置跨域过滤器或者前端用开发服务器的代理转发。我习惯两种都写上开发环境走前端代理生产环境用 Nginx 反向代理这样在论文里也能多写一个知识点。2.3 数据库选型与配置的注意点数据库选型没什么悬念MySQL 5.7 或 8.0 是绝大多数毕业设计最稳妥的选择。它免费、资料多、Navicat 等可视化工具功能完善老师也默认熟悉这个数据库。如果你所在的学校更偏爱 SQL Server那也行但网上能找到的参考代码相对少一些遇到问题排查成本会高一点。这里必须提醒一个非常现实的坑现在很多同学创建 Spring Boot 项目时默认下载的 Spring Boot 版本已经是 3.x 甚至更高了但 3.x 要求 JDK 17和学校机房里的 JDK 8 环境往往不兼容同时很多老版本的 MyBatis 相关依赖也没适配。我在给学弟排查问题时碰到最多的就是这类“Spring Boot 版本太高导致启动失败或依赖冲突”。如果你手头的电脑是 JDK 8建议直接创建 Spring Boot 2.7.x 的项目不要盲目追求新版。注意Spring Boot 2.x 对应 JDK 8Spring Boot 3.x 对应 JDK 17。毕业设计环境不确定时优先选 2.7.x兼容性最好。数据库脚本方面我建议所有建表 SQL、初始数据 SQL 都拆分清楚并且带上注释。答辩时老师很可能直接在 Navicat 里打开你的数据库如果表结构看起来井井有条数据也规划得合理第一印象分会高很多。3. 数据库设计核心表结构与数据关系3.1 垃圾分类基础数据模型数据库是整个系统最不能省心的一层。我把表结构设计成一套“类别表 子类表 具体物品表”的层级结构而不是简单地把垃圾名字和类别放在一张表里这样设计的目的是为了后期维护方便也为了让论文里的 ER 图更好看。主表garbage_category存储四大分类可回收物、有害垃圾、厨余垃圾湿垃圾、其他垃圾干垃圾。字段包括主键 id、分类名称、分类编码、分类描述、图标地址、排序号、创建时间。分类编码用数字比如 1 可回收物、2 有害垃圾、3 厨余垃圾、4 其他垃圾前后端统一用编码传输避免中文名称出现编码问题。具体物品表garbage_item最重要的字段是item_name和category_id再补充一个别名表或者直接用一个“别名”字段存多个名字比如“塑料瓶矿泉水瓶、饮料瓶”这样用户查询“矿泉水瓶”时也能命中。还应该加上search_count字段记录搜索次数后期可以做热门搜索推荐虽然不复杂但写在论文里也算一个小亮点。在实际建表时字符集一定选utf8mb4别选utf8因为 utf8 在 MySQL 里最多存 3 个字节遇到 emoji 表情或某些生僻字会报错或者乱码。这条可能看起来不起眼但在后端接收用户留言反馈时用户一旦输入 emoji你就会明白什么叫“早知如此”。3.2 用户与积分体系设计用户表user就是经典的字段组合id、用户名、密码必须 BCrypt 加密存储不能明文、手机号、头像、积分余额、角色user/admin、注册时间、状态。密码加密这一点非常重要答辩的时候如果你直接明文存密码老师大概率会追问安全问题如果你答得上 BCrypt 是不可逆加密、自带盐值这就是一个加分点。积分体系单独拆了两张表积分记录表points_record和积分兑换表points_exchange。积分记录表记录每一次积分变动字段要有 user_id、变动类型获取/消费、变动分值、来源说明比如“参与分类答题奖励 5”、创建时间。积分兑换表记录用户用积分兑换了什么商品字段包括 user_id、goods_name虚拟物品名称、消耗积分、兑换状态待发放/已发放/已取消、申请时间、处理时间。这么拆的好处是数据链路完整。用户在前端“积分商城”页面提交兑换申请后台插入一条points_exchange记录同时扣减用户积分、写入points_record一条消费记录。这三步操作必须放在同一个数据库事务里否则可能出现用户积分扣了但兑换记录没生成的数据不一致问题。为了让代码更简洁我直接用Transactional注解在 Service 方法上这个问题会在后面细讲。3.3 资讯、留言与预约功能的数据结构资讯公告表article用作文宣信息发布字段包括 id、标题、封面图、摘要、正文内容、发布时间、发布人。用户端的首页轮播图和资讯列表从这张表查后台管理员发布时填写这些字段。正文内容我建议用富文本存储 HTML 格式的字符串这样在前端展示时可以直接渲染比单独存 Markdown 再转换要省事。留言反馈表message是用户和平台沟通的渠道。字段有 id、user_id、留言内容、留言时间、管理员回复内容、回复时间、是否已处理。这里要注意一个细节留言内容要限制长度并做特殊字符过滤防止用户输入过长的内容或带上一些奇怪的标签导致前端渲染出错。Spring Boot 处理这类 XSS 问题的思路是把用户输入里的script等危险标签过滤掉虽然这个话题有点敏感但作为工程实践的确需要关注。垃圾回收预约表appointment是给用户预约大件垃圾上门回收用的。字段包括 id、user_id、预约地址、预约时间、垃圾描述、状态待确认/已完成/已取消、创建时间。这个功能虽然简单但涉及“状态流转”的概念——用户提交后状态是待确认管理员后台可以改成已完成或已取消答辩时你可以借此讲讲枚举状态管理而不是在代码里到处写魔法数字。4. 后端核心模块与业务实现4.1 项目工程结构与分层思路后端项目我建议按标准的分层架构来组织controller 层负责接收请求和返回响应service 层写业务逻辑mapper 层dao 层操作数据库entity 实体类对应数据库表dto 用于接收前端传入的数据vo 用于返回给前端的数据。这种分层方式虽然老套但它让代码职责清晰答辩时老师顺着 controller 往下追问时你能一层一层讲清楚。包名结构大概是这样的com.example.garbage ├── controller # 接收请求的控制器 ├── service # 业务逻辑接口 ├── service/impl # 业务逻辑实现 ├── mapper # MyBatis Plus 的 Mapper 接口 ├── entity # 数据库表对应的实体类 ├── dto # 数据传入对象 ├── vo # 数据返回对象 ├── config # 配置类跨域、拦截器、MyBatis Plus 分页 ├── common # 通用结果封装类、异常处理、工具类 └── GarbageApplication.java # Spring Boot 启动类有一个很影响阅读体验的点很多同学的代码把全部业务写在 controller 里一个方法几十行看着很吓人。我的建议是 controller 只做参数接收和结果包装真正的判断逻辑放 service。比如“用户兑换积分”这个操作controller 里就一行调用service 里做校验用户积分是否足够、商品是否还有库存、扣减积分、插入记录等步骤。这样做的好处是答辩时你能对照着把“业务链”讲得非常清楚。4.2 统一结果返回与全局异常处理前后端分离的项目接口返回格式必须统一规范。我封装了一个Result类所有接口统一返回{ code: 200, message: success, data: ... }这种结构。code 为 200 表示成功400 表示参数错误401 表示未登录或 token 失效500 表示服务器异常。前端拿到响应后先在 Axios 拦截器里统一判断 code如果不是 200 就直接弹出错误提示不用每个页面都写一遍错误处理。全局异常处理用RestControllerAdvice注解实现。比如业务里手动抛出的ServiceException(积分不足)会被全局异常处理器捕获并包装成Result.error(500, 积分不足)返回给前端。这样你的 service 代码里就不需要到处 try-catch 了专心写业务逻辑出错就抛异常由统一的地方兜底。说一个被很多人忽略的小细节ResponseBody 里如果序列化 Date 日期默认格式可能是2024-01-01T00:00:00.00000:00这种令人抓狂的格式。我在application.yml里配置了统一的日期格式spring: jackson: date-format: yyyy-MM-dd HH:mm:ss time-zone: GMT8前端拿到的时间就是2024-06-01 12:30:00这种人类友好的格式。类似这样的小配置论文里写一句“自定义统一时间格式”细节分就拿到了。4.3 垃圾分类查询接口的后端逻辑分类查询是整个系统最核心的业务接口。前端输入垃圾名称后端通过/api/garbage/query?keywordxxx接口返回预测的垃圾分类结果。这个接口的实现逻辑分三步处理第一步把 keyword 做 trim 和空值判断如果为空直接返回“请输入垃圾名称”的提示。第二步先精确匹配garbage_item表的item_name字段命中就直接返回对应的category_name没命中就做模糊匹配把包含 keyword 的所有物品都查出来。第三步如果精确匹配和模糊匹配都失败就返回一个兜底提示比如“未找到该垃圾请尝试换个名称或参考分类规则”。这里有个可以聊的改进点数据库里garbage_item表的数据量通常不会太大直接LIKE查询就够用了不需要引入 Elasticsearch 之类重的搜索引擎。如果你在论文里说“本系统采用 MySQL 模糊查询实现垃圾分类智能检索”老师不会觉得简陋因为数据规模和应用场景是匹配的。画蛇添足上一套搜索引擎反而容易在答辩时被问住。分类规则展示和模拟分类检测也是这个模块的加分项。我做了两个入口一个展示四个分类的详细说明和典型垃圾列表另一个模拟“投放场景”随机给用户一个垃圾名称用户选择把它扔进哪类垃圾桶后台判断对错并返回解释。这实际上是给项目增加了一点互动性也延展了“积分获取”的来源渠道。4.4 积分与预约流程的事务处理积分模块直接体现了后端对数据一致性的处理能力。以“模拟投放正确奖励积分”为例用户提交答案后后端先校验答案是否正确正确就往points_record插入一条“5”记录并同步更新user表的points字段。这里不能先更新用户积分再插入记录因为如果第二条 SQL 失败用户积分已经增加了但明细缺失双方对不上。我的经验是给这个 Service 方法加Transactional注解遇到任何 RuntimeException 就整体回滚。虽然对这个量级的项目来说事务不复杂但在论文里写清楚“基于 Spring 声明式事务保证数据一致性”专业性一下就体现出来了。预约流程同理。用户提交预约时service 里调用预约插入逻辑同时更新用户的“待完成预约数”统计字段预约完成时管理员在后台点击“完成预约”后端更新预约状态并给用户加积分。这些操作都放在一个事务方法里避免出现“状态改了、积分没到账”的乌龙。5. 前端页面与交互实现5.1 Vue 项目目录结构与前端的工程化基础前端项目我用 Vue CLI 创建目录结构如下src ├── api # 按模块封装的接口请求文件 ├── assets # 静态资源图片、样式 ├── components # 公共组件头部导航、轮播图、分页组件 ├── router # vue-router 路由配置 ├── store # Vuex 状态管理保存用户信息 ├── utils # axios 封装、工具函数 ├── views # 页面组件 │ ├── home # 首页 │ ├── classify # 分类查询页 │ ├── points # 积分商城页 │ ├── appointment # 预约页面 │ ├── user # 个人中心 │ └── admin # 后台管理页面 └── App.vue # 根组件这样的目录划分能让代码结构一目了然。很多初学者把页面组件全堆在 views 里api 请求散落在各个页面后期改起来非常痛苦。模块化拆分这件事早做早省心。路由配置方面我用 vue-router 的懒加载方式加载页面组件即component: () import(../views/home/index.vue)这样的话首屏只加载首页需要的代码其他页面按需加载。这个细节虽然用户感知不到但答辩时如果老师问“首屏加载性能怎么优化”你可以把懒加载和代码分割讲一遍算是加分项。5.2 核心页面功能拆解首页的设计目标是环保资讯的展示和业务入口的聚合。顶部轮播图展示最近的环保活动海报下面放四个分类的快捷入口用户点进去直接看到该类垃圾的详细列表。首屏的数据来源有三个接口轮播图列表、分类统计每个分类下有多少种垃圾、最新资讯。三个请求并行发出页面加载完后一次性渲染。垃圾分类查询页是交互核心我设计成搜索框 结果卡片的形式。用户在搜索框输入垃圾名称回车后请求后端查询接口结果卡片展示垃圾类别名称、类别颜色可回收物蓝色、有害垃圾红色、厨余垃圾绿色、其他垃圾灰色、典型示例和投放注意事项。搜索结果还会展示同类别的其他垃圾方便用户拓展了解。这部分虽然逻辑不复杂但“颜色锚定四分类”的设计能显著提升用户识别速度放在论文中属于“交互设计优化”的维度。积分商城页面展示可兑换的积分商品和用户当前积分。兑换按钮点击后前端先本地判断积分是否足够不够则提示够则弹出确认框用户确认后调用兑换接口。兑换成功后会重新拉取用户积分和兑换记录保证页面显示的数据是最新的。这类“操作后刷新”的细节是整个前端体验顺畅的关键。个人中心页面展示用户信息、我的积分明细、我的兑换记录、我的预约记录。信息通过 Tab 切换展示不同列表。每个列表都调用了分页查询接口做了加载状态和空状态的判断。页面最底部有一个“退出登录”按钮点击后清除本地 token 并跳转到登录页。5.3 Axios 封装与 Token 认证流程Axios 封装我放在utils/request.js文件中统一配置基础 URL、超时时间和请求拦截器。每次发送请求时从 localStorage 里取出 token 放到请求头的 Authorization 字段响应拦截器里对返回的Result对象做统一处理code 为 200 时直接返回 data非 200 时弹出错误提示并 reject。401 的处理也很关键。当 token 过期或无效时后端返回 401前端收到后自动清除本地登录状态并跳转到登录页同时提示“登录已过期请重新登录”。这样用户在进行多个操作时不会因为某一接口失败而卡在当前页面。登录流程整体走 JWT 认证用户输入用户名和密码后端校验通过后签发一个 token 返回给前端前端把 token 存在 localStorage 里之后所有请求都带上这个 token。后端用一个拦截器HandlerInterceptor统一校验请求头里的 token判断用户是否登录、token 是否过期。这样的认证链路虽然简单但在答辩时讲出来说明你是懂“前后端分离下的认证机制”的。6. 本地部署与运行指南6.1 环境准备清单部署这套系统我建议本地至少准备好以下这些环境工具推荐版本用途注意事项JDK1.8 或 JDK 17运行后端版本必须与 Spring Boot 版本匹配Maven3.6依赖下载与打包建议配置阿里云镜像加速MySQL5.7 或 8.0数据存储8.0 需要留意驱动依赖版本Node.js14 及以上运行前端建议使用 16 LTS 版本更稳定IDEA2021 以上后端开发社区版也能用VS Code最新前端开发也可以直接用 IDEA 打开Navicat任意版本数据库可视化操作也可以用 DataGrip这里有一个非常容易踩的坑MySQL 8.0 的时区问题。连接 MySQL 8.0 时jdbc.url需要配置serverTimezoneAsia/Shanghai否则项目启动时会报时区相关的错误。MySQL 5.7 通常不需要加这个参数但加上也不会出问题所以统一加上更省事。6.2 数据库初始化与配置拿到项目的 SQL 文件之后先在 MySQL 里创建一个数据库比如叫garbage_db字符集选utf8mb4排序规则选utf8mb4_general_ci。然后打开 Navicat在数据库上右键选择“运行 SQL 文件”把项目里的garbage_db.sql导进去即可。导入完成后检查一下四个分类的数据是否都在确保管理员账户也初始化好了。之后在 IDEA 里打开后端项目修改application.yml里的数据库连接配置spring: datasource: url: jdbc:mysql://localhost:3306/garbage_db?useUnicodetruecharacterEncodingutf8serverTimezoneAsia/Shanghai username: root password: 你的数据库密码 driver-class-name: com.mysql.cj.jdbc.Driver注意一点如果启动时报java.sql.SQLException: The server time zone value ...就是没写serverTimezone或者没加时区参数。再把pom.xml里的依赖确认一下MyBatis Plus 的版本和 Spring Boot 的版本要兼容如果你用的 Spring Boot 2.7.xMyBatis Plus 用 3.5.x 即可。6.3 后端启动步骤与常见报错后端启动流程其实很简单在 IDEA 中打开项目等待 Maven 下载好所有依赖然后找到启动类GarbageApplication.java右键 Run 即可。启动成功后控制台会打印 Spring Boot 的 logo 和 Tomcat 端口号比如Tomcat started on port(s): 8081。但第一次启动经常遇到问题我把最常见的几条列出来端口被占用。报错信息是Port 8081 was already in use解决方式有两种关掉占用端口的进程或者在application.yml里换一个端口。Maven 依赖下载慢或失败。一定要在settings.xml里配置阿里云镜像否则下载 Spring Boot 依赖时会怀疑人生。找不到启动类。检查src/main/java下的包路径是不是被 IDEA 正确识别为源码根目录通常右键该目录选择“Mark Directory as Sources Root”就能解决。JDK 和 Spring Boot 版本不匹配。如果你的是 Spring Boot 3.x就必须要 JDK 17 及以上否则编译直接报错。如果代码本身没问题但就是启动失败优先检查版本匹配。6.4 前端启动步骤前端启动前先确认 Node.js 和 npm 已经安装好然后在项目根目录打开命令行执行npm install安装依赖。这一步耗时取决于网络和机器国内建议配置淘宝镜像源npm config set registry https://registry.npmmirror.com能明显加速。依赖装完后执行npm run serve控制台会显示本地访问地址通常是http://localhost:8080。浏览器打开这个地址就能看到系统首页。此时前端默认请求后端接口的地址如果前后端分别在 8080 和 8081 端口启动且后端已配置允许跨域或用代理那么页面数据就能正常加载。如果页面可以打开但数据为空优先排查浏览器开发者工具里 Network 标签页看看请求是否失败、状态码是多少。如果提示跨域错误检查后端是否配置了 CORS 过滤器或者前端vue.config.js里是否配置了代理。7. 常见问题与排查技巧实录7.1 数据库连接与编码相关的坑这类问题在起步阶段最折磨人。我遇到过的情况包括本地 MySQL 是 8.0但驱动依赖是 5.1.49 老版本启动直接报Public Key Retrieval is not allowed。这个报错的解决方案有两种在 jdbc url 后面加allowPublicKeyRetrievaltrue或者把 mysql-connector-java 升级到 8.0.x。建议直接升级驱动一劳永逸。中文乱码问题也常见。如果后端返回的数据都是问号检查三处数据库表字符集是否为 utf8mb4、application.yml里的characterEncodingutf8是否配置、前端页面 meta 标签的 charset 是否为 utf-8。这三个地方任何一个不对都会导致中文显示异常。还有一个隐蔽的问题MySQL 8.0 的默认认证插件是caching_sha2_password有些老的客户端连接不了。这种情况下可以在 MySQL 里把用户认证插件改为mysql_native_password或者升级客户端版本。这个问题在 Navicat 旧版本上特别容易出现。7.2 Spring Boot 版本过高导致的依赖冲突创建项目时如果直接指定最新版本比如 Spring Boot 3.2.x那你就要做好心理准备很多教程里用的依赖都要跟着升级。最典型的例子是springfox-swagger2这个库在高版本 Spring Boot 下配置会非常麻烦容易产生 NullPointerException。如果你不想在配置上花太多时间就老老实实用 Spring Boot 2.7.x。另外Spring Boot 3.x 里javax.servlet变成了jakarta.servlet如果你从老代码迁移过来所有 import 都要改。虽然改动量不大但对毕业设计来说完全是没用必要增加的工作量。我的建议是不追求版本新追求版本稳。最后再提醒一个关于 MyBatis Plus 分页插件的坑新版的分页插件要配置MybatisPlusInterceptor这个 Bean否则分页查出来的结果永远是全量数据。很多同学发现“为什么我传了 page 和 size 参数但还是返回所有记录”原因就是没有注册这个拦截器。配置方法很固定写一个配置类加一个Bean就行。7.3 前端跨域、路由与数据渲染问题跨域问题前后端分离项目 100% 会遇到。解决方式有三个层级开发环境用 Vue CLI 的 devServer proxy 把/api前缀的请求代理到后端后端通过 CORS 过滤器加响应头生产环境用 Nginx 反向代理把前端静态资源和后端接口统一在同一个域名下。毕业设计阶段前两个就完全够用了。路由跳转后页面空白也是常见问题。排查思路先看控制台有没有报错如果没有大概率是路由表配置的组件路径不对或者组件没有默认导出。我曾经遇到过因为文件名大小写不一致导致路由匹配不上页面的情况Home.vue和home.vue在 Windows 上不受影响但部署到 Linux 上就会找不到文件。所以文件名一定要严谨统一。前端数据渲染不出来时不要急着改代码先打开开发者工具的 Network 面板看接口返回。如果接口返回的字段名和后端实体类不一致比如后端的userName被序列化成username那前端绑定user.name就取不到数据。这种问题排查起来很快但不知道思路的人可能折腾半天也找不到原因。8. 答辩准备与项目扩展建议8.1 怎么讲才能让答辩老师给出高分第一个核心原则不要只演示功能要讲“为什么”。比如演示垃圾分类查询时不要只说“我输入塑料瓶它就显示可回收物”而是说“垃圾物品的数据是存在 garbage_item 表里的创建时关联了 garbage_category 表查询接口优先精确匹配、然后模糊匹配如果命中不了就返回一条友好提示保证用户不会因为查不到而失去耐心”。第二个核心原则准备好回答一些“刁钻”问题。比如老师可能问“如果数据库里垃圾名称有 10 万条模糊查询会不会很慢”这个问题你可以提前准备好答案当前数据规模下 MySQL LIKE 查询足够快如果未来数据量更大可以引入全文索引或做成倒排索引思路的简单搜索也可以给item_name建索引优化。能答出“当前方案适用未来优化方向清晰”老师就觉得你有工程思维。第三个核心原则对项目中的每个表结构都了然于心。老师随便问到“积分兑换记录表有哪些字段”“预约状态怎么管理”你都要能流利答出来。建议答辩前自己把数据库脚本从头到尾读两遍把每个字段的用途都能解释清楚。8.2 项目可以扩展的方向如果你时间充裕系统还有一些值得扩展的方向。第一个方向是接入图像识别分类让用户上传垃圾照片后端调用图像识别接口返回类别横跨了前后端、AI 和接口设计三个层面项目档次瞬间提升不过实现复杂度也会明显增加。第二个方向是做一个数据可视化管理页面用 ECharts 展示每天分类查询次数最多的垃圾、各分类垃圾的查询占比、用户积分分布等统计图表这类页面不仅好看还能支撑你论文中的“系统测试与分析”章节。第三个方向是部署上线把后端打包成 jar 放到服务器、前端打包成 dist 目录用 Nginx 托管数据库放到云数据库这样就从一个“毕业设计”升级成一个真正能访问的在线系统。我在给学弟学妹们做项目迭代时最常说的一句话是毕业设计本身就是一次完整的工程实践机会不要只把它当成交作业。做完这套系统Spring Boot 的接口开发、Vue 的组件通信、前后端联调、数据库建模、Linux 部署这些你都会有一个完整的概念找实习面试时至少能聊上半个小时不心虚。8.3 最后分享一个调试小技巧项目最容易出问题的地方往往是前后端数据格式对不上。我个人的经验是每次前后端联调之前先用 Postman 或者 Apifox 把每个后端接口都测一遍确认接口的入参、出参都正常再开始写前端页面。不要等到前端写完了再去联调那样一旦出问题你都不知道是后端的问题还是前端的问题排查起来非常痛苦。还有一个小建议在 IDEA 和 VS Code 里都开启代码自动保存和 ESLint 检查前端代码多多少少会踩到语法警告的坑。Vue 项目如果有一个页面里组件忘记注册运行时不会直接报错只是页面空白这种问题在没有编译错误提示的情况下排查会耗费很久。先跑通一个最小可用版本再逐步迭代加功能比一口气写完再调试要高效得多。本文还有配套的精品资源点击获取