漏斗限流(leaky bucket)

2024-06-17 03:20
文章标签 bucket 限流 漏斗 leaky

本文主要是介绍漏斗限流(leaky bucket),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

漏斗限流(leaky bucket)

  • 介绍
  • 工作原理
  • leaky bucket实现示例:
  • 搭配pool池
    • pool.lua示例
    • 搭配示例
  • 对象池(pool)结合漏斗限流(leaky bucket)的好处:

介绍

漏斗限流(leaky bucket)是一种流量控制算法,用于限制在网络或系统中通过的数据量或请求速率。通常用于平滑网络流量或请求到达的速率,防止突发流量导致系统负载过高或网络拥塞。

工作原理

1. 漏斗模型:

  • 漏斗可以看作是一个容器,有一个固定的最大容量(即最大请求速率),漏嘴则控制了流出速率
  • 如果漏斗里的水量超过了当前漏口的处理能力,多余的水会溢出(即请求被限流或丢弃)

2. 处理流程:

  • 漏斗以固定速率处理请求,类似于水从漏斗底部流出的速度
  • 请求到达时,先判断漏斗当前的水量是否能容纳新的请求。如果可以,则接受请求并将水量增加;否则,拒绝请求或以某种方式处理溢出的请求

应用场景:

  • 网络流量控制:限制流过路由器或服务器的数据包速率,防止网络拥塞
  • API请求管理:限制API接口的访问频率,避免服务器过载
  • 消息队列消费速率控制:平滑处理从消息队列中获取的消息,防止消费者因处理速度不足导致消息堆积

leaky bucket实现示例:

-- 漏斗限流逻辑
local os_time = os.time
local mt = {}
mt.__index = mt-- 是否处于正常可通过状态
function mt:watering()local t_now = os_time()local leak_water = self.rate * (t_now - self.last_ts)if leak_water > 0 thenlocal left_water = self.water - leak_waterself.water = (left_water > 0) and left_water or 0self.last_ts = t_nowendif self.water < self.cap thenself.water = self.water + 1return trueendreturn false
end-- 重置
function mt:reset()self.water = 0
endlocal M = {}
function M.create_bucket(rate, cap)local bucket = {}bucket.rate = rate -- 漏斗每秒速率bucket.cap = cap -- 漏斗容量bucket.water = 0 -- 漏斗当前的水位bucket.last_ts = 0 -- 最近一次处理的时间return setmetatable(bucket, mt)
endreturn M

搭配pool池

pool.lua示例

用于管理可复用对象的创建、获取和释放
-- object pool, from: https://github.com/treamology/pool.lualocal type, pairs, table, setmetatable = type, pairs, table, setmetatable 
local pool = {}
local poolmt = {__index = pool}function pool.create(newObject, poolSize, maxPoolSize)if type(newObject) ~= "function" thenreturn nilendpoolSize = poolSize or 16maxPoolSize = (maxPoolSize and maxPoolSize >= poolSize) and maxPoolSize or 2 * poolSizelocal freeObjects = {}for _ = 1, poolSize dotable.insert(freeObjects, newObject())endreturn setmetatable({freeObjects = freeObjects,newObject = newObject,maxPoolSize = maxPoolSize},poolmt)
endfunction pool:obtain()return #self.freeObjects == 0 and self.newObject() or table.remove(self.freeObjects)
endfunction pool:free(obj, ...)if not obj thenreturn falseendif #self.freeObjects < self.maxPoolSize thentable.insert(self.freeObjects, obj)endif obj.reset then obj.reset(obj, ...) endreturn true
endfunction pool:clear()for k in pairs(self.freeObjects) doself.freeObjects[k] = nilend
endreturn pool

搭配示例

local leaky_bucket = require "leaky_bucket"
local pool = require "pool"
local bucketPool = nil -- 漏斗限流池local buckets = {} -- 漏限流对象池
local function new_bucket_object()return leaky_bucket.create_bucket(50, 80)
end
bucketPool = pool.create(new_bucket_object, 100, 200)local BUCKETS = setmetatable(buckets, {__index = function (t, id)t[id] = bucketPool:obtain()return t[id]end
})

对象池(pool)结合漏斗限流(leaky bucket)的好处:

1. 资源重复利用:

  • 对象池(pool)可以有效管理和重复利用漏斗限流对象。通过调用 pool.create(new_bucket_object, m, n) 创建的 bucketPool 对象池,可以预先创建并维护多个漏斗限流对象
  • 当需要使用漏斗限流对象时,通过 bucketPool:obtain() 方法从对象池中获取一个可用对象,而不是每次都重新创建

2. 减少资源消耗:

  • 漏斗限流对象通常包含一些初始化和配置,创建和销毁开销较大。通过对象池,可以避免频繁地创建和销毁漏斗限流对象,从而减少系统资源的消耗,提高性能和效率

3. 提高系统响应速度:

  • 由于对象池中已经预先创建了一定数量的漏斗限流对象,获取对象时只需从池中取出,并可能调用重置方法进行初始化,而不需要完全重新创建。这样可以大大缩短获取对象的响应时间,提高系统对漏斗限流需求的响应速度

4. 动态管理和限制:

  • 通过设置 maxPoolSize 参数,可以动态调整对象池的大小,确保不会因为对象池过小而导致获取对象失败。在需要时,可以根据系统负载和需求灵活地调整对象池的大小

