深刻了解SAPI

1、SAPI比较

1. SAPI

服务器应用程序编程接口,就是服务器与编程语言之间交互的接口。好比Linux命令行执行一段PHP代码,实际上是Linux shell经过PHP SAPI传入一组参数,zend引擎执行后返回给shell。在PHP生命周期的各个阶段,一些与服务相关的操做都是经过SAPI接口实现。php

php_sapi_name()能够查看当前SAPI接口的类型。  
如 cli(php -r "echo php_sapi_name();")、fpm-fcgi等

2. PHP运行和加载的4个阶段

①Minit 模块初始化阶段,能够初始化php扩展、类库的内部变量、注册常量,定义模块使用的类等。html

②Rinit 请求初始化阶段,在模块初始化并激活后,会建立PHP运行环境,初始化本次请求所需的环境变量,好比 $_SERVER,$_SESSIONmysql

③Rshutdown 请求关闭阶段,执行最后的清理工做,释放全部处理本次请求的资源(申请的变量)。请求完成多是执行到脚本完成,也多是调用die()或exit()函数完成nginx

④Mshutdown 模块回收阶段,用于关闭本身的内核子系统,释放没存。sql

3. SAPI 5种运行模式

①单进程模式(CLI,CGI),每次执行PHP脚本,都会执行第二部分讲的四个INT和Shutdown事件。当用户请求数量很是多时,会大量挤占系统的资源如内存,CPU时间等,形成系统开销很大
clipboard.pngshell

②多进程模式(Apache下的prefork MPM模式),会fork不少子进程,每一个子进程拥有本身独立的进程地址空间,在一个子进程中,PHP的生命周期是调用MINT启动后,执行屡次请求(RINT/RSHUTDOWN),在Apache关闭或进程结束后,才会调用MSHUTDOWN进行回收阶段。
多进程模型中,每一个子进程都是独立运行,没有代码和数据共享,所以一个子进程终止退出和从新生成,不会影响其余子进程的稳定。数据库

clipboard.png

clipboard.png

③多线程模式(Apache2的Worker MPM),在一个进程下建立多个线程,在同一个进程地址空间执行编程

clipboard.png

④fastCGI模式,nginx+php-fpm就是这个模式,fast-cgi是CGI的升级版本,FastCGI能够当作是一个常驻型的CGI,它能够一直执行着,运行后能够fork多个进程,不用花费时间动态Fork子进程。也不须要每次请求都调用MINT/MSHUTDOWN。
⑤内嵌模式,容许在C/C++语言中调用PHP提供的函数,运行模式和CGI同样,执行4个阶段vim

2、php-fpm运行原理

  • CGI:是个协议,服务器发起请求,传给PHP解析器,传递哪些数据,以什么格式,由CGI决定
  • fastcgi:是个协议,提升CGI性能的,不用每次都去初始化,进程不够用,会预先启动几个进程,进程空闲太多了也会停掉一些,fastCGI对进程的管理,提升性能,节约了资源
  • php-fpm:实现fastCGI协议的程序,被PHP官方收了,也提供了进程管理功能,进程包含 master 进程和 worker 进程两种进程。 master 进程只有一个,负责监听端口分发请求,接收来自 Web Server 的请求,而 worker 进程则通常有多个(具体数量根据实际须要配置),每一个进程内部都嵌入了一个 PHP 解释器,是 PHP 代码真正执行的地方。
  • php-cgi:cgi解释器进程

FastCGI的工做原理:api

  1. Web Server启动时载入FastCGI进程管理器
  2. FastCGI进程管理器自身初始化,启动多个CGI解释器(可见多个php-cgi)并等待来自Web Server的链接
  3. 当客户端请求到达Web Server时,FastCGI进程管理器选择并链接到一个CGI解释器。Web Server将CGI环境变量和标准输入发送到FastCGI子进程php-cgi
  4. FastCGI子进程完成处理后将标准输出和错误信息从同一链接返回Web Server。当FastCGI子进程关闭链接时,请求便告知处理完成。FastCGI子进程接着等待并处理来自FastCGI继承管理器的下一个链接

使用FastCGI,系统开销小。另外,对于数据库和Memcache的持续链接能够工做。

数据库短链接connect:请求关闭阶段,释放请求所用的资源,数据库链接句柄也会被释放

数据库长链接pconnect:请求关闭后,PHP会收留这次链接,即便主动关闭也不会关闭而是收留,下次有打开相同链接的请求时,PHP直接把收留的句柄拿出来,省去创建链接的过程。

php-fpm实现长链接也须要配合数据库一些配置,一个进程收留一个链接,数据库链接的数量就是子进程数量,因此数据库容许链接数就要大于子进程数。

clipboard.png

3、php-fpm进程管理的三种模式

php-fpm支持三种运行模式,分别为static、ondemand、dynamic,默认为dynamic 。

  • static : 静态模式,启动时分配固定的worker进程。只须要考虑max_children的数量,数量取决于cpu的个数和应用的响应时间。
  • ondemand: 按需分配,启动时不分配任何进程,当收到用户请求时才启动进程。 master进程检查work进程的数量是否受限,是否有空闲的work进程,没有就新建work进程。在大流量的系统上master进程会变得繁忙,占用系统cpu资源,不适合大流量环境的部署。
  • dynamic: 动态模式,启动时分配固定的进程。伴随着请求数增长,在设定的浮动范围调整worker进程。
pm = dynamic  //动态进程管理,对于专用服务器,能够设置为static,静态一次性启动最大子进程数,不会变化。
 
 pm.max_children = 50 //最大子进程数,ps aux能够查看
 
 pm.start_servers = 20 //启动服务时会启动的进程数
 
 pm.min_spare_servers = 5 //保证空闲子进程数的最小值,若是空闲进程小于这个值,php-fpm服务会建立新的子进程。
 
 pm.max_spare_servers = 35 //保证空闲子进程数的最大值,若是空闲进程高于这个值,就进行清理。
 
 pm.max_requests = 500  //定义一个子进程最多处理的请求数,达到这个值,进程自动退出。目的是为了控制内存溢出,使内存在一个可控范围内。可是若是设置的很小,有可能多个进程同时达到这个值,同时重启,就会致使PHP中止响应直到重启完毕。设置为0表示一直接受请求。

4、php-fpm慢日志

若是一个php网站能够访问,就是访问速度变慢了,能够经过php-fpm的慢执行日志,清晰的了解到php的脚本哪里执行时间长,它能够定位到具体的代码行

vim /usr/local/php/etc/php-fpm.d/www.conf
 request_slowlog_timeout = 1 //超时时间
 slowlog = /usr/local/php/var/log/www-slow.log
 重启php-fpm /etc/init.d/php-fpm reload

我在php文件中加了一行sleep(3);,运行以后返回结果

clipboard.png

图片描述

参考文献

一、https://www.jianshu.com/p/c9a... php-fpm进程管理的三种模式
二、https://www.jb51.net/article/... SAPI的5种运行模式
三、http://blog.51cto.com/1260661... php-fpm慢日志
四、https://www.cnblogs.com/wpjam... php-fpm与mysql长链接

相关文章
相关标签/搜索