一、背景介绍:真实需求中的问题与挑战

设想你正在负责一家大型电商平台的基础架构服务,该平台拥有超过1000万注册用户,活跃用户规模庞大,日均请求量达到数亿级别。最近,产品团队提出了一个新的用户运营需求

“当用户从未登录过的城市打开我们的App,平台应在第一时间发送一条欢迎短信,提醒用户注意账号安全,并展示该地区的专属优惠。”

听上去很简单,但细节与挑战远不止如此。


二、需求场景详解

这条“欢迎短信”必须满足以下逻辑判断:

  1. 用户15天内是否第一次从该城市登录(防止重复发送);
  2. 同一用户一天可能在多个城市登录,如旅行途中需跨多个城市;
  3. 数据来源是基站信令信息(包含手机号、经纬度/城市编码、登录时间);
  4. 信令数据接入量巨大,每秒约7万条,高并发压力下如何精准判断、及时响应成为关键。

此外,技术实现还必须满足:

  • 高性能、低延迟,避免短信发送过慢;
  • 尽量不增加新组件,充分利用现有 RocketMQ、Redis 资源;
  • 系统具备容错能力,避免因组件异常导致大规模重复发送或发送失败。

三、整体架构概览

我们设计了一个高并发、低误判、支持异地登录识别的短信发送系统,通过如下核心组件实现:

  • RocketMQ:承接基站信令信息流;
  • Redis + 布隆过滤器(Bloom Filter):完成城市访问记录的高效判重;
  • 短信服务集群:分布式部署支持高并发处理与异步投递;
  • PG(PostgreSQL)数据库:保存发送记录、用于布隆过滤器重建;
  • 定时调度任务系统:定期清理/更新过滤器内容与发送状态。

四、数据流程详解

步骤1:信令数据入队

  • 每秒7万条基站信令数据进入 RocketMQ;
  • 信令内容:手机号、时间、经纬度(城市编码);
  • 消息分布到多个 Broker 分区中,便于消费者集群并行拉取。

步骤2:短信服务集群拉取数据

  • 使用消费者集群(多实例部署);
  • 拉取模式控制速率(如每30秒拉取一批);
  • 拉取后解析出“手机号+城市”。

步骤3:城市布隆过滤器判重

  • Redis 中每个城市有一个独立的布隆过滤器;
  • 判定逻辑:
    • 若手机号在城市布隆过滤器中存在:已发送过短信,丢弃;
    • 若不存在:符合发送条件,进入发送流程。

步骤4:发送短信并记录状态

  • 使用异步任务将短信投递到运营商网关;
  • 同时在数据库插入发送记录(手机号、城市、时间、状态);
  • 投递成功后,将手机号写入布隆过滤器,后续访问即判定为已发送。

五、布隆过滤器设计要点

为什么选择布隆过滤器?

  • 能在海量数据判重场景中提供极高性能;
  • 占用内存极小,适合 Redis 内存存储;
  • 理论误判率可控制在万分之一以下
  • 不能误判未访问用户为“已访问”,符合短信业务需求(误发一条无伤大雅,漏发风险大)。

设计细节:

  • 总共设定 40个城市 × 每个城市一个布隆过滤器
  • 每个过滤器设定约 100万位(BitMap),可支持百万级用户标记;
  • 每日凌晨定时清理并重建布隆过滤器,只保留15天内记录;
  • 使用 Redis 主从结构:
    • 主节点负责写入
    • 多个从节点随机读取,做读写分离,缓解并发压力。

六、Redis 架构及访问路由策略

Redis 集群结构:

  • 主从模式部署,如主节点:128,两个从节点:129、130;
  • 主节点标记为 WR(可写可读),从节点标记为 R(只读);
  • 短信服务通过配置文件维护 Redis 节点列表;
  • 随机路由访问某一个节点,均摊访问压力;
  • 支持未来快速横向扩展,从节点越多越抗压。

七、短信发送与状态管理

异步发送策略:

  • 避免因网关响应慢导致线程阻塞;
  • 支持批量发送(每30秒汇总手机号列表批量推送),减少请求频率,提升效率;
  • 初始状态写入数据库(“待发送”),短信服务监听发送状态并更新。

网关反馈方式:

  1. 运营商回调接口(推荐);
  2. 自建任务调度器定时查询短信状态

八、每日布隆过滤器更新策略

  • 每天凌晨触发调度任务;
  • 查询过去15天内的短信记录;
  • 按城市重建布隆过滤器内容;
  • 自动覆盖 Redis 原始数据;
  • 避免布隆过滤器持续膨胀、误判率增加。

九、性能优化策略总结

场景 方案
高并发信令数据 RocketMQ 消息队列+拉取模式+消费者集群
高频判重 Redis + 布隆过滤器
Redis 扩展性 主从部署+读写分离+路由均衡
网关延迟 异步发送+批量投递
历史数据清理 每日定时重建布隆过滤器
误发控制 30分钟内重复校验 + 万分之一误判容忍度

十、系统容错与兜底机制

Redis 主从延迟的处理:

  • 主从延迟通常在百毫秒级;
  • 可增加“近30分钟是否已发送过短信”判断,避免主从未同步时漏判;

网关故障兜底:

  • 若短信连续多次投递失败,则终止;
  • 可通知用户其他方式如App Push、邮件、人工客服介入等。

十一、总结与展望

该短信系统设计遵循了“性能优先、可控成本、低误判、高可用”的原则,实现了在千万级用户+7万QPS信令输入下,仅依赖 Redis 与 MQ 就完成了:

  • 高效判重
  • 准确触发
  • 稳定投递
  • 异步解耦
  • 可平滑扩容

它是典型的“不加新组件,提升系统战斗力”的架构设计范例。


十二、补充建议

  • 布隆过滤器持久化(防止宕机后丢失);
  • 城市粒度可配置化(支持城市集群逻辑);
  • 灰度策略:按用户标签控制短信发送比例;
  • 接入全链路追踪监控系统(追踪手机号、城市、过滤、发送全过程);

十三、结语

短信发送并不是难点,难的是在高并发场景下高效“决定是否发送”。这个系统展示了如何将传统的数据结构(布隆过滤器)与现代的分布式基础设施(MQ、Redis)结合,解决了一个实用性极强的互联网问题。

如果你在运营、风控、物联网等场景中也面临类似挑战,相信本方案能为你提供切实可落地的思路。

Logo

电商企业物流数字化转型必备!快递鸟 API 接口,72 小时快速完成物流系统集成。全流程实战1V1指导,营造开放的API技术生态圈。

更多推荐