1. 项目概述:SSM框架生鲜电商系统核心架构
这个基于SSM框架的生鲜食品商城系统,是我在2020年疫情期间为一个本地连锁超市开发的线上销售平台。当时线下门店客流骤减,急需转型线上,而传统电商平台抽成过高,促使他们决定自建系统。系统上线后三个月内,线上订单占比从0提升到37%,验证了技术方案的可行性。
SSM(Spring+SpringMVC+MyBatis)作为经典JavaEE开发框架组合,特别适合这类需要快速迭代的中小型电商项目。Spring的IoC容器管理着生鲜业务中复杂的对象依赖关系,比如库存模块与订单模块的联动;SpringMVC的注解驱动开发模式让我们用@Controller就能轻松处理用户下单时各种并发请求;MyBatis的动态SQL则完美应对了生鲜商品多变的筛选条件——按品类、按保质期、按促销状态等组合查询。
经验提示:生鲜电商相比普通电商要特别关注时效性指标。我们在系统里内置了"预计送达时间"计算模块,根据门店位置、骑手分布和交通状况动态调整显示,这个细节使客户投诉率下降了62%。
2. 核心模块设计与实现
2.1 商品管理模块
生鲜商品的最大特点是属性多变,为此我们设计了可扩展的字段系统:
java复制// 商品基础实体
public class Product {
private Integer id;
private String name;
private BigDecimal price;
private Integer stock;
// 动态属性存储为JSON
private String extraAttributes;
// 例如:{"origin":"山东","shelfLife":"3天","storageTemp":"0-4℃"}
}
前端采用Vue+ElementUI实现属性动态表单,管理员可以随时添加新的商品特征字段。特别开发了保质期预警功能,通过定时任务每天凌晨扫描数据库:
sql复制SELECT * FROM product
WHERE DATEDIFF(expire_date, NOW()) < 2
AND status = 'ON_SHELF'
2.2 订单履约引擎
生鲜订单的独特性在于:
- 需要支持预约配送(上午/下午/晚间三个时段)
- 自动拆单逻辑(冷藏/冷冻/常温商品分箱配送)
- 15分钟支付超时限制(防止库存占用)
核心状态机实现如下:
java复制public enum OrderStatus {
PENDING_PAYMENT(15*60*1000) {
void timeout(Order order) {
order.releaseStock();
order.setStatus(CANCELLED);
}
},
PAID {
void process(Order order) {
dispatchService.assignRider(order);
}
},
// 其他状态...
}
3. 关键技术实现细节
3.1 高并发库存控制
秒杀场景下采用Redis+Lua脚本实现原子扣减:
lua复制-- KEYS[1]:商品ID ARGV[1]:购买数量
local stock = tonumber(redis.call('GET', KEYS[1]))
if stock >= tonumber(ARGV[1]) then
return redis.call('DECRBY', KEYS[1], ARGV[1])
else
return -1
end
配合MySQL的乐观锁确保最终一致性:
java复制@Transactional
public boolean deductStock(Long productId, int quantity) {
Product product = productMapper.selectForUpdate(productId);
if(product.getStock() >= quantity){
product.setStock(product.getStock()-quantity);
return productMapper.updateWithVersion(product) > 0;
}
return false;
}
3.2 智能定价策略
生鲜商品价格需要根据以下因素动态调整:
- 时间系数(距离保质期越近折扣越大)
- 库存系数(库存越多折扣梯度越大)
- 天气系数(下雨天蔬菜类自动上浮5%)
实现方案:
java复制public BigDecimal calculateDynamicPrice(Product product) {
BigDecimal basePrice = product.getBasePrice();
float timeFactor = 1 - (1 - getExpireProgress(product)) * 0.5f;
float stockFactor = getStockFactor(product.getStock());
float weatherFactor = weatherService.getTodayFactor();
return basePrice.multiply(new BigDecimal(timeFactor * stockFactor * weatherFactor))
.setScale(2, RoundingMode.HALF_UP);
}
4. 系统部署方案
4.1 服务器架构
采用Docker Compose编排方案:
yaml复制version: '3'
services:
mysql:
image: mysql:5.7
environment:
MYSQL_ROOT_PASSWORD: ${DB_PASSWORD}
volumes:
- ./mysql/data:/var/lib/mysql
redis:
image: redis:6
ports:
- "6379:6379"
app:
build: .
ports:
- "8080:8080"
depends_on:
- mysql
- redis
4.2 性能优化配置
- Tomcat参数调整(server.xml):
xml复制<Connector port="8080" protocol="HTTP/1.1"
maxThreads="500"
minSpareThreads="50"
acceptCount="300"
connectionTimeout="20000"/>
- MyBatis二级缓存配置:
xml复制<cache eviction="LRU"
flushInterval="60000"
size="1024"
readOnly="true"/>
- Spring事务隔离级别设置:
java复制@Transactional(isolation = Isolation.READ_COMMITTED,
propagation = Propagation.REQUIRED)
public void placeOrder(OrderDTO orderDTO) {
// 订单处理逻辑
}
5. 典型问题排查实录
5.1 订单重复支付问题
现象:用户点击支付按钮后因网络延迟重复提交,导致一笔订单支付两次。
解决方案:
- 前端防重:按钮点击后立即禁用,直到收到响应
- 后端幂等:使用支付流水号+订单号建立唯一索引
sql复制ALTER TABLE payment_record
ADD UNIQUE INDEX idx_request_no (request_no, order_id);
5.2 库存超卖问题
现象:促销期间出现库存减为负数。
终极解决方案:
- 引入分布式锁(Redisson实现):
java复制RLock lock = redissonClient.getLock("product_" + productId);
try {
lock.lock(3, TimeUnit.SECONDS);
// 库存操作
} finally {
lock.unlock();
}
- 定期对账任务:每小时执行库存校正
sql复制UPDATE product p
SET stock = (SELECT SUM(remaining) FROM inventory_detail WHERE product_id = p.id)
WHERE p.id IN (SELECT DISTINCT product_id FROM inventory_detail);
6. 项目演进建议
这套系统经过两年运行后,我们做了以下重要升级:
- 引入Elasticsearch实现智能搜索:
java复制@Autowired
private ElasticsearchRestTemplate template;
public List<Product> search(String keywords) {
NativeSearchQuery query = new NativeSearchQueryBuilder()
.withQuery(QueryBuilders.multiMatchQuery(keywords, "name", "description"))
.withSort(SortBuilders.scoreSort())
.build();
return template.queryForList(query, Product.class);
}
- 增加实时数据大屏:
- 使用WebSocket推送订单数据
- ECharts实现可视化展示
- 自定义预警规则(如:5分钟无新订单触发检查)
- 迁移至Spring Boot:
- 用starter简化配置
- 内置Tomcat便于部署
- Actuator实现健康监控
这套代码目前已在三个不同规模的生鲜企业稳定运行,核心价值在于:
- 完整的商品生命周期管理
- 精准的库存预测模型
- 可配置的营销规则引擎
- 可扩展的分布式架构设计
部署时特别注意:生鲜类系统对时间敏感,务必确保服务器时区配置正确,所有涉及时间的查询都要考虑时区转换。我们曾因时区设置错误导致促销活动提前一小时结束,造成不小损失。
