彈性可伸縮微服務架構設計中的流控話題探討

先簡單談可伸縮彈性服務架構

先簡單談彈性可伸縮服務架構,具體的架構設計後面會有文章詳細介紹。
何爲彈性?何爲可伸縮?其實這是架構設計中除了考慮高可用,高穩定性,高性能,易擴展因素外更進一步的思考。
彈性,顧名思義,面對劇烈衝擊的時候仍能應保持正常功能和服務。劇烈衝擊一般可以理解爲突增流量。
可伸縮,一般指服務節點和整體服務器資源的可動態調度和部署。
具體方案這裏不詳細展開,這裏着重談一下在彈性架構設計中經常用到的流程手段和原理。

流控的意義

流量一般都會經過反向代理層,應用服務層,數據層,而者每一層之間都因該有流量控制組件的身影,每一層流控的目的和意義都不一樣,但總體都是爲了保證整體應用的高可用性和高穩定性,各個層的流控作用如下:

  1. 反向代理層
    過濾惡意流量,主要是對惡意攻擊流量和爬蟲進行甄別
    灰度測試的流量分發
    對後端服務層的QPS過載保護
    2.服務層
    可以通過微服務框架對服務和接口進行治理包括,服務降級,限流等
    對第三方接口進行QPS過載保護
  2. 數據層
    包括通過限流組件防止流量雪崩式的壓向數據庫,避免數據庫的服務端因某個應用的tps過高而引發資源問題

流控原理(或稱方法論)

  1. 漏桶原理 (leaky bucket)
    在這裏插入圖片描述
    簡單的說就是桶是有容量(capacity)限制的,流量(請求)進入通內後一定的速度流出,每次流出的流量大小是固定的,達到桶的容量限制後,流量會被拒絕。
    Wiki的上原文解釋如下:
    The leaky bucket is an algorithm based on an analogy of how a bucket with a leak will overflow if either the average rate at which water is poured in exceeds the rate at which the bucket leaks or if more water than the capacity of the bucket is poured in all at once, and how the water leaks from the bucket at an (almost) constant rate. It can be used to determine whether some sequence of discrete events conforms to defined limits on their average and peak rates or frequencies, or to directly limit the actions associated to these events to these rates, and may be used to limit these actions to an average rate alone, i.e. remove any variation from the average.
  2. 令牌桶原理
    在這裏插入圖片描述
    理解令牌桶算法的要點是流量過來是需要領取桶內的令牌的,拿到令牌即可通過,否則繼續等待或直接拒絕,桶內的令牌總數也是有限制的,在消耗桶內令牌的同時,還會以一定速率想桶內添加固定量的令牌。
    有興趣的可以看下Wiki的原文描述:
    The token bucket algorithm is based on an analogy of a fixed capacity bucket into which tokens, normally representing a unit of bytes or a single packet of predetermined size, are added at a fixed rate. When a packet is to be checked for conformance to the defined limits, the bucket is inspected to see if it contains sufficient tokens at that time. If so, the appropriate number of tokens, e.g. equivalent to the length of the packet in bytes, are removed (“cashed in”), and the packet is passed, e.g., for transmission. The packet does not conform if there are insufficient tokens in the bucket, and the contents of the bucket are not changed. Non-conformant packets can be treated in various ways:
    • They may be dropped.
    • They may be enqueued for subsequent transmission when sufficient tokens have accumulated in the bucket.
    • They may be transmitted, but marked as being non-conformant, possibly to be dropped subsequently if the network is overloaded.
    A conforming flow can thus contain traffic with an average rate up to the rate at which tokens are added to the bucket, and have a burstiness determined by the depth of the bucket. This burstiness may be expressed in terms of either a jitter tolerance, i.e. how much sooner a packet might conform (e.g. arrive or be transmitted) than would be expected from the limit on the average rate, or a burst tolerance or maximum burst size, i.e. how much more than the average level of traffic might conform in some finite period.

案例及demo

比較經典的開源限流實現如java 版guava ratelimiter ,另外還有redisratelimiter。 還有nginx 的limit_conn和limit_req_zone,其中limit_req_zone是用漏桶算法實現的限流機制。go語言也有l類似rateimiter實現,如juju/ratelimit ,和golang.com/x/rime/rate 兩個版本的實現,均是基於token bucket 算法的實現。個人覺得go語言的實現非常簡潔,適合大家來理解限流組件的使用,下面就go版本作簡要介紹,其他版本的可以自行查閱資料:


```go
		...
		var lim *rate.Limiter
		lim = rate.NewLimiter(2, 1)
		...
		//流量控制
		if ok :=lim.AllowN(time.Now(),1);ok{
			fmt.Println("accept ")
			handler(writer,request)
		}else {
			log.Print("refused by limiter.....")
			 defaultHandler(writer,request)
		}
		
```具體demo 見:https://github.com/smileclound/go_ratelimiter

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章