十年前我刚入行时,电影院售票系统还停留在单体应用的阶段。一个War包包含所有前端JSP页面和后端Java代码,每次修改按钮颜色都要重新部署整个系统。如今这套基于SpringBoot+Vue的前后端分离架构,完美解决了传统模式的痛点。
这个影院订票系统实现了以下核心功能:
技术栈选择体现了现代Web开发的典型范式:
采用标准的RESTful API交互模式,通过Swagger生成接口文档。这里有个关键设计决策:我们放弃了传统的JWT方案,改用基于Spring Security OAuth2的认证体系。实测发现当并发购票请求超过500次/秒时,JWT的签名验证会成为性能瓶颈。
接口设计示例(影片模块):
java复制@RestController
@RequestMapping("/api/movie")
public class MovieController {
@GetMapping("/nowPlaying")
public Result<List<MovieVO>> getNowPlaying(
@RequestParam(required = false) Integer cinemaId) {
// 业务逻辑
}
@GetMapping("/detail/{id}")
public Result<MovieDetailVO> getDetail(
@PathVariable Integer id) {
// 包含影片详情+排片信息
}
}
电影院选座最怕遇到"幽灵座"问题——显示可选但实际已被占用。我们采用三级锁定策略:
关键代码片段:
java复制public boolean lockSeats(List<Integer> seatIds, Integer scheduleId) {
// Redis原子操作
String lockKey = "lock:" + scheduleId;
return redisTemplate.opsForValue()
.setIfAbsent(lockKey, seatIds, 10, TimeUnit.MINUTES);
}
支付流程采用状态机模式,定义了6个核心状态:
mermaid复制stateDiagram
[*] --> PENDING
PENDING --> PAID: 支付成功
PENDING --> CANCELLED: 用户取消
PENDING --> TIMEOUT: 15分钟未支付
PAID --> COMPLETED: 观影后
PAID --> REFUNDING: 申请退款
这里有个踩坑经验:最初使用数据库时间戳判断超时,后来发现各服务器时间不同步会导致异常。改为使用Redis的自动过期特性后问题解决。
春节档期会出现瞬时万人抢票的场景,我们通过以下方案保障系统稳定:
压力测试结果(JMeter模拟):
| 并发用户数 | 平均响应时间 | 错误率 |
|---|---|---|
| 1000 | 238ms | 0% |
| 5000 | 1.2s | 0.3% |
| 10000 | 2.8s | 1.5% |
当用户跨影院选座时,需要保证多个影院座位和订单状态的一致性。最终采用的方案是:
核心事务代码:
java复制@Transactional
public Result createOrder(OrderDTO dto) {
// 1. 扣减库存
seatService.lockSeats(dto.getSeatIds());
// 2. 创建订单
orderMapper.insert(order);
// 3. 记录事务日志
transactionLogService.addLog(order.getId());
}
推荐使用阿里云ECS配置:
后端服务Dockerfile示例:
dockerfile复制FROM openjdk:17-jdk
COPY target/cinema-service.jar /app.jar
EXPOSE 8080
ENTRYPOINT ["java","-jar","/app.jar"]
使用docker-compose编排:
yaml复制version: '3'
services:
mysql:
image: mysql:8.0
environment:
MYSQL_ROOT_PASSWORD: ${DB_PASSWORD}
redis:
image: redis:6.2
ports:
- "6379:6379"
处理Vue路由的404问题:
nginx复制location / {
try_files $uri $uri/ /index.html;
}
location /api {
proxy_pass http://backend;
proxy_set_header Host $host;
}
现象:前台显示可售但下单时报已被占用
排查步骤:
redis-cli --cluster checkSELECT * FROM seat_lock WHERE schedule_id=?现象:用户已付款但订单状态未更新
解决方案:
curl -X POST /api/order/compensate经过三个版本的迭代优化,关键指标提升:
主要优化手段:
这个项目让我深刻体会到,好的系统架构必须兼顾技术先进性和业务适配性。特别是在高并发场景下,每个技术选型都需要经过严谨的验证测试。源码中我特意保留了完整的Git提交历史,可以看到系统是如何通过持续迭代达到现在的稳定状态。