你好,我是田哥
最近,我在对充电桩项目进行微服务升级中,肯定会遇到一些问题
前面分享了:充电桩项目实战:搞定多数据源!
登录界面
在做充电桩项目时,其中用户的登录、注册等都需要用到短信这个功能,所以,我们在开发之前要做一些相对深入的考虑。
比如:
短信发送后,采取的了60秒后能再次重发,这么设计还有个好处,就是规避有些人恶意攻击系统,频繁发送短信,短信一条也就几分钱,但是量上来了,这个成本就不能小看了。
通常3分/条,如果100条那就是3块,10000条就是300块,100w条那就是3万块
但是,这个60秒也还不能完全杜绝这类事情发生,只是说这个量级变了,一个用户每隔60秒发一次,一小时就可以发60次,一条24*60=1440次,10个用户都这么恶搞,那就是每天短信成本变成:
每天10个用户恶搞,14400*3=43200,换算下来432,恶搞一个月就是
432*30
= 一万多了。
所以,我们还可以对用户进行每天次数限制,每月次数限制。比如:每天每个用户的某个功能发短信的次数限制在8次,或者20次。至少也能规避掉前面带来的问题。
其实,上述问题也可以说不能完全规避掉,只能说在不影响用户使用的前提下,我们可以尽可能规避。所以,我们可以采取一个分布式限流技术,就是每一个用户每天或者每分钟或每小时,最多只能发送xx次-----限流。
分布式限流方案有以下几种:
● 优点:实现简单,算法成熟,可以平滑限流请求,具有较高的容错性和稳定性。
● 缺点:限流粒度较粗,无法应对瞬时流量突增的情况。
● 适用场景:对于不需要严格限制每个请求的时间间隔的情况,可以使用基于令牌桶算法的限流方案。
● 优点:实现简单,可以平滑限流请求,具有较高的容错性和稳定性。
● 缺点:限流粒度较粗,无法应对瞬时流量突增的情况。
● 适用场景:对于不需要严格限制每个请求的时间间隔的情况,可以使用基于漏桶算法的限流方案。
● 优点:实现简单,可以较为准确地控制请求的速率。
● 缺点:无法平滑限流请求,容易因瞬时流量突增而导致系统压力过大。
● 适用场景:对于需要严格控制每个请求的时间间隔的情况,可以使用基于计数器的限流方案。
● 优点:可以分布式地存储和管理限流规则,适用于大规模分布式系统。
● 缺点:需要依赖分布式缓存系统,增加了系统的复杂性。
● 适用场景:对于需要分布式地管理限流规则的大规模系统,可以使用基于分布式缓存的限流方案。
● 优点:可以集中管理和控制流量,支持多种限流策略,适用于大规模分布式系统。
● 缺点:需要引入额外的流量控制网关,增加了系统的复杂性。
● 适用场景:对于需要集中管理和控制流量的大规模系统,可以使用基于流量控制网关的限流方案。
不同的限流方案适用于不同的场景,我们需要根据具体的业务需求和系统架构来选择合适的方案。假设我们采用每小时用户最多只能发送6次短信,那我们可以采取滑动窗口来解决。
关于滑动窗口模型图:
滑动窗口
在我们的充电桩项目中,采用的是Redisson来实现限流的。
public boolean limitBySlidingWindow(String key,long rate, long rateInterval, RateIntervalUnit rateIntervalUnit) {
RRateLimiter rateLimiter = redissonClient.getRateLimiter(key);
rateLimiter.trySetRate(RateType.OVERALL, rate, rateInterval, rateIntervalUnit);
if (rateLimiter.tryAcquire()) {
return false;
} else {
// 触发限流处理
return true;
}
}
固定速率(Fixed)和滑动窗口速率(Sliding Window)是两种常见的限流算法,它们在实现上有一些区别。
总结:固定速率算法通过设置固定的请求处理时间间隔来限制请求的处理速度,而滑动窗口算法通过维护一个时间窗口来控制请求的处理速度。两者都可以实现对请求的处理速度进行限制,但具体实现方式和效果略有不同。
估计很多人看了这段话还是不太清楚我们到底要选择哪一种?
固定速率的优点:
● 实现简单:固定速率算法的实现相对简单,只需要设置一个时间间隔,确保每个请求之间有足够的处理时间。
● 预测性强:由于时间间隔是固定的,所以可以很容易地预测系统的处理能力,便于进行资源规划和分配。固定速率的缺点:
● 不够灵活:在高并发情况下,固定速率可能会导致资源浪费,因为它不考虑实际的请求情况,即使请求量减少,也会保持相同的处理速度。
● 无法应对突发流量:当遇到突发流量时,固定速率可能无法及时响应,因为它不能根据实际情况动态调整处理速度。
滑动窗口速率的优点:
● 灵活性高:滑动窗口算法可以根据实际的请求情况动态调整处理速度,更加灵活地应对不同的流量模式。
● 资源利用率高:通过动态调整时间窗口的大小,滑动窗口算法可以更有效地利用系统资源,避免在请求量少时的资源浪费。
滑动窗口速率的缺点:
● 实现复杂:相比于固定速率,滑动窗口算法的实现更为复杂,需要考虑窗口的大小和滑动的策略。
● 性能开销大:由于需要维护一个时间窗口的数据结构,滑动窗口算法可能会引入额外的性能开销。
总的来说,固定速率算法适合对处理速度要求较为稳定的场景,而滑动窗口速率算法则更适合对处理速度有较高灵活性要求的场景。
在充电桩项目中短信模块设计,整体流程如下
短信模块设计
用到了策略模式和模板方法模式。关于策略模式和模板方法模式之前我已经分享过,所以,参考之前的文章即可。