这篇关于漏斗限流(leaky bucket)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1068351

相关文章

通俗易懂的Java常见限流算法具体实现

《通俗易懂的Java常见限流算法具体实现》:本文主要介绍Java常见限流算法具体实现的相关资料,包括漏桶算法、令牌桶算法、Nginx限流和Redis+Lua限流的实现原理和具体步骤,并比较了它们的... 目录一、漏桶算法1.漏桶算法的思想和原理2.具体实现二、令牌桶算法1.令牌桶算法流程:2.具体实现2.1

Redis 多规则限流和防重复提交方案实现小结

《Redis多规则限流和防重复提交方案实现小结》本文主要介绍了Redis多规则限流和防重复提交方案实现小结,包括使用String结构和Zset结构来记录用户IP的访问次数,具有一定的参考价值,感兴趣... 目录一:使用 String 结构记录固定时间段内某用户 IP 访问某接口的次数二:使用 Zset 进行

基于Redis有序集合实现滑动窗口限流的步骤

《基于Redis有序集合实现滑动窗口限流的步骤》滑动窗口算法是一种基于时间窗口的限流算法,通过动态地滑动窗口,可以动态调整限流的速率,Redis有序集合可以用来实现滑动窗口限流,本文介绍基于Redis... 滑动窗口算法是一种基于时间窗口的限流算法,它将时间划分为若干个固定大小的窗口,每个窗口内记录了该时间

Java后端微服务架构下的API限流策略:Guava RateLimiter

Java后端微服务架构下的API限流策略:Guava RateLimiter 大家好,我是微赚淘客返利系统3.0的小编,是个冬天不穿秋裤,天冷也要风度的程序猿! 在微服务架构中,API限流是保护服务不受过度使用和拒绝服务攻击的重要手段。Guava RateLimiter是Google开源的Java库中的一个组件,提供了简单易用的限流功能。 API限流概述 API限流通过控制请求的速率来防止

微服务之网关安全基于Zuul并实现网关限流

微服务网关安全 微服务架构下的问题 处理安全和业务逻辑耦合,增加了复杂性和变更成本 随着业务节点增加,认证服务器压力增大 多个微服务同时暴露,增加了外部访问的复杂性 通过网关处理流程 1、请求令牌。2、转发请求。3、返回令牌。4、转发令牌各客户端应用。5、携带令牌发送请求。6、校验令牌。7、返回校验结果信息。8、访问微服务。 实例 引入依赖 <dependencies><depe

谈谈经典限流方法—漏桶、令牌桶与Guava RateLimiter的实现

大数据技术与架构 点击右侧关注,大数据开发领域最强公众号! 暴走大数据 点击右侧关注,暴走大数据! 高并发的业务系统经常要接受大流量的考验,为了保证系统的响应度和稳定性,往往都需要对有风险的接口实施限流(rate limiting),更高大上的说法则是“流量整形”(traffic shaping)。限流的思想最初来源于计算机网络,有两种经典的方法:漏桶和令牌桶。本文先来稍微研究一下它们。

经典限流方法——漏桶、令牌桶与Guava RateLimiter的实现

点击上方蓝色字体,选择“设为星标” 回复”资源“获取更多资源 大数据技术与架构 点击右侧关注,大数据开发领域最强公众号! 暴走大数据 点击右侧关注,暴走大数据! 高并发的业务系统经常要接受大流量的考验,为了保证系统的响应度和稳定性,往往都需要对有风险的接口实施限流(rate limiting),更高大上的说法则是“流量整形”(traffic shaping)。限流的思想最初来源于计算机

使用信号量实现一个限流器:C++实战指南

使用信号量实现一个限流器:C++实战指南 在现代软件开发中,限流器(Rate Limiter)是一种常用的技术,用于控制系统的请求速率,防止系统过载。信号量(Semaphore)是一种强大的同步原语,可以用于实现限流器。本文将详细介绍如何在C++中使用信号量实现一个限流器,并提供完整的代码示例和详细的解释。 什么是限流器? 限流器是一种控制系统请求速率的机制,确保在单位时间内处理的请求数量不

Java 文件下载/上传限流算法

文章目录 一、算法思路二、限流的完整java代码实现三、注意点四、具体demo的github地址 在做文件下载功能时,为了避免下载功能将服务器的带宽打满,从而影响服务器的其他服务。我们可以设计一个限流器来限制下载的速率,从而限制下载服务所占用的带宽。 一、算法思路 定义一个数据块chunk(单位 bytes)以及允许的最大速率 maxRate(单位 KB/s)。通过maxR

常用的限流算法-令牌桶(Token Bucket)php版

令牌桶(Token Bucket)是一种常用的限流算法,用于控制流量的速率。其核心思想是以固定速率向桶中放入令牌,当请求到来时,从桶中取走一定数量的令牌,如果桶中没有足够的令牌,则拒绝请求或进行排队等待。 下面是如何在 PHP 中实现一个简单的令牌桶算法。 1. 令牌桶的基本概念 令牌的生成速度:令牌以固定速率生成并加入到桶中。桶的容量:桶中可以容纳的最大令牌数,防止令牌无限增长。请求的消耗