资讯动态

SpringBoot+Vue+Uniapp商场停车场管理系统毕设全栈实现指南

发布时间:2026/10/13 11:55:27 来源:尧图企业网站定制
每年到毕设季停车场管理系统几乎都会出现在选题清单里需求量一直很大。原因也简单业务场景清晰、模块边界明确前端后端都有发挥空间扩展也容易。但真正把这个题目做到“能答辩、能演示、能讲清楚”不少人还是会在中后期翻车。我最近帮几个学弟学妹梳理了一套基于SpringBootVueUniapp的商场停车场管理系统后端管理端和用户端的小程序/App都覆盖到了从需求分析、数据库设计、核心代码到配套的源码、论文和PPT整理方法完整走了一遍。今天把这些内容系统整理出来给准备拿这个题目做毕设或者想独立完成一个全栈项目的你一条可以直接参考的路线。这套系统的完整交付形态一般包含三个工程目录SpringBoot后端工程、Vue管理后台工程、Uniapp用户端工程外加一个数据库初始化SQL脚本。三个工程分开存放README里写清楚启动步骤这样的项目结构放到论文和答辩里比“代码堆一堆、能跑就行”要加分得多。1. 项目整体设计与技术选型思路1.1 这个技术组合到底赢在哪先说技术栈。SpringBoot做后端接口Vue做管理后台Uniapp做用户端三者组合起来可以兼顾“管理端Web 用户端小程序/App”的完整场景。很多同学纠结要不要用Uniapp直接用微信小程序原生开发行不行行但Uniapp的价值在于一套代码可以编译到微信小程序、支付宝小程序、H5、甚至原生App。对于毕设演示来说你用微信开发者工具跑通一次后续换平台也不需要重写页面这个优势在论文里是实实在在的“技术亮点”。再往后端。SpringBoot本身就是现在Java后端的主流起步框架集成Web、MyBatis-Plus、Redis、JWT都很方便避开了SSH和SSM时代大量繁琐的XML配置。Vue管理后台用Element Plus能很快速搭出像样的后台界面。整个组合的思路可以概括成“面向业务闭环优先”把主要精力放在停车场业务流程本身的完整性上而不是纠结框架底层配置。对比一下传统JSPServlet方案最大的区别在于前后端分离。Vue和Uniapp共用一套后端接口管理员在Web端看到的数据和车主在手机端看到的数据是同一份接口层可以统一做权限控制。这个点在答辩时不需要讲得多高深一句“前后端分离之后用户端和管理端能共享业务接口”就已经比很多老旧方案有说服力了。1.2 商场停车场和普通停车场有什么不同如果只是把这个项目做成“无脑记录进出场时间出场按小时计费”后面被老师追问业务细节时大概率会卡住。商场停车场的计费逻辑比路边停车场复杂得多体现在几个地方商场的停车逻辑远比路边停车场复杂。比如通常有免费停车时长15分钟或者30分钟内不收费一旦超出才开始计费还有“消费满XX元免停X小时”的商场规则这就要引入优惠券或消费核销记录跨天停车时凌晨零点的计费规则可能又不一样夜间封顶价格也要单独配置同时还有固定车位和临时车位的区别月租车、时租车处理逻辑不同。所以数据库里不能只有“车牌号、入场时间、出场时间”三列就完事。必须要有车辆类型、优惠券、计费规则、支付状态、停车记录状态这些概念。这些延伸出来的内容既是系统设计的核心难点也是论文里最好写“研究意义”和“创新点”的地方。一个能在商场停车场真实落地的系统必须把这些业务规则放进设计里。1.3 整体模块划分把系统画成主线基本可以分成三大块第一块是管理后台给停车场管理员用负责车位监控、订单管理、车辆信息管理、优惠券管理、计费规则配置、数据报表统计。第二块是用户端给车主用负责登录注册、绑定车牌、查找空闲车位、模拟入场、在线缴费、出场确认、查看历史停车记录。第三块是后端服务统一提供接口负责权限校验、停车记录创建、费用计算、订单生成、车位状态维护和消息推送。这三块是互相联动的。车主在用户端提交入场后端会创建停车记录并修改车位状态管理后台的车位平面图上马上能看到状态变化订单列表也多了一条记录。这条数据流是贯通的也是整个项目答辩时最好讲的一条主线。你甚至可以拿它串起从数据库设计到接口设计再到前端交互展示的完整链路。2. 数据库设计与核心业务逻辑2.1 核心表结构与字段设计数据库设计决定了这个项目后面能走多远。我把最常用的一套表结构整理出来不少成型版本基本都是从这套表改出来的。用户表sys_user要有主键id、用户名、密码必须加密存储、手机号、角色类型管理员/普通用户、创建时间、状态。车辆信息表car_info要有id、用户id、车牌号、车牌颜色、车辆类型临时车/月租车/新能源车、是否默认车辆。车牌号这里强烈建议建唯一索引因为车牌是停车场业务最核心的索引键。车位信息表parking_space要有id、车位编号、所属区域、楼层、车位类型普通/新能源/无障碍、当前状态0空闲/1占用/2预占、绑定车辆id、更新时间。停车记录表parking_record要有id、车牌号、入场时间、出场时间、车位id、停车时长分钟、停车状态0进行中/1已支付待离场/2已完成。订单表pay_order要有id、停车记录id、订单号、应收金额、实收金额、支付状态0待支付/1已支付/2已关闭、支付方式、支付时间、优惠券id、减免金额。优惠券表coupon要有id、优惠券类型满减券/免停券、满额条件、减免金额或免停小时数、有效期、是否已核销。计费规则表parking_rule要有id、规则名称、免费分钟数、首个计费单位、首单位价格、后续单位价格、单日封顶金额、适用时段、是否启用。这些表加起来的核心逻辑是停车记录和订单表分开。为什么分开因为入场不等于马上支付用户可能先离场后补缴也可能先支付后离场优惠券核销和支付回调都需要独立订单来维护。如果合并成一张表写代码时会出现大量空字段状态流转会很混乱。表名核心作用关键字段sys_user用户与角色用户名、密码、角色类型car_info车辆与车主关系车牌号、车辆类型、用户idparking_space车位资源车位编号、区域、状态parking_record停车过程车牌号、入场时间、车位id、状态pay_order支付与结算订单号、金额、支付状态、优惠券idcoupon优惠券满额条件、减免金额、有效期parking_rule计费规则免费分钟、单价、封顶金额、适用时段2.2 停车状态怎么流转核心状态有三类车位状态、停车记录状态、订单支付状态。这三个状态不要混在一个字段里否则会写出更新极其困难的代码。车位状态0空闲、1占用、2预占。停车记录状态0进行中、1已支付待离场、2已完成。订单状态0待支付、1已支付、2已关闭、3退款。正常流程是这样的。入场时校验车牌是否绑定、是否黑名单、车位是否空闲月租车会优先分配固定区域然后创建停车记录车位状态改为占用。用户出场前在手机端查询费用点击支付订单状态改为已支付停车记录状态改为“已支付待离场”。最后出口道闸校验到已支付记录后放行停车记录改为已完成车位状态释放为空闲。这里有一个特别值得说的点为什么要把“已支付待离场”和“已完成”分开因为支付成功到车辆真正开走之间还有时间差。如果支付后立刻释放车位车还没挪走另一个车就可能被分配进同一个车位这在真实停车场里是非常严重的事故。能把这个逻辑讲清楚是答辩中一个很有质量的细节。2.3 计费规则的实现思路计费规则字段设计好之后具体计算逻辑要放进一个独立的计费服务里不要写在Controller里。临时车按时长计费基本分三步先判断是否在免费时长内在免费时长内直接返回0元超出免费时长后按计费粒度向上取整比如每30分钟为一个计费单位哪怕只超了1分钟也按一个单位算最后对比单日封顶金额超过封顶就按封顶收。跨天计费是另一个难点。更稳妥的做法是把入场时间和出场时间按自然日拆成多段每段应用当天的计费规则最后汇总。比如入场是晚上23点出场是次日凌晨2点那前1小时按白天规则后2小时按夜间规则两张计费规则各算各的。这块代码可以在项目里做成一个单独的计价方法也是论文里一个很好的技术细节。下面贴一段简化版的日常计费核心逻辑public BigDecimal calculateFee(ParkingRecord record, ParkingRule rule) { long minutes Duration.between(record.getEntryTime(), record.getExitTime()).toMinutes(); // 免费时长内直接返回 0 if (minutes rule.getFreeMinutes()) { return BigDecimal.ZERO; } // 超出部分按计费粒度向上取整 long billable minutes - rule.getFreeMinutes(); long steps (billable rule.getBillingStep() - 1) / rule.getBillingStep(); // 逐单位累加费用 BigDecimal fee rule.getPricePerStep().multiply(BigDecimal.valueOf(steps)); // 单日封顶 if (rule.getDailyCap() ! null fee.compareTo(rule.getDailyCap()) 0) { fee rule.getDailyCap(); } return fee; }这个只是基础版本真实跨天场景还得按天拆分。用BigDecimal而不是double是为了避免金额精度问题。别小看这个选择答辩老师问到金额计算时能说出“用BigDecimal避免浮点误差”会显得很专业。3. 后端SpringBoot核心实现3.1 工程分层和常用依赖后端工程建议按标准分模块方式组织controller层负责接口路由service层负责业务逻辑mapper层负责数据库操作entity层放实体类dto层放接口出入参config层放配置类utils层放工具类。包名统一层次清晰论文里的架构图也会好画很多。依赖推荐用这些spring-boot-starter-web、mybatis-plus-boot-starter、mysql-connector-j、lombok、jjwt、spring-boot-starter-data-redis。其他像hutool这种工具包也可以加但并不是必须。使用MyBatis-Plus能省掉单表CRUD的大量XML保留自定义SQL的能力即可满足复杂查询。如果项目里引入了Redis就要想清楚它的场景。我的建议是把热门车位状态和用户登录token放入Redis缓存但写入核心停车记录必须以数据库为准。缓存和数据库的一致性不必做太复杂先更新数据库再删除缓存同时给缓存设置一个过期时间兜底就能满足毕设场景。3.2 关键接口一览后端接口设计成RESTful风格会很好说明。下面是主流程接口的概要模块接口路径方法说明用户认证/api/auth/loginPOST登录并返回JWT绑定车牌/api/car/bindPOST绑定车牌到账号查询车位/api/parking/space/listGET按区域查询空闲车位入场开闸/api/parking/entryPOST创建停车记录查询费用/api/parking/feeGET根据停车记录计算费用在线支付/api/order/payPOST创建订单并调起支付离场确认/api/parking/exitPOST校验支付后释放车位后台概览/api/admin/dashboardGET今日流量、收入统计接口设计的原则是尽量做到“一个操作一个接口”。入场和离场是操作型接口用POST车位和费用是查询型接口用GET。不要为了减少Controller方法数量把多个操作塞到一个接口里这会让我们后面写权限控制变得更麻烦。3.3 入场核心逻辑实现入场接口是第一个有并发风险的接口。同一个车牌重复提交入场请求或者两个请求同时分配同一个车位都是需要处理的问题。最简单的处理方式是在数据库层做一个原子更新直接对车位状态进行CAS操作Transactional public ParkingRecord entry(String plateNo, Long spaceId) { // 1. 校验车辆是否已绑定 CarInfo car carService.getByPlateNo(plateNo); if (car null) { throw new BizException(未绑定车牌); } // 2. 车位状态原子更新0 - 1 int rows parkingSpaceMapper.compareAndSetStatus(spaceId, 0, 1); if (rows 0) { throw new BizException(车位已被占用请刷新重试); } // 3. 生成停车记录 ParkingRecord record new ParkingRecord(); record.setPlateNo(plateNo); record.setEntryTime(LocalDateTime.now()); record.setSpaceId(spaceId); record.setStatus(0); parkingRecordMapper.insert(record); return record; }这里先用数据库的原子更新抢占车位再插入停车记录而不是先select判断再update。因为select和update之间有时间窗口两个并发请求都能查到“空闲”然后一起抢这一个车位。有了UPDATE ... WHERE id ? AND status 0这种前置条件只有第一个请求能成功更新状态第二个请求的影响行数为0直接提示失败。能讲出这个方案答辩时“高并发车位分配”这个问题就过关了。还有一点需要落实停车记录表里要对“同一车牌当前未完成”的情况做业务限制或者建一个唯一索引。否则用户重复点击入场按钮会出现同一车牌产生两条“进行中”的停车记录。3.4 离场、支付与权限细节离场接口逻辑上要判断订单是否已支付。车辆出场时如果还有未支付订单系统需要提示“请先支付后再离场”。如果订单已支付则把停车记录状态置为已完成同时释放车位。注意释放车位前要再次确认车辆还在场内避免重复出场。这里有一个容易忽略的问题车辆支付成功但还没出场车位状态一直是占用占用时间继续增加费用是否继续计算真实商场中的规则是不继续计费因为订单已经生成且已支付金额不会再变。所以当订单创建成功后停车时长和费用就应当“锁定”在一个快照里离场接口不要回头再重新计算。这个点经常被老师拿来问如果你能回答“已支付订单费用固定离场不再重新计费”说明你真的理解业务闭环。权限部分推荐用JWT作为身份凭证。Vue和Uniapp都没有Cookie概念用一个无状态的Token最方便。后端只需要一个拦截器校验请求头里的Authorization解析出用户身份和角色即可。实现时注意两个细节JWT密钥不要写在代码里可以放在配置文件通过环境变量注入密码存储不要用MD5至少用BCrypt这几乎是安全方面的基础要求。Redis在这个项目里可以做几件事缓存登录Token、缓存车位状态列表、防止支付回调重复处理。尤其是车位状态使用Redis的Map保存每个车位状态后前端车位平面图可以快速加载不用每次都全表查数据库。但存在一个需要注意的细节如果修改车位状态时Redis更新失败数据就会不一致。我的处理方式是数据库更新成功后再更新RedisRedis更新失败时主动删除缓存让下一次查询回源到数据库。这个方案简单实用适合毕设项目。4. 后台管理和用户端实现4.1 Vue管理后台页面规划与实现要点管理后台是整个系统展示“成熟度”的地方。建议最少包含这些页面登录页、工作台系统概览、车位监控、订单管理、车辆管理、优惠券管理、数据报表、系统设置。车位监控页面是最能出效果的一页。可以用一个二维平面图模拟停车场布局每个车位是一个卡片按区域排列空闲显示绿色、占用显示红色、预占显示黄色。刷新方式有两种选择简单方案是前端定时轮询接口每5秒拉一次车位列表实现简单但不算优雅加分方案是后端使用WebSocket推送车位变化事件Vue端收到消息后只更新受影响的车位卡片。WebSocket的写法并不复杂。SpringBoot里声明一个WebSocketConfig注册访问端点前端用一个全局WebSocket连接收到消息后解析出车位id和状态再调用本地状态更新方法。用户在端上入场或离场时后端广播一条变更消息其他在线管理员就能实时看到。论文里把这部分写上可以在“实时性说明”中占一个不错的篇幅。数据报表用ECharts展示。重点推荐四张图近7日收入走势折线图、今日车流量时段分布柱状图、当前车位占用率环形图、今日支付方式占比饼图。这些统计接口都是基于订单表和停车记录表做聚合查询数据量不大直接写MySQL的GROUP BY查询就行不需要额外引入数据仓库工具。4.2 Uniapp用户端功能实现用户端页面不需要太多但主流程必须完整。设计这些页面就够了首页、找车位页、绑定车牌页、停车记录页、缴费页、我的页面。首页要解决的问题最重要就是“让用户一眼知道我现在是什么状态”。我给你返回状态判断例如当前是否有正在进行中的停车记录有就显示入场时间和车辆所在区域没有就显示剩余车位数量并提供找车位入口。这是停车场用户端最核心的信息。找车位页可以用列表形式展示车位也可以用地图。列表实现简单但地图效果更贴合真实场景。Uniapp内置的map组件可以在地图上打标记点每个车位对应一个Marker不同状态使用不同颜色的Marker图标。点击Marker后出现底部弹窗显示车位编号、类型、距离点击“导航到这里”能调起导航软件。绑定车牌页是用户端一个重要前置操作因为不绑定车牌就无法模拟入场。车牌输入框需要考虑车牌号中包含汉字、字母和数字的情况前端做格式校验后端做数据校验格式统一存大写。在模拟入场页面是直接输入车牌号还是从绑定的车辆里选一辆我建议从绑定列表里选更符合真实逻辑。支付环节最麻烦。毕设阶段很难有真实的微信商户号我建议做一个模拟支付流程后端根据停车记录生成订单订单状态置为待支付前端弹出一个支付确认弹窗点击确认后调用一个模拟支付接口后端直接更新订单为已支付。这个流程在答辩演示中比接入真实的支付SDK更稳定同时预留了以后接入的能力。跨端差异用Uniapp的条件编译来处理。比如H5和小程序获取登录凭证的方式不同#ifdef MP-WEIXIN和#ifndef MP-WEIXIN在同一个页面文件里对登录逻辑做分支。这个知识点写进论文“跨平台解决方案”小节能体现你对客户端工程的理解。4.3 管理端和用户端的权限控制权限要把管理员接口和用户接口分开。后端可以在路径设计上区分/api/auth/**面向所有已登录用户/api/admin/**要求管理员角色。拦截器校验JWT时先从Token里解析出角色再根据路径判断是否允许访问。Vue管理端用路由守卫做页面级别控制。用户没有登录时跳转登录页登录后根据返回的角色渲染动态菜单。Uniapp端的权限没那么复杂主要控制到“是否显示管理员入口”这一层。真实的停车场系统中管理员可能是多个角色比如超级管理员、财务、保安各有各的权限。毕设项目中做一个简单的角色字段区分管理员和普通用户即可不需要引入专门的权限框架否则会占用大量时间去维护配置。如果你想让权限这部分显得更完整也可以在后端引入Sa-Token或Spring Security。但我个人建议在没有充分时间的情况下一个自定义拦截器外加一个角色字段足够应对常规答辩。把省下来的时间投入到业务主流程的打磨上性价比更高。5. 论文与PPT的包装思路5.1 论文结构怎么安排论文写作不要按照代码目录结构写而应该按照软件工程流程写。推荐章节安排是引言背景与意义、国内外现状、主要研究内容、需求分析功能性需求、非功能性需求、用例图、可行性分析、系统设计总体架构、功能模块、数据库设计、接口设计、系统实现按模块展示核心代码、界面截图和效果说明、系统测试测试环境、测试用例、测试结果分析。写论文时最容易被导师挑的问题有三个。第一个是没有数据字典只有建表SQL截图正确的做法是列成表格写清字段名、数据类型、是否允许为空、字段说明。第二个是核心代码贴得太多整段整段堆代码不仅占篇幅也看不出设计思路论文里只需要放关键方法的核心代码片段配一段文字说明逻辑即可。第三个是缺少真实测试数据性能测试和接口测试结果最好真的跑出来比如用Postman测接口响应时间统计一批并发请求的成功率。这里有一个很实用的写作技巧论文里每一个“功能模块实现”小节都可以按“界面截图 核心代码片段 业务逻辑说明”结构来写。界面让老师直观看到效果代码片段说明你确实实现了逻辑说明解释你理解背后的原理。三件套齐全这个小节的文字量就达标了。5.2 图表怎么画画图工具用Draw.io或ProcessOn都行不需要花哨。重点画四张图系统总体架构图、功能模块图、数据库E-R图、核心业务时序图。系统总体架构图画成分层结构从上到下分别是展示层Vue管理后台、Uniapp客户端、应用层SpringBoot服务、权限控制、业务服务、消息推送、数据层MySQL、Redis。这张图放在论文“系统设计”的第一位置基本就是全篇技术含量的代表。数据库E-R图是必备。把用户、车辆、停车记录、订单、车位、优惠券、计费规则之间的关系画清楚。注意E-R图不是把所有字段都画上而是主要表现实体和关系字段明细放在数据字典表格里不要重复堆到一张图上。核心业务时序图建议画“入场到出场”的完整流程用户端请求入场、后端校验车位、创建停车记录、用户缴费、支付回调、用户离场、释放车位。这张图画出来答辩翻到这页就可以顺带把主流程讲一遍老师一下子就能看懂系统做了哪些事。5.3 PPT答辩路线和常见提问PPT做20页左右就够了不要贪多。答辩现场核心是演示而不是读PPT。推荐顺序是题目页加项目价值、技术选型、系统架构图、数据库设计、功能演示录屏、核心代码讲解、测试结果、总结与展望。功能演示录屏是最容易出效果的部分。提前录好一段操作视频内容包含用户端绑定车牌、模拟入场、查看费用、模拟支付、离场然后切换到管理后台刷新订单列表、查看数据报表。如果现场有网络直接连数据库做实时演示也行但录屏可以作为Plan B防止现场出了任何意外切不过来。老师围绕这个题目最常问的问题我整理成了一张速查表提前把答案背熟问题建议回答为什么用JWT而不用Session前后端分离接口无状态扩展性好Redis挂了怎么办数据库保存最终数据缓存降级后可回源查询并发时同一个车位会被重复分配吗不会车位状态更新采用原子CAS方式跨天计费怎么处理按自然日拆分停车时长分段应用规则汇总支付成功但车没走车位是否释放不释放订单状态和停车记录状态是分开的为什么用BigDecimal计算金额double存在浮点精度问题金额计算必须精确这六个问题能答上来整套系统的逻辑你基本已经掌握了。比起堆砌功能答辩时“讲得清”才是拿高分的关键。6. 常见问题与排查技巧实录6.1 高并发抢车位导致状态不一致这是写停车管理系统的第一个大坑。有人习惯“先查车位是否空闲再更新占用”并发下两个请求都查到空闲结果都认为抢到了。解决方式上文已经提到用原子更新语句UPDATE parking_space SET status 1 WHERE id ? AND status 0再通过影响行数判断是否成功。如果使用MyBatis-Plus可以在Mapper里自定义SQL也可以用MyBatis-Plus的乐观锁注解。我在实际项目中还遇到过另一种情况用户并发提交入场车位状态更新成功但停车记录插入失败导致车位被占住但没有订单记录。解决办法是给入场逻辑加事务管理Transactional包住车位更新和停车记录插入任何一个失败都回滚。别小看这个细节真实联调时最容易出这种“半路失败”问题。日志也要加上。入场、支付回调、离场这几个关键操作务必打印日志包含请求参数和响应结果。排查问题的时候没有日志就只能靠猜。6.2 跨天计费算错导致金额异常跨天计费是计费模块最容易出错的部分。简单方案是把出入场时间差算成分钟数再套一套规则但遇到跨天时会出现停车3小时被按两天白天标准收费的尴尬结果。更好的实现是拆分时间段入场当天、中间完整自然日、出场当天每段独立调用当天规则最后把各段费用累加。拆分实现并不复杂核心是循环切分时间区间。先把入场时间的零点作为第一个切分点每次前进一天直到覆盖出场时间。注意时区问题LocalDateTime默认跟随系统时区数据库连接串要设置serverTimezone否则时间差八小时切分位置全错。我建议在单元测试里专门写几个跨天测试用例入场23:50出场次日00:10入场23:00出场次日02:00入场周五出场周一这类边界场景全测一遍。测试通过后计费模块基本就稳了答辩时也可以拿出测试用例说明你做过边界校验。6.3 微信支付没有商户号怎么办支付是很多毕设同学的卡点原因是真实支付必须绑定营业执照和商户号个人很难申请。毕设阶段最稳妥的方案是“模拟支付”后端有真实支付接口的雏形但支付方法体里只做订单状态更新不真正调用第三方支付。具体做法是在支付服务里增加一个开关比如配置文件中在演示环境下将pay.mock-enabledtrue当开关打开时调用支付接口直接返回“支付成功”订单状态更新成已支付。在论文中还可以加一句“预留第三方支付接入能力”表示后续只需要替换支付调用底层实现即可不影响上层业务。这个方案在演示时非常稳定也不会因为某个真实支付参数报错而现场翻车。6.4 小程序请求本地接口失败小程序端最常见的问题就是请求不到本地后端接口。微信开发者工具默认对域名做合法性校验使用localhost或局域网IP时会被拦截。解决方法是打开微信开发者工具在“详情-本地设置”里勾选“不校验合法域名、web-view业务域名、TLS版本以及HTTPS证书”。除了这个设置还要注意请求地址不能写localhost。开发者工具里的模拟环境可以访问本机但真机预览时手机访问的是电脑的局域网IP需要在Uniapp的配置文件里区分开发环境的baseURL。我一般会把baseURL做成环境变量开发时指向局域网IP上线时换成正式域名。这个问题不是代码bug而是环境配置第一次遇到会卡很久。6.5 数据库时间差八小时很多人在页面上看到的时间和数据库不一致比真实时间少了8小时几乎都是JDBC时区设置问题。MySQL连接串上要显式加上serverTimezoneAsia/ShanghaiJava实体统一使用LocalDateTime前端展示时间由后端格式化好返回。不要在每一层都手动转时区那样很容易出现双重转换。部署到服务器后还要检查系统时区使用date命令确认是否为Asia/Shanghai。如果服务器时区是UTC应用起来后时间又会差八小时。这个排查点经常被忽略一旦出现感觉像是代码问题其实是环境问题。6.6 图片上传和车牌识别怎么落地真实停车场会接摄像机和车牌识别SDK但毕设项目不需要强上。设计时在停车记录表中预留“入场图片”和“出场图片”字段即可实际演示时让用户从相册选择图片或者直接输入车牌号。入场接口的参数里已经包含车牌号真正接入识别时只需要把“识别结果车牌号”作为参数传入其他逻辑不用改。如果你想让系统看起来更真实可以加一个简单的图片上传接口前端把车牌图片上传后后端调用一个预设的识别服务并返回结果。没有真实SDK的情况下也可以做成“返回用户选择或输入的车牌号”的模拟识别。重点是在论文中把扩展思路写清楚让老师知道你有面向未来的接口设计意识。6.7 部署演示时的环境问题答辩现场最容易翻车的不是逻辑bug而是环境问题。教室断网、CDN加载失败、数据库没启动、端口被占用这些都可能让演示白屏。我的习惯是答辩前单独做一次“断网白屏测试”把一切外部网络依赖切断只保留本地后端和前端看看系统还能不能完整跑起来。Vue管理后台如果依赖CDN上的Element Plus或ECharts断网后页面会直接白屏。所以打包时要把依赖全部本地化不要使用外链CDN。后端接口地址不要写死localhost部署到演示机器上用127.0.0.1或者局域网IP并确保防火墙放行了8080端口。数据库导入好初始数据提前准备一份固定账号和密码演示时不会被临场输入卡住。最后再分享一个我在实际带项目中的体会这个题目想做得“能交差”不难但想做得“能讲透”需要把业务状态理清楚。你可以功能少一点但入场、计费、出场、支付这条主链路一定要闭环数据库里的状态流转要能自圆其说。如果后续想扩展可以考虑往月租套餐、会员积分、车位预约、反向寻车这几个方向加每一个都会让系统更有真实项目的分量也比单纯堆页面有价值得多。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