前阵子有个做养老信息化项目的朋友跟我聊起他们公司的系统架构,我脑子里第一时间冒出来的,就是SpringBoot+Vue这套组合。说实话,近几年我接触到的智慧园区、智慧社区、医院信息管理类项目,十有八九都是这个技术栈,智慧养老中心管理系统更是如此。毕竟Java生态足够稳、SpringBoot极大降低了配置成本,Vue上手快、组件生态完善,MySQL部署成本低,这三样拼在一起,做一套给养老中心用的管理平台,无论从开发效率还是后期维护角度看,都是性价比极高的方案。
我自己完整拆过、也带人做过几个类似的系统源码项目,对这个领域的业务逻辑、代码组织、常见坑点都很熟悉。如果你正打算拿“智慧养老中心管理系统”当毕业设计、课程设计,或者想通过一个完整的前后端分离项目来练手SpringBoot、Vue、Java、MySQL这套技术栈,那这篇文章能帮你少走很多弯路。我会从一个真实开发者的角度,把项目拆开来讲:从后台管理、老人档案、健康数据、护理工单到前台可视化大屏,每个模块怎么设计、表结构怎么定义、接口怎么调、常见问题怎么排查,都会尽量落到具体代码和配置层面。
1. 项目整体设计与功能拆解
1.1 养老中心到底需要一个什么样的系统
先说业务场景。智慧养老中心跟我们平时做的普通企业管理系统有个明显的区别:它服务的对象是老人、护理人员和机构管理者三拨人,而且业务链条很长,从前台接待、入住登记、房间分配,到日常护理、健康监测、餐饮安排,再到费用结算、家属探视,每一个环节都产生数据,也都需要管理。
我做养老类项目时,第一件事就是跟客户确认“谁在用这个系统”。大多数养老中心管理系统源码里,角色基本固定为三类:系统管理员、护理人员、老人家属。管理员管全局,负责员工排班、收费标准、房间床位管理、数据统计;护理人员手里拿着工单,负责老人的日常起居、用药提醒、健康指标录入;家属则通过系统查看老人的身体状况、护理记录和费用明细。当然,很多毕业设计场景下还会加一个“超级管理员”的概念,用来初始化数据、分配账号。
搞清楚角色之后,功能模块就顺理成章了。我梳理过一套非常通用的模块划分,绝大多数智慧养老管理系统源码项目都遵循这个结构:
- 老人档案管理:基本信息、家属联系方式、既往病史、过敏药物、入住时间、房间床位绑定
- 健康监测管理:血压、心率、血糖、体温等指标录入,支持趋势图表展示
- 护理工单管理:护理任务的创建、指派、完成状态跟踪,比如定时巡房、送餐、助浴
- 床位与房间管理:楼层、房间、床位的层级关系,入住率统计,换房/退房操作
- 餐饮管理:每周菜谱、老人饮食禁忌、送餐记录
- 费用管理:床位费、护理费、餐饮费、医疗费,按月生成账单
- 系统管理:用户管理、角色管理、菜单权限、操作日志
- 数据统计与可视化:入住率、护理任务完成率、健康指标分布,用图表展示在首页大屏
这个模块划分的好处是,既覆盖了真实业务,又能让评委或老师一眼看出你对业务的理解深度。而且每个模块的难度梯度也合适:基础的是CRUD,进阶一点的是健康指标折线图、工单状态流转、权限拦截,再加个Excel导入导出,整个项目的完成度和含金量立马不一样。
1.2 核心模块的数据流转逻辑
数据流这块,我一般会先画一个草图(不要笑,拿到代码之前先看数据怎么走,能避免很多后期返工)。前端Vue组件里,用户点击或者页面加载时,通过Axios发起HTTP请求,到达SpringBoot的Controller层,Controller接收参数后转发给Service层,Service里处理业务逻辑,然后通过MyBatis(或者MyBatis-Plus)操作MySQL数据库,数据返回时再逐层封装回去,最终由Vue用双向绑定渲染到页面上。
以“护理人员录入老人血压数据”这个操作为例,完整的链路是这样的:
- 护理人员登录系统,Vue前端用JWT Token调用后端
/api/health/record接口 - SpringBoot的
HealthRecordController收到POST请求,参数里带着老人ID、血压值、心率等 HealthRecordService里校验参数,调用HealthRecordMapper.insert()往health_record表里写入一条记录- 同时Service层做了一件事:判断血压值是否超出正常范围,如果超标,自动往
alert_log表里插入一条预警记录,并且标记为“待处理” - 返回结果给前端,前端刷新表格和图表
这套流程看起来简单,但里面有几个可以写进毕业设计论文里的亮点设计:参数校验用@Validated注解、统一返回结果用R对象封装、异常用@RestControllerAdvice做全局捕获,健康值异常自动触发预警,这都属于能加分的细节。
1.3 为什么这套项目特别适合当毕设
我见过太多毕设选题了,有的太简单(比如纯CRUD的学生信息管理),答辩时没什么可讲;有的太难(比如要做分布式微服务、高并发秒杀),吭哧吭哧搞半年还没跑通。智慧养老中心管理系统恰恰卡在一个“恰到好处”的位置。
首先是业务复杂度适中。管理系统的核心还是增删改查,但养老这个场景天生自带几个亮点:健康数据可能产生连续时间序列,适合做图表;护理工单有状态流转,适合做流程控制;权限系统要区分三类角色,适合做Spring Security或者拦截器+JWT的权限演示。这几个点既有技术深度,又不至于让人卡死。
其次是技术栈主流。SpringBoot、Vue、MySQL是当前企业里Java开发和前端开发最常用的组合之一。哪怕你以后出去找工作,面试官看到这个项目也会跟你多聊几句。而且这套技术栈的社区资料特别丰富,我在文章后面整理的常见问题,基本都是网上被反复问到的,说明大家做的项目高度相似,遇到的问题也高度一致,你踩坑时总能搜到答案。
最后是扩展空间灵活。基础版做完之后,你还可以加物联网设备模拟(比如用一个定时任务生成心率数据)、加消息通知(老人血压异常时给家属发短信或站内信)、加微信小程序端。这些扩展点我在文章最后会细说,你可以根据自己的时间和能力酌情选择。
2. 技术选型与核心原理分析
2.1 后端:SpringBoot + MyBatis-Plus + MySQL
SpringBoot能成为Java后端开发的事实标准,核心就是“约定大于配置”。以前用SSM框架写项目,光xml配置文件就能堆一摞,SpringBoot把内嵌Tomcat、自动配置、Starter依赖管理全做进去了,你只需要在pom.xml里引入几个依赖,写个启动类,一个web服务就起来了。智慧养老这类管理系统,业务逻辑没有特别复杂的交易和并发,SpringBoot默认的配置完全够用,而且它有一个特别契合毕设场景的优点:自带spring-boot-devtools热部署,改完代码自动重启,这能让你在调试阶段省下大量时间。
MyBatis-Plus是MyBatis的增强版,我个人的态度非常明确:单表CRUD你手写SQL纯属浪费时间。MP提供了BaseMapper接口,里面封装好了selectById、selectPage、insert、updateById这些通用方法,你继承一下就能用。举个例子,实现老人档案的分页查询,用MP可以写成:
public interface ElderMapper extends BaseMapper<Elder> { } // Service层 page = elderMapper.selectPage(new Page<>(current, size), new LambdaQueryWrapper<Elder>() .like(StringUtils.isNotBlank(name), Elder::getName, name) .eq(status != null, Elder::getStatus, status) .orderByDesc(Elder::getCreateTime));这段代码干了什么?三件事:分页、按姓名模糊查询、按状态精确查询。如果换成手写XML,你需要写select count(*)、写limit、写动态if标签,逻辑一多还容易拼错SQL。MP帮我们屏蔽了这部分重复劳动,让你把精力放在业务上。当然,答辩的时候老师可能会问MP的原理,我当时就重点讲了两点:它的分页插件底层通过MyBatis拦截器对SQL做了改写(解析原SQL生成COUNT语句,再拼接LIMIT),它的条件构造器本质是个组合模式,通过Lambda表达式安全引用字段名,避免硬编码数据库列名。这两点能答上来,基本就稳了。
MySQL的选择相对简单。8.0版本现在已经是绝对主流,性能比5.7好,窗口函数、CTE这些新特性在某些统计场景下很好用。唯一需要注意的是时区问题,我后面的常见问题会专门提到。字符集用utf8mb4,排序规则用utf8mb4_general_ci,这就够了。表引擎默认InnoDB,支持事务,养老系统里账单、工单这类数据需要事务保护。
2.2 前端:Vue2还是Vue3,Element-UI还是Element-Plus
前端选型是很多同学纠结的地方。我的建议非常直接:如果你是第一次做Vue项目,而且目标是快速、稳妥地完成毕设,那就选Vue2 + Element-UI;如果你已经上手过Vue2,想借这个项目体验一下新东西,那就Vue3 + Vite + Element-Plus + Pinia。
原因很简单。Vue2 + Element-UI的存量资料是全网最多的,webpack脚手架的坑也都被人踩平了,你遇到问题去搜索引擎一查,几乎都能找到一模一样的报错和解决方案。Vue3是趋势,组合式API写起来确实更爽,但Element-Plus的某些组件细节和Vue2的Element-UI略有差异,而且Vite虽然有“快”的优势,但在一些老版本Node环境下也会出现兼容问题,对新手没那么友好。
我做这个项目时用的是Vue2 + Element-UI,但代码里会有意识地用一些进阶写法,比如Vuex做全局状态管理(存用户信息、权限标识)、Vue Router的导航守卫做路由权限控制。这里放一个典型的路由守卫代码,判断用户是否登录:
router.beforeEach((to, from, next) => { const token = localStorage.getItem('token') if (to.path === '/login') { next() } else { if (!token) { next('/login') } else if (to.meta.roles && !to.meta.roles.includes(store.state.user.role)) { next('/403') } else { next() } } })这段逻辑很简单:没登录就去登录页,登录了但角色不匹配就去403页面。很多毕设项目只做了“有没有登录”的判断,忽略了“登录之后有没有权限看这个页面”的判断,你要是能写出来,就是加分项。
2.3 技术版本搭配与资源规划
基于我做过的多个类似项目,给出一份经过验证的版本搭配表:
| 组件 | 推荐版本 | 备注 |
|---|---|---|
| JDK | 1.8 或 11 | JDK8兼容性最好,JDK11更现代 |
| Spring Boot | 2.7.x | 2.x系列成熟稳定,3.x需要JDK17起步 |
| MySQL | 8.0 | 5.7也能跑,8.0更推荐 |
| MyBatis-Plus | 3.5.x | 自带分页插件和代码生成器 |
| Node.js | 14.x ~ 16.x | 建议用16,配Vue2很稳 |
| Vue CLI | 4.x / 5.x | Vue2配4,Vue3也兼容5 |
| Element-UI | 2.15.x | 不要下成Element-Plus |
这份搭配表的特点是“中庸而可靠”。我见过有人拿SpringBoot 3.0 + JDK 17 + Vue3跑项目,确实很新,但SpringBoot 3.0对某些老版本依赖的兼容性会有问题,一旦遇到一个冷门报错,排查成本极高。毕设的核心目标是稳,新技术可以适当用,但没必要拿自己的进度去冒险。
3. 环境准备与项目初始化实操
3.1 数据库设计与初始化SQL的思路
拿到一个智慧养老管理系统源码,第一步不是急着启动,而是先看SQL脚本。大多数靠谱的源码包会提供两个文件:init.sql(建库建表)和data.sql(初始化数据)。如果只有一个文件,大概率两个功能合在一起了。
我建议你拿到项目后,先自己把表结构梳理一遍。养老系统的核心表我列一下,这些表是基本盘:
sys_user:用户表,包含用户名、密码(BCrypt加密后的密文)、姓名、手机号、角色IDsys_role:角色表,管理员/护理员/家属就三条数据elder:老人档案表,姓名、性别、身份证号、家属联系电话、既往病史、入住日期room/bed:房间表和床位表,房间有楼层、房号、类型,床位关联房间ID、老人IDhealth_record:健康记录表,老人ID、血压、心率、血糖、体温、记录时间nurse_task:护理工单表,任务类型、指派护工、老人、截止时间、状态(待处理/进行中/已完成)meal_menu:菜谱表,日期、早中晚餐内容、适用老人饮食要求cost_bill:费用账单表,老人ID、费用项、金额、账期、缴费状态sys_menu/sys_role_menu:菜单表和角色菜单关联表,做权限控制用
这十张表是智慧养老系统的基础骨架。其中sys_menu和sys_role_menu是用来做动态菜单的,登录后根据角色返回能看到的菜单列表,前端再根据菜单列表渲染侧边栏,这个设计在企业项目里很常见,写在毕设论文里也是个亮点。
有些源码项目会加device_data表(对接智能手环等设备的上报数据)、visit_record表(家属探视记录)、expense_type表(费用类型字典),这些属于锦上添花,可视情况增删。
3.2 后端启动:配置文件里的三个坑
数据库导入好之后,启动后端前一定要检查application.yml(或者application.properties)。我碰到过太多人在这里卡壳了,无非就那么几个点:
第一个是数据源配置。MySQL的url写法有讲究:
spring: datasource: url: jdbc:mysql://localhost:3306/smart_care?useUnicode=true&characterEncoding=utf8&serverTimezone=Asia/Shanghai&useSSL=false&allowPublicKeyRetrieval=true username: root password: 123456 driver-class-name: com.mysql.cj.jdbc.DriverserverTimezone=Asia/Shanghai是必须加的,不加的话,MySQL 8.0连接时会报“Cannot create PoolableConnectionFactory”或者时区错误,非常经典。allowPublicKeyRetrieval=true在MySQL 8.0的某些认证插件下也要加上,不然会报“Public Key Retrieval is not allowed”。
第二个是端口占用。SpringBoot默认8080,如果你本机已经跑了别的服务,启动就会报“Port 8080 was already in use”。解决办法有两种:改配置,server.port: 8081;或者找到占用进程干掉它。Windows下用netstat -ano | findstr 8080找到PID,然后任务管理器结束;Mac/Linux下用lsof -i :8080,再kill -9 PID。
第三个是MyBatis-Plus的配置。有些项目会用到逻辑删除,那全局配置里就要加上逻辑删除的字段名和值:
mybatis-plus: global-config: db-config: logic-delete-field: deleted logic-delete-value: 1 logic-not-delete-value: 0加了逻辑删除之后,你调deleteById时底层执行的是update set deleted = 1,而不是物理删除。这个设计对“老人退房但需要保留历史档案”这类业务特别有用。
启动类通常是SmartCareApplication.java,右上角点运行后,控制台出现“Started SmartCareApplication in 3.21 seconds (JVM running)”就说明服务起来了。接着你可以用接口调试工具(Postman、Apifox,或者网页直接访问)测试http://localhost:8080/api/login,传个JSON格式的用户名密码,看看能不能拿到Token。
3.3 前端启动:npm install的灾难现场
前端这部分,80%的同学会卡在依赖安装上。先说操作流程:
- 打开终端,进入前端项目目录
cd frontend - 安装依赖:
npm install - 启动开发服务器:
npm run serve - 浏览器访问
http://localhost:8080
听上去很简单对吧?但现实往往是npm install一跑就是十几分钟,好不容易装完,启动的时候报了一堆红色错误。我见过的前端启动问题主要分两类:
第一类是Node版本和依赖不匹配。比如node-sass就是个典型的“版本刺客”,它需要从GitHub下载二进制文件,国内网络环境下经常下载失败,报“Node Sass could not find a binding”。解决办法:如果是Vue2项目,把node-sass换成sass(dart-sass),兼容性更好,安装速度也更快;或者直接用镜像源:npm config set registry https://registry.npmmirror.com。装依赖之前先把镜像设好,能省一半时间。
第二类是ESLint的报错。Vue CLI创建的默认项目开了ESLint,很多时候你复制别人的代码进来,会因为多了个空格、多了个分号直接报错。解决办法:开发阶段在vue.config.js里把LintOnSave关掉:
module.exports = { lintOnSave: false, devServer: { port: 8080, proxy: { '/api': { target: 'http://localhost:8080', changeOrigin: true } } } }这里有个容易被忽略的配置:proxy。前端开发服务器端口是8080,后端SpringBoot端口也是8080,那就撞了。更合理的做法是前端用8081(devServer.port改掉),后端保持8080,然后前端通过代理把/api开头的请求转发到后端8080端口。这个代理配置能帮你规避掉开发环境下的跨域问题,比在后端加@CrossOrigin注解要正规得多。
前端启动成功后,浏览器访问,看到登录页、能正常输入账号密码跳转到首页,说明前后端联调已经打通了。
4. 核心功能模块的代码实现思路
4.1 登录、JWT鉴权与权限拦截
登录认证是每个管理系统的门面。智慧养老系统源码里通常用JWT方案,实现思路分三步。
第一步,用户提交用户名密码,后端UserController接收并调用UserService.login()。密码用BCrypt加密存储,校验时用BCryptPasswordEncoder.matches(原始密码, 数据库密文),千万不要把明文密码存在数据库里。验证通过后,生成JWT Token,把用户ID、用户名、角色ID放进去,设置过期时间(一般24小时),返回给前端。
第二步,前端把Token存在localStorage或者Vuex里,之后每次Axios请求都带上这个Token。这里要在axios的拦截器里做:
service.interceptors.request.use(config => { const token = localStorage.getItem('token') if (token) { config.headers['Authorization'] = 'Bearer ' + token } return config })第三步,后端写一个拦截器(实现HandlerInterceptor),拦截所有/api/**请求,校验Header里的Token是否有效。校验通过就把用户信息放到ThreadLocal里,后续业务方法里直接取;校验失败返回401状态码,前端接收到401后跳回登录页。
这里有一个容易踩的坑:Token的Secret密钥别用默认写死的简单字符串,答辩时老师可能会挑这个毛病。你可以从配置文件读取,或者动态生成一段随机字符串,这个细节不算难,但很能体现工程的严谨性。
4.2 老人档案与健康管理:分页、条件查询与图表渲染
老人档案模块是标准的CRUD,但在分页查询上值得做得更细致一点。管理端列表页通常需要组合条件查询:按老人姓名、按状态(在住/已退住)、按房间类型。用我前面提到的LambdaQueryWrapper,一个方法搞定。
健康管理模块是智慧养老系统的特色,核心是把历史健康数据渲染成折线图。后端接口的设计思路是:
// 返回最近7天的血压数据 public List<HealthTrendVO> getTrend(Long elderId, Integer days) { LocalDate startDate = LocalDate.now().minusDays(days); return healthRecordMapper.selectList( new LambdaQueryWrapper<HealthRecord>() .eq(HealthRecord::getElderId, elderId) .ge(HealthRecord::getRecordDate, startDate) .orderByAsc(HealthRecord::getRecordDate) ).stream().map(record -> { HealthTrendVO vo = new HealthTrendVO(); vo.setDate(record.getRecordDate()); vo.setHighPressure(record.getHighPressure()); vo.setLowPressure(record.getLowPressure()); return vo; }).collect(Collectors.toList()); }前端用ECharts接收这个数组,直接绑定到series.data。ECharts的引入方式很简单,在main.js里全局注册:
import * as echarts from 'echarts' Vue.prototype.$echarts = echarts页面里动态渲染折线图时,有个细节:ECharts实例在组件beforeDestroy时要调用dispose()释放,否则切换路由后页面会出现内存泄漏和图表加载错乱。这个细节我踩过坑,后来就写成了一条经验:凡是创建了图表实例的组件,一定记得销毁。
4.3 护理工单与任务状态流转
工单模块的核心是状态机。我把状态设计成四个值:0-待处理,1-进行中,2-已完成,3-已取消。界面上的操作对应状态的流转:新建工单默认待处理;护理人员点击“接单”,状态变成进行中;点击“完成”,状态变成已完成。
后端Service里用switch判断当前状态和目标状态是否合法:
public boolean updateStatus(Long taskId, Integer targetStatus) { NurseTask task = getById(taskId); switch (task.getStatus()) { case 0: // 待处理 -> 进行中 或 取消 if (targetStatus == 1 || targetStatus == 3) return doUpdate(taskId, targetStatus); break; case 1: // 进行中 -> 已完成 if (targetStatus == 2) return doUpdate(taskId, targetStatus); break; default: return false; } return false; }这样写的好处是,既在代码里体现了业务流程规则,又避免了非法跳转。答辩时如果老师问“你怎么保证工单状态不会乱”,这段代码就是直接回答。
工单列表页还有一个小优化:加一个Tab切换,用“待处理/进行中/已完成/全部”四个Tab快速过滤,本质上就是根据状态条件多查询一次,但操作体验会好很多,这个交互细节也适合写进论文的“系统特色”部分。
4.4 数据统计与可视化大屏
既然叫“智慧养老”,首页的数据大屏肯定是重中之重。大屏通常包含几个核心指标:今日入住老人数、今日护理任务完成率、本月费用收缴率、近7天新增健康预警数,以及一张入住率趋势图、一张护理任务类型分布饼图。
后端写一个统计接口,聚合返回:
public DashboardVO getDashboardData() { DashboardVO vo = new DashboardVO(); vo.setTodayElderCount(elderMapper.selectCount( new LambdaQueryWrapper<Elder>().eq(Elder::getStatus, 1) )); vo.setTodayTaskFinishRate(nurseTaskMapper.getFinishRateByDate(LocalDate.now())); vo.setMonthBillPayRate(costBillMapper.getPayRateByMonth(YearMonth.now())); vo.setHealthAlertTrend(healthRecordMapper.getAlertTrendLast7Days()); vo.setTaskTypeDistribution(nurseTaskMapper.getTypeDistribution()); return vo; }SQL写在XML里,统计类查询用SQL最直接,不用MP硬凑。比如“近7天每天的新增预警数”,SQL就是select date(alert_time) as day, count(*) from alert_log where alert_time >= date_sub(now(), interval 7 day) group by date(alert_time)。
前端大屏的布局可以参考“仪表盘风格”:顶部标题栏,中间三个KPI卡片,下方左侧入住率折线图、右侧任务类型饼图。ECharts设置backgroundColor为深色系,配上axisLabel的字号、颜色调整,视觉上就很“智慧”。这里我不建议花太多时间在炫酷特效上,功能完整、数据准确才是第一位的。
5. 常见问题与排查技巧实录
5.1 启动过程中最常见的五大报错
我把这些年带人做系统时遇到的典型问题整理成一个速查表,方便你对应排查:
| 报错或现象 | 原因 | 解决办法 |
|---|---|---|
| 启动报“Port 8080 was already in use” | 端口被占用 | `netstat -ano |
| 连接数据库报“Access denied for user” | 数据库账号密码不对 | 检查application.yml里的用户名密码,和MySQL实际账号一致 |
| 连接数据库报“Public Key Retrieval is not allowed” | MySQL 8.0认证插件问题 | JDBC URL加上allowPublicKeyRetrieval=true |
| 启动报“Failed to configure a DataSource” | 项目启动时找不到数据源配置 | 确认application.yml位置正确,Mapper扫描路径没问题 |
| npm install报“node-sass not found” | node-sass二进制下载失败 | 改package.json用sass替代,或配置镜像源重装 |
这里有一条调试心法:看日志永远先看第一行Exception。很多人一看到控制台一大片红色的错误就懵了,其实核心错误往往只在最上面的几行,下面的堆栈信息大多是无效噪音。后端调试时,先在application.yml里把日志级别调成debug(logging.level.com.example: debug),能帮你看清SQL和参数绑定情况。
5.2 前后端联调阶段的两个高频问题
联调时最大的坑是跨域。前端启动在8081,后端在8080,浏览器直接发请求会被同源策略拦住。我前面已经在vue.config.js里写了proxy代理,这是开发环境最优雅的解决方案。但如果你用了@CrossOrigin注解、或者在后端写了一个CORS配置类,两种方式同时存在时反而可能出现冲突,表现为请求带了OPTIONS预检后拿不到正常响应。我建议二选一:要么纯代理,要么纯后端CORS配置,不要混用。
第二个高频问题是时间格式。后端返回的日期时间可能是一个时间戳数组,或者2024-01-01T12:00:00这种带T的格式,前端展示出来很丑。解决办法:在后端统一配置Jackson的日期格式:
spring: jackson: date-format: yyyy-MM-dd HH:mm:ss time-zone: Asia/Shanghai前端也可以配合用dayjs做格式化,双保险。
5.3 数据展示不出来的排查思路
页面拿到了接口数据,但表格或图表是空的,这时候不要瞎改代码,按顺序排查:先看后端接口是否有数据,用Postman直接调用接口,如果返回了数据,说明问题在后端和前端之间;再开浏览器开发者工具(F12)看Network里请求是否200,响应体里有没有数据;然后看Vue组件里数据是否赋值成功,控制台打印一下this.list;最后看表格的列字段名和后台返回的字段名是否一致。很多时候不是没数据,而是字段名对不上——后台返回elderName,前端写的是name,自然就空白。这类问题我见过太多,做个简单映射或者统一下划线转驼峰就能解决。
另外,ECharts图表数据不显示还有一个常见原因:容器高度没设置。ECharts的init方法需要一个有宽度和高度的DOM容器,如果父元素的height是0,图表初始化出来就是一张白纸。给图表容器写死一个高度,比如style="height: 350px",问题立刻消失。
结语:一些做完这个项目后的真话
如果你正在为毕业设计或者课程设计选项目,这个SpringBoot+Vue的智慧养老中心管理系统确实是个不错的选择。做完一套源码级别的项目,跟看十套教程的效果完全不一样,过程中你会真正理解接口怎么设计、权限怎么控制、分页怎么查询、图表怎么渲染,这些能力在以后的工作里都是天天要用的。
我的个人建议是,不要只满足于把项目跑起来。跑起来只是第一步,你应该从上手到完整读一遍核心模块的代码,尤其是登录鉴权、统一封装的返回结果、异常全局处理、工单状态流转,这几块代码看懂了,你的收获会翻倍。再往后,如果你想让它更有竞争力,可以考虑往里面加一个简单的微信小程序端,或者模拟一个IoT设备数据上报的定时任务,这些都是很自然的扩展方向。
最后提醒一点:请一定确保你拿去演示的数据、截图和代码是真实的、自己亲手跑过的。做一个技术人,最基本的原则就是对自己写出来的东西负责。这套项目只是一个起点,祝你顺利。