1. 项目概述:儿童疫苗管理系统核心价值
在基层医疗机构工作十年,最让我头疼的就是手工登记疫苗信息。去年接种高峰期,因登记错误导致3名儿童重复接种的医疗事故,让我下定决心开发这套系统。这个基于SpringBoot的疫苗管理系统,核心解决三个痛点:
- 接种记录易出错:纸质登记本字迹潦草、涂改频繁
- 库存管理混乱:经常出现疫苗过期才发现的情况
- 统计效率低下:每月手工汇总报表需要2个工作日
系统采用B/S架构,前端用Thymeleaf+ECharts实现数据可视化,后端基于SpringBoot 2.7整合MyBatis-Plus。特别设计了双重校验机制:在护士提交接种记录后,必须由另一名医生审核才能生效。实测使用半年,登记错误率下降92%,库存损耗降低67%。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 技术架构设计解析
2.1 为什么选择SpringBoot+SSM组合
在技术选型时对比过SpringCloud和纯MyBatis方案,最终选择这个组合主要考虑:
- 开发效率:SpringBoot的starter依赖让整合SSM(Spring+SpringMVC+MyBatis)只需3个pom配置
- 性能需求:经压测验证,单机部署可支撑500并发(TPS 280+),满足社区医院日均300接种量
- 维护成本:SSM架构在医疗行业有成熟案例,后期招聘开发人员更容易
xml复制<!-- 典型依赖配置 -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.5.2</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
2.2 数据库设计关键点
疫苗管理最核心的是三张表的设计:
-
疫苗库存表(vaccine_stock)
- 包含批次号、有效期、冷链温度等字段
- 建立联合索引(vaccine_id, expiry_date)
-
儿童档案表(child_info)
- 采用身份证号作为唯一标识
- 包含过敏史等医疗敏感信息(需加密存储)
-
接种记录表(vaccination_record)
- 使用状态机设计(0-待审核 1-已接种 2-已取消)
- 记录操作人、审核人双字段
sql复制CREATE TABLE `vaccine_stock` (
`batch_no` varchar(32) NOT NULL COMMENT '疫苗批次号',
`expiry_date` date NOT NULL COMMENT '有效期',
`storage_temp` decimal(3,1) DEFAULT NULL COMMENT '存储温度',
`current_stock` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`batch_no`),
KEY `idx_vaccine_expiry` (`vaccine_id`,`expiry_date`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
3. 核心功能实现细节
3.1 接种预约模块
采用分段锁设计解决高并发预约问题:
- 按疫苗ID哈希分片
- 使用Redis分布式锁(Redisson实现)
- 库存扣减采用CAS机制
java复制public boolean makeAppointment(Long vaccineId, Long childId) {
String lockKey = "vaccine:lock:" + vaccineId % 10;
RLock lock = redissonClient.getLock(lockKey);
try {
lock.lock(5, TimeUnit.SECONDS);
// 检查库存
VaccineStock stock = stockMapper.selectById(vaccineId);
if (stock.getCurrentStock() > 0) {
// 使用MyBatis-Plus的乐观锁更新
stockMapper.updateStock(vaccineId);
// 创建接种记录(状态为待审核)
recordMapper.insert(new VaccinationRecord(childId, vaccineId));
return true;
}
} finally {
lock.unlock();
}
return false;
}
3.2 冷链监控告警
通过MQTT协议接入温度传感器数据:
- 使用EMQX作为MQTT broker
- 温度超标时触发三级告警:
- 超过阈值1℃:系统弹窗提醒
- 超过阈值2℃:短信通知管理员
- 超过阈值3℃:自动标记该批次疫苗不可用
yaml复制# application.yml 配置节选
emqx:
broker-url: tcp://localhost:1883
topic: vaccine/temperature
client-id: vaccine-server
qos: 1
4. 安全与合规设计
4.1 医疗数据加密方案
根据《医疗卫生机构网络安全管理办法》要求:
- 敏感字段使用AES-256加密
- 密钥通过HSM硬件模块管理
- 日志脱敏处理
- 身份证号显示为:110**********1234
- 审计日志保留6个月
java复制// 使用Jasypt实现字段加密
@Column
@Encrypted(
algorithm = "AES",
keyObtentionIterations = 1000,
password = "${jasypt.encryptor.password}")
private String idCardNumber;
4.2 双人审核机制
关键操作采用"经办-审核"双人模式:
- 接种记录提交后状态为"待审核"
- 需具有审核权限的医生二次确认
- 操作留痕包含双方工号
sql复制UPDATE vaccination_record
SET status = 1,
auditor = '10086',
audit_time = NOW()
WHERE id = 123
AND status = 0; -- 确保只有待审核记录能被操作
5. 部署与性能优化
5.1 容器化部署方案
使用Docker Compose编排服务:
- 主服务:SpringBoot应用
- 依赖服务:MySQL+Redis+EMQX
- 通过Nginx实现负载均衡
dockerfile复制# Dockerfile示例
FROM openjdk:11-jre
COPY target/vaccine-system.jar /app.jar
ENTRYPOINT ["java","-jar","/app.jar"]
EXPOSE 8080
5.2 性能调优实战
通过Arthas诊断发现的三个关键优化点:
- MyBatis二级缓存启用(针对疫苗目录等静态数据)
- ThreadPoolTaskExecutor配置核心线程数=CPU核数*2
- 接种记录分表(按月份拆分)
java复制// 线程池配置示例
@Bean
public TaskExecutor taskExecutor() {
ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
executor.setCorePoolSize(Runtime.getRuntime().availableProcessors() * 2);
executor.setMaxPoolSize(50);
executor.setQueueCapacity(1000);
return executor;
}
6. 踩坑经验实录
6.1 疫苗批次号冲突问题
现象:不同厂商的疫苗批次号重复
解决方案:
- 在批次号前增加厂商代码前缀
- 数据库增加唯一索引(厂商代码+批次号)
6.2 日期查询性能优化
错误做法:
sql复制SELECT * FROM record WHERE DATE(create_time) = '2023-01-01'
正确做法:
sql复制SELECT * FROM record
WHERE create_time >= '2023-01-01 00:00:00'
AND create_time < '2023-01-02 00:00:00'
性能对比:查询耗时从1200ms降至80ms
7. 扩展功能建议
-
对接省级免疫规划平台
- 使用WebService实现数据同步
- 定时任务每日凌晨同步数据
-
移动端接种提醒
- 集成微信模板消息
- 提前3天推送接种提醒
-
疫苗溯源功能
- 区块链存证关键操作
- 提供扫码查询接口
这套系统在社区卫生中心运行一年后,接种工作效率提升40%,家长满意度达98%。特别提醒:医疗系统开发必须预留足够时间进行合规性测试,我们当时用了3周专门做等保测评整改。
