nginx worker_processes 配置

2018-12-07 22:55:02
搜索到原作者的话:
As a general rule you need the only worker with large number of
worker_connections, say 10,000 or 20,000.
However, if nginx does CPU-intensive work as SSL or gzipping and
you have 2 or more CPU, then you may set worker_processes to be equal
to CPU number.
Besides, if you serve many static files and the total size of the files
is bigger than memory, then you may increase worker_processes to
utilize a full disk bandwidth.
Igor Sysoev


一般一个进程足够了,你可以把连接数设得很大。
如果有SSL、gzip这些比较消耗CPU的工作,而且是多核CPU的话,可以设为和CPU的数量一样。
或者要处理很多很多的小文件,而且文件总大小比内存大很多的时候,也可以把进程数增加,
以充分利用IO带宽(主要似乎是IO操作有block)。


根据我配置实践,
服务器是“多个CPU+gzip+网站总文件大小大于内存”的环境,worker_processes设置为CPU个数的两倍比较好。


分享二:
最近PPC经常出现502错误,网页经常无法打开,所以本人决定对Nginx进行深入折腾!
Nginx本身没有挂掉,否则不会出现502的错误信息,所以原因一定在Nginx的设置上。


经过我查阅资料和测试,发现有可能是worker_processes的参数设置不当引起的。


worker_processes默认情况下为1,一般情况下不用修改,但考虑到实际情况,可以修改这个数值,以提高性能;
官方的建议是修改成CPU的内核数,这里引用一段翻译过的文章: 
worker_processes指明了nginx要开启的进程数,
据官方说法,一般开一个就够了,多开几个,可以减少机器io带来的影响。


据实践表明,nginx的这个参数在一般情况下开4个或8个就可以了,再往上开的话优化不太大。
据另一种说法是,nginx开启太多的进程,会影响主进程调度,所以占用的cpu会增高。
经过我测试发现,
这个数字是不能乱设置的,如果网站没有出现io性能问题,最好不要修改,采用默认的1即可,
如果非要设置,必须要和CPU的内核数匹配,否则要么就假死(主要是Windows),要么就出现502的错误(主要是Linux)。


我的电脑是双核的,按理说应该是2,但是实际上应该是4,因为是双线程的。测试结果如下: 
1、worker_processes为1,线程打开2个,有一个是主线程,运行很稳定。
2、worker_processes为2,线程打开3个,有一个是主线程,1分钟左右挂掉
  (假死,无法打开网页,浏览器一直处于载入中)。
3、worker_processes为4,线程打开5个,有一个是主线程,运行很稳定。
4、worker_processes为8,线程打开9个,有一个是主线程,和2一样,1分钟左右挂掉。


配置参考
配置1:
4 CPU (4 Core) + 4 worker_processes (每个worker_processes 使用1个CPU)
[reistlin@reistlin.com ~]$ cat /proc/cpuinfo | grep processor
processor : 0
processor : 1
processor : 2
processor : 3


worker_processes 4;
worker_cpu_affinity 0001 0010 0100 1000;


配置2:
8 CPU (8 Core) + 8 worker_processes (每个worker_processes 使用1个CPU)
[reistlin@reistlin.com ~]$ cat /proc/cpuinfo | grep processor
processor : 0
processor : 1
processor : 2
processor : 3
processor : 4
processor : 5
processor : 6
processor : 7


worker_processes 8;
worker_cpu_affinity 00000001 00000010 00000100 00001000 00010000 00100000 01000000 10000000;


配置3:
16 CPU (16 Core) + 16 worker_processes (每个worker_processes 使用1个CPU)
[reistlin@reistlin.com ~]$ cat /proc/cpuinfo | grep processor
processor : 0
processor : 1
processor : 2
processor : 3
processor : 4
processor : 5
processor : 6
processor : 7
processor : 8
processor : 9
processor : 10
processor : 11
processor : 12
processor : 13
processor : 14
processor : 15


worker_processes 16;
worker_cpu_affinity 
0000000000000001 0000000000000010 0000000000000100 0000000000001000 0000000000010000 0000000000100000 0000000001000000 0000000010000000 0000000100000000 0000001000000000 0000010000000000 0000100000000000 0001000000000000 0010000000000000 0100000000000000 1000000000000000;


Nginx worker_cpu_affinity 设置
根据 Nginx Wiki 上的资料显示:
worker_cpu_affinity
Syntax: worker_cpu_affinity cpumask [cpumask...]
Default: none
Linux only.
With this option you can bind the worker process to a CPU, it calls sched_setaffinity().


For example,
worker_processes 4; worker_cpu_affinity 0001 0010 0100 1000;
Bind each worker process to one CPU only.
worker_processes 2; worker_cpu_affinity 0101 1010;
Bind the first worker to CPU0/CPU2, bind the second worker to CPU1/CPU3. This is suitable for HTT.


