当前位置: 首页 > news >正文

中国网站为什么要备案网站开发视频 百度云

中国网站为什么要备案,网站开发视频 百度云,企业信用信息查询方式,网站集约化平台建设这是我的第 195 期分享作者 | 王磊来源 | Java中文社群#xff08;ID#xff1a;javacn666#xff09;转载请联系授权#xff08;微信ID#xff1a;GG_Stone#xff09;为了上班方便#xff0c;去年我把自己在北郊的房子租出去了#xff0c;搬到了南郊#xff0c;这样… 这是我的第 195 期分享作者 | 王磊来源 | Java中文社群IDjavacn666转载请联系授权微信IDGG_Stone为了上班方便去年我把自己在北郊的房子租出去了搬到了南郊这样离我上班的地方就近了它为我节约了很多的时间成本我可以用它来做很多有意义的事最起码不会因为堵车而闹心了幸福感直线上升。但即使这样生活也有其他的烦恼。南郊的居住密度比较大因此停车就成了头痛的事我租的是路两边的非固定车位每次只要下班回来一定是没有车位停了因此我只能和别人的车并排停着但这样带来的问题是我每天早上都要被挪车的电话给叫醒心情自然就不用说了。但后来几天我就慢慢变聪明了我头天晚上停车的时候会找第二天限行的车并排停着这样我第二天就不用挪车了这真是限行给我带来的“巨大红利”啊。而车辆限行就是一种生活中很常见的限流策略他除了给我带来了以上的好处之外还给我们美好的生活环境带来了一丝改善并且快速增长的私家车已经给我们的交通带来了巨大的“负担”如果再不限行可能所有的车都要被堵在路上这就是限流给我们的生活带来的巨大好处。从生活回到程序中假设一个系统只能为 10W 人提供服务突然有一天因为某个热点事件造成了系统短时间内的访问量迅速增加到了 50W那么导致的直接结果是系统崩溃任何人都不能用系统了显然只有少人数能用远比所有人都不能用更符合我们的预期因此这个时候我们要使用「限流」了。限流分类 限流的实现方案有很多种磊哥这里稍微理了一下限流的分类如下所示合法性验证限流比如验证码、IP 黑名单等这些手段可以有效的防止恶意攻击和爬虫采集容器限流比如 Tomcat、Nginx 等限流手段其中 Tomcat 可以设置最大线程数maxThreads当并发超过最大线程数会排队等待执行而 Nginx 提供了两种限流手段一是控制速率二是控制并发连接数服务端限流比如我们在服务器端通过限流算法实现限流此项也是我们本文介绍的重点。合法性验证限流为最常规的业务代码就是普通的验证码和 IP 黑名单系统本文就不做过多的叙述了我们重点来看下后两种限流的实现方案容器限流和服务端限流。容器限流 Tomcat 限流Tomcat 8.5 版本的最大线程数在 conf/server.xml 配置中如下所示Connector port8080 protocolHTTP/1.1connectionTimeout20000maxThreads150redirectPort8443 / 其中 maxThreads 就是 Tomcat 的最大线程数当请求的并发大于此值maxThreads时请求就会排队执行这样就完成了限流的目的。小贴士maxThreads 的值可以适当的调大一些此值默认为 150Tomcat 版本 8.5.42但这个值也不是越大越好要看具体的硬件配置需要注意的是每开启一个线程需要耗用 1MB 的 JVM 内存空间用于作为线程栈之用并且线程越多 GC 的负担也越重。最后需要注意一下操作系统对于进程中的线程数有一定的限制Windows 每个进程中的线程数不允许超过 2000Linux 每个进程中的线程数不允许超过 1000。Nginx 限流Nginx 提供了两种限流手段一是控制速率二是控制并发连接数。控制速率我们需要使用 limit_req_zone 用来限制单位时间内的请求数即速率限制示例配置如下limit_req_zone $binary_remote_addr zonemylimit:10m rate2r/s; server { location / { limit_req zonemylimit;} } 以上配置表示限制每个 IP 访问的速度为 2r/s因为 Nginx 的限流统计是基于毫秒的我们设置的速度是 2r/s转换一下就是 500ms 内单个 IP 只允许通过 1 个请求从 501ms 开始才允许通过第 2 个请求。我们使用单 IP 在 10ms 内发并发送了 6 个请求的执行结果如下从以上结果可以看出他的执行符合我们的预期只有 1 个执行成功了其他的 5 个被拒绝了第 2 个在 501ms 才会被正常执行。速率限制升级版上面的速率控制虽然很精准但是应用于真实环境未免太苛刻了真实情况下我们应该控制一个 IP 单位总时间内的总访问次数而不是像上面那么精确但毫秒我们可以使用 burst 关键字开启此设置示例配置如下limit_req_zone $binary_remote_addr zonemylimit:10m rate2r/s; server { location / { limit_req zonemylimit burst4;} } burst4 表示每个 IP 最多允许4个突发请求如果单个 IP 在 10ms 内发送 6 次请求的结果如下从以上结果可以看出有 1 个请求被立即处理了4 个请求被放到 burst 队列里排队执行了另外 1 个请求被拒绝了。控制并发数利用 limit_conn_zone 和 limit_conn 两个指令即可控制并发数示例配置如下limit_conn_zone $binary_remote_addr zoneperip:10m; limit_conn_zone $server_name zoneperserver:10m; server {...limit_conn perip 10;limit_conn perserver 100; } 其中 limit_conn perip 10 表示限制单个 IP 同时最多能持有 10 个连接limit_conn perserver 100 表示 server 同时能处理并发连接的总数为 100 个。小贴士只有当 request header 被后端处理后这个连接才进行计数。服务端限流 服务端限流需要配合限流的算法来执行而算法相当于执行限流的“大脑”用于指导限制方案的实现。有人看到「算法」两个字可能就晕了觉得很深奥其实并不是。算法就相当于操作某个事务的具体实现步骤汇总其实并不难懂不要被它的表象给吓到哦~限流的常见算法有以下三种时间窗口算法漏桶算法令牌算法接下来我们分别看来。1.时间窗口算法所谓的滑动时间算法指的是以当前时间为截止时间往前取一定的时间比如往前取 60s 的时间在这 60s 之内运行最大的访问数为 100此时算法的执行逻辑为先清除 60s 之前的所有请求记录再计算当前集合内请求数量是否大于设定的最大请求数 100如果大于则执行限流拒绝策略否则插入本次请求记录并返回可以正常执行的标识给客户端。滑动时间窗口如下图所示其中每一小个表示 10s被红色虚线包围的时间段则为需要判断的时间间隔比如 60s 秒允许 100 次请求那么红色虚线部分则为 60s。我们可以借助 Redis 的有序集合 ZSet 来实现时间窗口算法限流实现的过程是先使用 ZSet 的 key 存储限流的 IDscore 用来存储请求的时间每次有请求访问来了之后先清空之前时间窗口的访问量统计现在时间窗口的个数和最大允许访问量对比如果大于等于最大访问量则返回 false 执行限流操作负责允许执行业务逻辑并且在 ZSet 中添加一条有效的访问记录具体实现代码如下。我们借助 Jedis 包来操作 Redis实现在 pom.xml 添加 Jedis 框架的引用配置如下!-- https://mvnrepository.com/artifact/redis.clients/jedis -- dependencygroupIdredis.clients/groupIdartifactIdjedis/artifactIdversion3.3.0/version /dependency 具体的 Java 实现代码如下import redis.clients.jedis.Jedis;public class RedisLimit {// Redis 操作客户端static Jedis jedis  new Jedis(127.0.0.1, 6379);public static void main(String[] args) throws InterruptedException {for (int i  0; i  15; i) {boolean res  isPeriodLimiting(java, 3, 10);if (res) {System.out.println(正常执行请求  i);} else {System.out.println(被限流  i);}}// 休眠 4sThread.sleep(4000);// 超过最大执行时间之后再从发起请求boolean res  isPeriodLimiting(java, 3, 10);if (res) {System.out.println(休眠后正常执行请求);} else {System.out.println(休眠后被限流);}}/*** 限流方法滑动时间算法* param key      限流标识* param period   限流时间范围单位秒* param maxCount 最大运行访问次数* return*/private static boolean isPeriodLimiting(String key, int period, int maxCount) {long nowTs  System.currentTimeMillis(); // 当前时间戳// 删除非时间段内的请求数据清除老访问数据比如 period60 时标识清除 60s 以前的请求记录jedis.zremrangeByScore(key, 0, nowTs - period * 1000);long currCount  jedis.zcard(key); // 当前请求次数if (currCount  maxCount) {// 超过最大请求次数执行限流return false;}// 未达到最大请求数正常执行业务jedis.zadd(key, nowTs,   nowTs); // 请求记录 1return true;} } 以上程序的执行结果为正常执行请求0正常执行请求1正常执行请求2正常执行请求3正常执行请求4正常执行请求5正常执行请求6正常执行请求7正常执行请求8正常执行请求9被限流10被限流11被限流12被限流13被限流14休眠后正常执行请求此实现方式存在的缺点有两个使用 ZSet 存储有每次的访问记录如果数据量比较大时会占用大量的空间比如 60s 允许 100W 访问时此代码的执行非原子操作先判断后增加中间空隙可穿插其他业务逻辑的执行最终导致结果不准确。2.漏桶算法漏桶算法的灵感源于漏斗如下图所示滑动时间算法有一个问题就是在一定范围内比如 60s 内只能有 10 个请求当第一秒时就到达了 10 个请求那么剩下的 59s 只能把所有的请求都给拒绝掉而漏桶算法可以解决这个问题。漏桶算法类似于生活中的漏斗无论上面的水流倒入漏斗有多大也就是无论请求有多少它都是以均匀的速度慢慢流出的。当上面的水流速度大于下面的流出速度时漏斗会慢慢变满当漏斗满了之后就会丢弃新来的请求;当上面的水流速度小于下面流出的速度的话漏斗永远不会被装满并且可以一直流出。漏桶算法的实现步骤是先声明一个队列用来保存请求这个队列相当于漏斗当队列容量满了之后就放弃新来的请求然后重新声明一个线程定期从任务队列中获取一个或多个任务进行执行这样就实现了漏桶算法。上面我们演示 Nginx 的控制速率其实使用的就是漏桶算法当然我们也可以借助 Redis 很方便的实现漏桶算法。我们可以使用 Redis 4.0 版本中提供的 Redis-Cell 模块该模块使用的是漏斗算法并且提供了原子的限流指令而且依靠 Redis 这个天生的分布式程序就可以实现比较完美的限流了。Redis-Cell 实现限流的方法也很简单只需要使用一条指令 cl.throttle 即可使用示例如下 cl.throttle mylimit 15 30 60 1integer0 # 0 表示获取成功1 表示拒绝 2integer15 # 漏斗容量 3integer14 # 漏斗剩余容量 4integer-1 # 被拒绝之后多长时间之后再试单位秒-1 表示无需重试 5integer2 # 多久之后漏斗完全空出来 其中 15 为漏斗的容量30 / 60s 为漏斗的速率。3.令牌算法在令牌桶算法中有一个程序以某种恒定的速度生成令牌并存入令牌桶中而每个请求需要先获取令牌才能执行如果没有获取到令牌的请求可以选择等待或者放弃执行如下图所示我们可以使用 Google 开源的 guava 包很方便的实现令牌桶算法首先在 pom.xml 添加 guava 引用配置如下!-- https://mvnrepository.com/artifact/com.google.guava/guava -- dependencygroupIdcom.google.guava/groupIdartifactIdguava/artifactIdversion28.2-jre/version /dependency 具体实现代码如下import com.google.common.util.concurrent.RateLimiter;import java.time.Instant;/*** Guava 实现限流*/ public class RateLimiterExample {public static void main(String[] args) {// 每秒产生 10 个令牌每 100 ms 产生一个RateLimiter rt  RateLimiter.create(10);for (int i  0; i  11; i) {new Thread(() - {// 获取 1 个令牌rt.acquire();System.out.println(正常执行方法ts:  Instant.now());}).start();}} } 以上程序的执行结果为正常执行方法ts:2020-05-15T14:46:37.175Z正常执行方法ts:2020-05-15T14:46:37.237Z正常执行方法ts:2020-05-15T14:46:37.339Z正常执行方法ts:2020-05-15T14:46:37.442Z正常执行方法ts:2020-05-15T14:46:37.542Z正常执行方法ts:2020-05-15T14:46:37.640Z正常执行方法ts:2020-05-15T14:46:37.741Z正常执行方法ts:2020-05-15T14:46:37.840Z正常执行方法ts:2020-05-15T14:46:37.942Z正常执行方法ts:2020-05-15T14:46:38.042Z正常执行方法ts:2020-05-15T14:46:38.142Z从以上结果可以看出令牌确实是每 100ms 产生一个而 acquire() 方法为阻塞等待获取令牌它可以传递一个 int 类型的参数用于指定获取令牌的个数。它的替代方法还有 tryAcquire()此方法在没有可用令牌时就会返回 false 这样就不会阻塞等待了。当然 tryAcquire() 方法也可以设置超时时间未超过最大等待时间会阻塞等待获取令牌如果超过了最大等待时间还没有可用的令牌就会返回 false。注意使用 guava 实现的令牌算法属于程序级别的单机限流方案而上面使用 Redis-Cell 的是分布式的限流方案。总结 本文提供了 6 种具体的实现限流的手段他们分别是Tomcat 使用 maxThreads 来实现限流Nginx 提供了两种限流方式一是通过 limit_req_zone 和 burst 来实现速率限流二是通过 limit_conn_zone 和 limit_conn 两个指令控制并发连接的总数。最后我们讲了时间窗口算法借助 Redis 的有序集合可以实现还有漏桶算法可以使用 Redis-Cell 来实现以及令牌算法可以解决 Google 的 guava 包来实现。需要注意的是借助 Redis 实现的限流方案可用于分布式系统而 guava 实现的限流只能应用于单机环境。如果你嫌弃服务器端限流麻烦甚至可以在不改代码的情况下直接使用容器限流Nginx 或 Tomcat但前提是能满足你的业务需求。好了文章到这里就结束了期待我们下期再会~最后的话原创不易如果觉得本文对你有用请随手点击一个「在看」这是对作者最大的支持与鼓励谢谢你参考 鸣谢https://www.cnblogs.com/biglittleant/p/8979915.html一口气说出 6 种延时队列的实现方法面试官满意的笑了String性能提升10倍的几个方法(源码原理分析)关注公众号发送”进群“磊哥拉你进读者群。
http://www.zqtcl.cn/news/378932/

