算法思想是:

令牌以固定速率产生,并缓存到令牌桶中;令牌桶放满时,多余的令牌被丢弃;要求要花费等比例的令牌才能被处理;令牌不足时,要求被缓存。
漏桶算法

算法思想是:

水(要求)从上方倒入水桶,从水桶下方流出(被处理);来不及流出的水存在水桶中(缓冲),以固定速率流出;水桶满后水溢出(丢弃)。
这个算法的核心是:缓存要求、匀速处理、多余的要求直接丢弃。
比较漏桶算法,令牌桶算法不同之处在于它不但有一只“桶”,还有个行列步队,这个桶是用来存放令牌的,行列步队才是用来存放要求的。

从浸染上来说,漏桶和令牌桶算法最明显的差异便是是否许可突发流量(burst)的处理,漏桶算法能够强行限定数据的实时传输(处理)速率,对突发流量不做额外处理;而令牌桶算法能够在限定数据的均匀传输速率的同时许可某种程度的突发传输。

ngixjsp逝世磕 Nginx 系列Nginx 限流设置装备摆设总结Nginx实战焦点常识 RESTful API

Nginx按要求速率限速模块利用的是漏桶算法,即能够强行担保要求的实时处理速率不会超过设置的阈值。

Nginx官方版本限定IP的连接和并发分别有两个模块:

limit_req_zone 用来限定单位韶光内的要求数,即速率限定,采取的漏桶算法 "leaky bucket"。
limit_req_conn 用来限定同一韶光连接数,即并发限定。
limit_req_zone 参数配置

Syntax: limit_req zone=name [burst=number] [nodelay];Default: —Context: http, server, locationlimit_req_zone$binary_remote_addrzone=one:10mrate=1r/s;

第一个参数:$binary_remote_addr 表示通过remote_addr这个标识来做限定,“binary_”的目的是缩写内存占用量,是限定同一客户端ip地址。
第二个参数:zone=one:10m表示天生一个大小为10M,名字为one的内存区域,用来存储访问的频次信息。
第三个参数:rate=1r/s表示许可相同标识的客户真个访问频次,这里限定的是每秒1次,还可以有比如30r/m的。

limit_req zone=one burst=5 nodelay;

第一个参数:zone=one 设置利用哪个配置区域来做限定,与上面limit_req_zone 里的name对应。
第二个参数:burst=5,重点解释一下这个配置,burst爆发的意思,这个配置的意思是设置一个大小为5的缓冲区当有大量要求(爆发)过来时,超过了访问频次限定的要求可以先放到这个缓冲区内。
第三个参数:nodelay,如果设置,超过访问频次而且缓冲区也满了的时候就会直接返回503,如果没有设置,则所有要求会等待排队。

例子:

