前言
限流器是后台服务中十分重要的组件,在实际的业务场景中使用居多,其设计在网关和一些后台服务中会经常遇到。限流器的作用是用来限制其请求的速率,保护后台响应服务,以免服务过载导致服务不可用现象出现。
**
在 Golang 库中官方给我们提供了限流器的实现 golang.org/x/time/rate,它是基于令牌桶算法(Token Bucket)设计实现的。
代码实现
编写中间件
// Create a rate limiter with a maximum number of operations to perform per second.func RateLimitMiddleware() gin.HandlerFunc {rateCfg := config.GetConfig().Rater := rate.Every(time.Duration(rateCfg.Limit) * time.Second)limit := rate.NewLimiter(r, rateCfg.Burst)return func(c *gin.Context) {if !limit.Allow() {fmt.Println("The current flow is too big, please try again later")c.JSON(http.StatusOK, gin.H{"status": status.RequestRateLimit,"message": status.GetStatusMessage(status.RequestRateLimit),})c.Abort()return}}}
测试接口
// Test controllermiddleRateLimit := md.RateLimitMiddleware()testHandler := testHandler.New()test := router.Group("/V1/internal/test", middleRateLimit){test.GET("/rate-limit", testHandler.RateLimitTest) // Testing rate limit for request}
接口返回
// Test an interface that rate limit for requestfunc (h *handler) RateLimitTest(c *gin.Context) {c.JSON(http.StatusOK, gin.H{"status": 200,"message": "Success",})}
测试用例
Postman

Jmeter
拓展
- uber 开源库中基于漏斗算法实现了一个限流器。漏斗算法可以限制流量的请求速度,并起到削峰的作用。
[https://github.com/uber-go/ratelimit](https://github.com/uber-go/ratelimit) - 滴滴开源实现了一个对http请求的限流器中间件。可以基于以下模式限流。
- 基于IP,路径,方法,header,授权用户等限流
- 通过自定义方法限流
- 还支持基于 http header 设置限流数据
- 实现方式是基于
github/go/time实现的,不同类别的数据都存储在一个带超时时间的数据池中。 - 代码地址
[https://github.com/didip/tollbooth](https://github.com/didip/tollbooth)
- golang 网络包中还有基于信号量实现的限流器。
[https://github.com/golang/net/blob/master/netutil/listen.go](https://github.com/golang/net/blob/master/netutil/listen.go)也值得我们去学习下。

