Skip to content

Commit

Permalink
more
Browse files Browse the repository at this point in the history
  • Loading branch information
day-dreams committed Mar 23, 2024
1 parent 2d44ada commit 50c8d46
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 1 deletion.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
"server": "hexo server"
},
"hexo": {
"version": "5.4.2"
"version": "5.3.0"
},
"dependencies": {
"hexo": "^5.0.0",
Expand Down
16 changes: 16 additions & 0 deletions source/_posts/后台常见策略-服务限流.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
---
title: 后台常见策略-服务限流
date: 2024-03-23 23:58:32
tags: 后台常见策略
---

后台服务领域内有很多通用的策略,他们的本质往往很简单,只是长时间不接触就会被我遗忘掉。这里总结下服务限流。

长久以来我只记得住令牌桶算法,它支持匀速发token,也允许有突发流量,就很完美。但这是算法角度,还有工程实践角度需要考虑:比如每次请求令牌,都要发起服务调用吗(也可能是redis之类的存储调用)?

在高性能场景下,特别是公司级基础服务,一定是把大量逻辑放到SDK,服务端只承担一定的限流规则记录&&同步功能。简单分为这几种模式:
* 单次分配。每次查询是否限流,都去发起服务调用。可以想象这在高性能场景下是不可能的,白白增加主调方耗时&&基础服务负载压力。
* 预分配。SDK定期从基础服务获取一定数量的令牌,然后主调方在本地就能判断是否需要限流。这就非常的高性能了,但是也有问题:不够精确。可能主调方的流量不均衡,大家需要的令牌数量不一致,如果预分配的策略不合适(均匀分配/按权重等),可能产生误判。
* 先消费,后结算。SDK直接本地决定是否限流,然后定期地/异步地去基础服务里结算:我用了多少个令牌,下次还能用多少个?好处是可以应对突发流量,快速抢占令牌;坏处是,可能产生超额消费令牌。**据某些分析**,整体流量较低时,先消费后结算的方式不容易触发超额消费,反而有自己的优势:可以应对突发流量。

世界上的事情大多不是非黑即白,总是你中有我,我中有你。比如司内就有人把第二/三种模式混合使用,流量较低时,关注突发流量,使用模式三;较高时,关注超额问题,使用模式二。但是我觉得很花哨,不知道真实效果如何。
17 changes: 17 additions & 0 deletions source/_posts/后台常见策略-负载均衡.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
---
title: 后台常见策略-负载均衡
date: 2024-03-23 23:43:59
tags: 后台常见策略
---

后台服务领域内有很多通用的策略,他们的本质往往很简单,只是长时间不接触就会被我遗忘掉。这里总结下负载均衡。

负载均衡有这么几种常见方式:

* round robin。 完全随机。
* 按权重随机。 比如一些纯计算的任务,他们完全不依赖缓存,对应服务也是无状态的;同时我们又因为开源节流的原因,使用了一些性能较差的机器,那么就适合以机器性能为权重,随机到服务节点。
* 一致性hash。 后台服务是有状态的,通常具有本地缓存,那么就适合使用一致性hash。

实战中我们都是使用一致性hash:在主调方的路由sdk内,建立hash值-虚拟节点-物理节点的映射关系。但是偶尔的,我们会遇到一些问题:
* 正常实现里,一个hash值总是对应一个物理节点。如果映射关系发生变化(机器上下线),就要承担流量迁移/重新建立缓存的开销。有时这个开销非常大,比如在推荐算法场景里,某个模型文件可能很大,重建一次要耗费很长时间(用于下载/解析)。为了减少开销,可以考虑一个hash值对应多个物理节点,然后随机路由到其中一个,这样可以使多台机器同时具有某个对象的缓存。具体怎么做呢?例如一个hash值本来对应虚拟节点X,现在路由的时候随机选区虚拟节点X-1/X/X+1,于是可以对应到3台物理节点。
* 有时候我们想做的很精细。比如节点上线时,要给它冷启动/预热的时间,那么就要分配对应的权重。本来一个物理节点对应N个虚拟节点,现在当机器上线时,我们先给他分配1个虚拟节点,然后按照一定时间间隔,慢慢地给它增加虚拟节点,直到冷启动完成(此时对应N个节点)。冷启动期间的节点变化节奏,还可以根据机器的接口耗时/成功率来变化,不过这就跟复杂了(有时候太复杂的东西实现起来容易出bug,建议不要瞎搞)。

0 comments on commit 50c8d46

Please sign in to comment.