相关文章:

  • 做图片推广的网站威海高端网站建设
  • 台州网站公司建站网站首页模板图片
  • 网站建设本科毕业设计论文网址
  • 泰州企业建站程序乐清网站建设公司
  • 微信小程序网站建设哪家好郑州建设网
  • 网站流量查询站长之家自己创业做原公司一样的网站
  • 哪有专做飞织鞋面的网站广州企业网站制作哪家好
  • 如何用域名做邮箱 网站站长工具5g
  • 威海 医院网站建设宝安专业网站设计公司
  • 营销企业网站建设步骤建筑 企业官网设计
  • 网站建设的内容网站怎么做视频的软件
  • 大型网站多少钱企业咨询管理是干嘛的
  • 陕西建设银行网站小企业网站建设公司
  • linux下网站开发计算机网络技术专业主要学什么
  • 长沙网站维护公司建个门户网站
  • 做采集网站难不做科技的网站
  • 中小微企业服务平台seo怎么提升关键词的排名
  • 优秀企业网站欣赏店名设计wordpress文章列表添加字段
  • 有哪些做软件的网站服务器安装WordPress没有权限访问
  • app开发和网站开发公司网站怎么做百度竞价
  • 医疗机构网站备案网站建设面试常见问题
  • 建设网银登录网站国内欣赏电商设计的网站
  • 自适应网站优点缺点网站上的在线答题是怎么做的
  • 查询单位信息的网站免费学编程的网站有哪些
  • 建设企业网站进去无法显示wordpress 在线课程
  • 博客型网站建设广州网站建设如何做
  • 网站导航栏全屏怎么做万年网站建设
  • flash源码网站百度关键词价格
  • 个人网站如何发布怎么做记步数的程序到网站
  • 石家庄网站制作公司排名前十可视化网站开发工具有哪些