worker_cpu_affinity 默认是没有开启的,
根据例子我们可以看得出,0001 0010 0100 1000 分别代表第1、2、3、4个逻辑CPU,
所以我们可以设置0010 0100 1000来将3个进程分别绑定到第2、3、4个逻辑CPU上:
worker_processes 3;
worker_cpu_affinity 0010 0100 1000;
同时根据例子我们也可以看出,
worker_cpu_affinity 可以将同1个进程绑定在2个逻辑CPU上:


worker_processes 2;
worker_cpu_affinity 0101 1010;
0101也就是第1、3个逻辑CPU上,1010就是第2、4个逻辑CPU上。 
 
 
分享三:
worker_processes指明了nginx要开启的进程数,
据官方说法,一般开一个就够了,多开几个,可以减少机器io带来的影响。


据实践表明,nginx的这个参数在一般情况下开4个或8个就可以了,再往上开的话优化不太大。
据另一种说法是,nginx开启太多的进程,会影响主进程调度,所以占用的cpu会增高,
这个说法我个人没有证实,估计他们是开了一两百个进程来对比的吧。


worker_processes配置的一些注意事项:


1、worker_cpu_affinity配置最好是能写上
我这里服务器多数是双核超线程,相当于4cpu,我一般开8进程,所以这个配置就是这样:
worker_cpu_affinity 0001 0100 1000 0010 0001 0100 1000 0010;


另,worker_cpu_affinity不是什么时候都能用的,
我没有认真研究并罗列所有情况,只知道2.4内核的机器用不了,
如果用不了的话,那么最好是加大worker_processes进程数,这样分配cpu就会平均一点啦,
如果不平均只好多重启几下。


2、worker_rlimit_nofile配置要和系统的单进程打开文件数一致,千万不要再画蛇添足地除以worker_processes。
我现在在linux 2.6内核下开启文件打开数为65535,worker_rlimit_nofile就相应应该填写65535。


这是因为nginx调度时分配请求到进程并不是那么的均衡,所以假如填写10240,
总并发量达到3-4万时就有进程可能超过10240了,这时会返回502错误。
  • 2020-11-22 22:58:52

    Android LiveData Transformations

    有时候有这样的需求,需要在LiveData将变化的数据通知给观察者前,改变数据的类型;或者是返回一个不一样的LiveData。

  • 2020-11-22 23:00:16

    androidx中的lifecycle组件

    Lifecycle-aware components生命周期感知组件执行操作,以响应另一个组件生命周期状态的更改,例如Activity和Fragment。这些组件可以帮助您生成更有组织、更容易维护的轻量级代码。

  • 2020-11-22 23:02:50

    Android数据存储之DataBase的Room

    Room是Google在AndroidX中提供的一个ORM(Object Relational Mapping,对象关系映射)库。它是在SQLite上提供的一个抽象层,可以使用SQLite的全部功能,同时可以更好更便捷流畅地访问数据库。(关于AndroidX可以参考

  • 2020-11-22 23:04:39

    Android组件 LiveData与MutableLiveData教程

    LiveData与ViewMode是经常搭配在一起使用的,但是为了不太混乱,我还是拆分开来说明,此篇博客只讲解 LiveData 与 MutableLiveData的概念与使用方式(但是会涉及到ViewMode的部分代码).

  • 2020-11-22 23:14:52

    Dagger 2 在 Android 上的用法

    在前面的文章我们介绍了Dagger2 中的大部分注解的使用,接下来我们从源码角度分析下第一篇文章中例子的原理。

  • 2020-11-22 23:18:59

    Android开发从Dagger2迁移至Kodein的感受

    最近个人在尝试构建 Kotlin版本 的Android MVVM开发框架,在依赖注入框架的选型上,我最终选择了 Kodein 。这是一个非常轻量级的DI框架,相比于配置繁琐的Dagger(繁琐的配置也是导致Dagger学习成本一直居高不下的原因!),它的配置过程更清晰且简单,并且,这个库的源码也是 Kotlin 的。

  • 2020-11-22 23:25:56

    Dagger2源码解析inject过程

    添加inject后,通过编译生成的DaggerMainComponent类来导入,说明编译以后生成了一些类,那到底生成了什么类呢。 Module和Component又是什么,该怎么里理解 在这篇文章后里将一一讨论。

  • 2020-11-22 23:27:28

    dagger学习教程

    dagger android 学习(一):dagger基础使用 dagger android 学习(二):AndroidInjector的使用 dagger android 学习(三):ContributesAndroidInjector的进一步优化 dagger android 学习(四):基于dagger2的mvp架构