http{limit_req_zone$binary_remote_addrzone=one:10mrate=1r/s;server{location/search/ {limit_reqzone=one burst=5nodelay;}}

下面配置可以限定特定UA(比如搜索引擎)的访问:

limit_req_zone$anti_spiderzone=one:10mrate=10r/s;limit_reqzone=one burst=100nodelay;if($http_user_agent~ "googlebot|bingbot|Feedfetcher-Google"){set$anti_spider$http_user_agent;}

其他参数

Syntax: limit_req_log_level info | notice | warn | error;Default:limit_req_log_level error;Context: http, server, location

当做事器由于limit被限速或缓存时,配置写入日志。
延迟的记录比谢绝的记录低一个级别。
例子:limit_req_log_level notice延迟的的基本是info。

Syntax: limit_req_status code;Default:limit_req_status503;Context: http, server, location

设置谢绝要求的返回值。
值只能设置 400 到 599 之间。

ngx_http_limit_conn_module 参数配置

这个模块用来限定单个IP的要求数。
并非所有的连接都被计数。
只有在做事器处理了要求并且已经读取了全体要求头时,连接才被计数。

Syntax: limit_conn zone number;Default: —Context: http, server, locationlimit_conn_zone$binary_remote_addrzone=addr:10m;server{location/download/ {limit_connaddr1;}

一次只许可每个IP地址一个连接。

limit_conn_zone$binary_remote_addrzone=perip:10m;limit_conn_zone$server_namezone=perserver:10m;server {...limit_conn perip 10;limit_conn perserver 100;}

可以配置多个limit_conn指令。
例如,以上配置将限定每个客户端IP连接到做事器的数量,同时限定连接到虚拟做事器的总数。

Syntax: limit_conn_zone key zone=name:size;Default: —Context: httplimit_conn_zone$binary_remote_addrzone=addr:10m;

在这里,客户端IP地址作为关键。
请把稳,不是$ remote_addr,而是利用$ binary_remote_addr变量。
$ remote_addr变量的大小可以从7到15个字节不等。
存储的状态在32位平台上占用32或64字节的内存,在64位平台上总是占用64字节。
对付IPv4地址,$ binary_remote_addr变量的大小始终为4个字节,对付IPv6地址则为16个字节。
存储状态在32位平台上始终占用32或64个字节,在64位平台上占用64个字节。
一个兆字节的区域可以保持大约32000个32字节的状态或大约16000个64字节的状态。
如果区域存储耗尽,做事器会将缺点返回给所有其他要求。

Syntax: limit_conn_log_level info | notice | warn | error;Default:limit_conn_log_level error;Context: http, server, location

当做事器限定连接数时,设置所需的日志记录级别。

Syntax: limit_conn_status code;Default:limit_conn_status503;Context: http, server, location

设置谢绝要求的返回值。

实战实例一 限定访问速率

limit_req_zone$binary_remote_addrzone=mylimit:10mrate=2r/s;server{location/ {limit_reqzone=mylimit;}}

上述规则限定了每个IP访问的速率为2r/s,并将该规则浸染于根目录。
如果单个IP在非常短的韶光内并发发送多个要求,结果会若何呢?

我们利用单个IP在10ms内发并发送了6个要求,只有1个成功,剩下的5个都被谢绝。
我们设置的速率是2r/s,为什么只有1个成功呢,是不是Nginx限定错了?当然不是,是由于Nginx的限流统计是基于毫秒的,我们设置的速率是2r/s,转换一下便是500ms内单个IP只许可通过1个要求,从501ms开始才许可通过第二个要求。

实例二 burst缓存处理

我们看到,我们短韶光内发送了大量要求,Nginx按照毫秒级精度统计,超出限定的要求直接谢绝。
这在实际场景中难免不免过于苛刻,真实网络环境中要求到来不是匀速的,很可能有要求“突发”的情形,也便是“一股子一股子”的。
Nginx考虑到了这种情形,可以通过burst关键字开启对突发要求的缓存处理,而不是直接谢绝。
来看我们的配置:

limit_req_zone$binary_remote_addrzone=mylimit:10mrate=2r/s;server{location/ {limit_reqzone=mylimit burst=4;}}

我们加入了burst=4,意思是每个key(此处是每个IP)最多许可4个突发要求的到来。
如果单个IP在10ms内发送6个要求,结果会若何呢?

比较实例一成功数增加了4个,这个我们设置的burst数目是同等的。
详细处理流程是:1个要求被立即处理,4个要求被放到burst行列步队里,其余一个要求被谢绝。
通过burst参数,我们使得Nginx限流具备了缓存处理突发流量的能力。

但是请把稳:burst的浸染是让多余的要求可以先放到行列步队里,逐步处理。
如果不加nodelay参数,行列步队里的要求不会立即处理,而是按照rate设置的速率,以毫秒级精确的速率逐步处理。

实例三 nodelay降落排队韶光

实例二中我们看到,通过设置burst参数,我们可以许可Nginx缓存处理一定程度的突发,多余的要求可以先放到行列步队里,逐步处理,这起到了平滑流量的浸染。
但是如果行列步队设置的比较大,要求排队的韶光就会比较长,用户角度看来便是RT变长了,这对用户很不友好。
有什么办理办法呢?nodelay参数许可要求在排队的时候就立即被处理,也便是说只要要求能够进入burst行列步队,就会立即被后台worker处理,请把稳,这意味着burst设置了nodelay时,系统瞬间的QPS可能会超过rate设置的阈值。
nodelay参数要跟burst一起利用才有浸染。

延续实例二的配置,我们加入nodelay选项:

limit_req_zone$binary_remote_addrzone=mylimit:10mrate=2r/s;server{location/ {limit_reqzone=mylimit burst=4nodelay;}}

单个IP 10ms内并发发送6个要求,结果如下:

跟实例二比较,要求成功率没变革,但是总体耗时变短了。
这怎么阐明呢?实例二中,有4个要求被放到burst行列步队当中,事情进程每隔500ms(rate=2r/s)取一个要求进行处理,末了一个要求要排队2s才会被处理;实例三中,要求放入行列步队跟实例二是一样的,但不同的是,行列步队中的要求同时具有了被处理的资格,以是实例三中的5个要求可以说是同时开始被处理的,花费韶光自然变短了。

但是请把稳,虽然设置burst和nodelay能够降落突发要求的处理韶光,但是长期来看并不会提高吞吐量的上限,长期吞吐量的上限是由rate决定的,由于nodelay只能担保burst的要求被立即处理,但Nginx会限定行列步队元素开释的速率,就像是限定了令牌桶中令牌产生的速率。

看到这里你可能会问,加入了nodelay参数之后的限速算法,到底算是哪一个“桶”,是漏桶算法还是令牌桶算法?当然还算是漏桶算法。
考虑一种情形,令牌桶算法的token为耗尽时会怎么做呢?由于它有一个要求行列步队,以是会把接下来的要求缓存下来,缓存多少受限于行列步队大小。
但此时缓存这些要求还故意义吗?如果server已经由载,缓存行列步队越来越长,RT越来越高,纵然过了良久要求被处理了,对用户来说也没什么代价了。
以是当token不足用时,最明智的做法便是直接谢绝用户的要求,这就成了漏桶算法。

示例四 自定义返回值

limit_req_zone$binary_remote_addrzone=mylimit:10mrate=2r/s;server{location/ {limit_reqzone=mylimit burst=4nodelay;limit_req_status598;}}

默认情形下 没有配置 status 返回值的状态:

自定义 status 返回值的状态:

Nginx实战

Nginx是一款轻量级的Web 做事器/反向代理做事器及电子邮件(IMAP/POP3)代理做事器,在BSD-like 协议下发行。
其特点是霸占内存少,并发能力强,事实上nginx的并发能力确实在同类型的网页做事器中表现较好,中国大陆利用nginx网站用户有:百度、京东、新浪、网易、腾讯、淘宝等。

Nginx 是一个很强大的高性能Web和反向代理做事,它具有很多非常优胜的特性:

在连接高并发的情形下,Nginx是Apache做事不错的替代品:Nginx在美国是做虚拟主机买卖的老板们常常选择的软件平台之一。
能够支持高达 50,000 个并发连接数的相应,感谢Nginx为我们选择了 epoll and kqueue作为开拓模型。

由于细节内容实在太多啦,以是只把部分知识点截图出来粗略的先容,每个小节点里面都有更细化的内容!

Nginx实战

第 1 章 Nginx 简介基本先容

第 2 章 Nginx 做事器的安装与配置

第 3 章 Nginx 的基本配置与优化

第 4 章 Nginx 与 PHP(FastCGI)的安装、配置与优化

第 5 章 Nginx 与 JSP、ASP.NET、Perl 的安装与配置

第 6 章 Nginx HTTP 负载均衡和反向代理的配置与优化

第 7 章 Nginx 的 Rewrite 规则编写实例

第 8 章 Nginx 模块开拓

第 9 章 Nginx 的 Web 缓存做事与新浪网的开源 NCACHE 模块

第 10 章 Nginx 在海内有名网站中的运用案例

第 11 章 Nginx 的非范例运用实例

第 12 章 Nginx 的核心模块

第 13 章 Nginx 的标准 HTTP 模块

第 14 章 Nginx 的其他 HTTP 模块

第 15 章 Nginx 的邮件模块

须要获取这份Nginx电子版书本的和更多资料的小伙伴可以转发加关注后私信(学习)即可获取!