在互联网社交、短视频、直播等场景中,“点赞”是一项极其常见却又极具挑战性的功能。用户只需轻点一下,系统后台却要扛住千万级的并发请求,同时保证数据不丢失、延迟低、体验流畅。近日,某互联网技术团队公开分享了他们从零搭建高并发点赞系统的实战经验,核心思路是“缓存先扛、MQ削峰、异步落库”,引发业内广泛关注。
高并发场景下的“点赞之痛”
点赞看似简单,实则暗藏“三高”难题:高并发(热点内容瞬间涌入数万点赞请求)、高一致性(用户期望实时看到点赞数变化,且不能重复计数)、高可靠性(一旦数据库写入失败,点赞数据将永久丢失)。传统做法是直接操作数据库,但面对几十万甚至上百万的并发写入,数据库很快成为瓶颈,不仅响应变慢,还可能导致连接池耗尽、死锁,甚至系统雪崩。
某知名短视频平台技术负责人坦言:“早期的点赞系统设计不当,曾多次在热门视频上线后出现点赞数‘卡死’或‘回滚’现象,用户体验极差。后来我们全面迁移到缓存+MQ方案,才彻底解决了问题。”
缓存先行:Redis扛住瞬发流量
设计高并发点赞系统的第一步,是将点赞计数从数据库迁移到内存缓存中。Redis因其高性能、支持原子操作(如INCR、DECR)以及丰富的数据结构,成为首选。
具体实战中,团队采用两级缓存策略:本地缓存(Caffeine)+分布式缓存(Redis)。本地缓存主要用于热点数据的极速响应,减少网络IO;Redis作为最终计数的权威存储。当用户点赞时,系统首先在Redis中执行INCR操作,并记录用户的点赞状态(使用Set或Hash结构),确保同一用户对同一内容只能点赞一次。
“缓存设计的关键是‘热数据留在内存,冷数据落盘’。”该技术团队架构师解释,“我们通过TTL和LRU淘汰策略,让缓存始终服务最新、最热的点赞请求。实测下,单台Redis实例能扛住每秒10万次的点赞操作。”
MQ异步持久化:将写压力“削峰填谷”
缓存虽然能抗住高并发,但数据不能永远留在内存——断电或重启会导致丢失。因此需要将点赞数据最终同步到数据库(如MySQL)进行持久化。然而如果每次点赞都直接写数据库,缓存的意义就荡然无存。
解决方案是引入消息队列(MQ)。点赞请求经Redis处理后,生成一条包含用户ID、内容ID、操作类型(点赞/取消点赞)的消息,发送到Kafka或RocketMQ等消息队列。后端单独的消费者服务以固定的速率(如每秒1000条)从MQ拉取消息,批量写入数据库。
“MQ在这里起到了‘削峰填谷’的关键作用。”专家指出,“即使瞬时并发暴增到每秒50万,MQ也能平稳吸收,下游数据库按自身能力消费,不会被打垮。”同时,MQ自带的消息确认和重试机制,保证了即使消费者异常,数据也不会丢失,实现了“最终一致性”。
实战效果与经验总结
该团队在压测环境中模拟了100万用户同时点赞一个视频的场景。结果如下: - 缓存层(Redis):平均响应时间<5ms,QPS超过10万。 - MQ层:消息堆积最高达50万条,但消费者平稳处理,无消息丢失。 - 数据库层:批量写入后,每秒处理约3000条,CPU和IO均稳定。 - 用户侧:点赞按钮即时反馈,无卡顿,取消点赞同样实时生效。
技术负责人强调,该方案有几点注意事项: 1. 幂等性:确保同一条消息被重复消费时不会导致重复计数。可通过数据库的唯一索引或业务ID去重。 2. 缓存与数据库的双写一致性:采用“先更新缓存,再发送MQ”的方式,并配合定期对账任务(如每小时扫描缓存与数据库的差异)来修正少量不一致。 3. 降级容灾:当Redis或MQ出现故障时,系统应能降级为直接写数据库(牺牲部分性能),或对用户展示“点赞服务繁忙”提示。
展望:走向更极致的点赞体验
随着业务发展,点赞系统还面临更多挑战:多维度计数(如按小时、性别统计)、防刷(同一IP或设备恶意点击)、实时热度榜单等。该团队表示,未来计划引入分布式读写分离和旁路计算,将点赞数据实时同步到分析引擎,支撑更复杂的推荐和运营需求。
从“硬扛数据库”到“缓存+MQ异步化”,高并发点赞系统的设计理念已成为互联网后端架构的典范。这一实战方案为无数中小型团队提供了可复用的思路——用最成熟的组件,解决最棘手的问题,让每一次点赞都“又快又稳”。