单用户N天M次频控缓存设计

一. 复杂点

  1. M和N均会变化
  2. 需支持变更实时生效
  3. 对超领零容忍
  4. 可能需要溯源, 如原来5天3次改成7天2次时, 原来5天内买了1次的用户只能再领1次

二. 隐含条件

  1. 业务上N的最大值Nmax
    如一般送体验会员, 频控最大周期为一个月, Nmax可以取2个月
  2. 业务上M都比较小(这意味着缓存数据的空间几乎可以忽略不计)

三. 方案选择

方案1

  1. kv结构
  2. key为uid+resourceId,value为领取次数
  3. expire为当前周期第1次领取资格时间向后偏移当时的N天

方案2

  1. zset结构
  2. key为uid+resourceId,member为orderNo,score为领券时间
  3. expireAt为领取资格时间向后偏移潜在的最大Nmax, 每次领取都expire
  4. 领取次数通过size来获取

方案比较

  1. 方案1的过期时间包含N, 但N变化时不好处理
  2. 每次领取资格的时间不知道, 当规则变化时没法最大程度兼容上一版本的规则, 如原来5天3次改成7天2次时, 原来领过1次的用户只能再领券1次就不好实现, 因为没有每次的领券时间戳, 不符合业务预期
  3. 方案适用的场景: N不会变化
  1. 方案2将过期时间固定取潜在最大Nmax
  2. 有领取资格时间, N变化时也可根据score精确溯源
  3. 配置变化时会最大程度兼容上一版本, 丝滑过渡

方案二的时序图:
单用户N天M次频控缓存设计_第1张图片


四. 拓展

上述的N为非自然月/周
如果需要设置成每资源日/周/月重置次数, 则计算expire时还要查找最近的重置临界点

你可能感兴趣的:(Cache,缓存,频控)