Nginx实现FastCGI

CGI的由来

  最早的Web服务器只能简单地响应浏览器发来的HTTP请求,并将存储在服务器上的HTML文件返回给浏览器,也就是静态html文件,但是后期随着网站功能增多网站开发也越来越复杂,以至于出现动态技术,比如像php(1995年)、java(1995)、python(1991)语言开发的网站,但是nginx/apache服务器并不能直接运行 php、java这样的文件,apache实现的方式是打补丁,但是nginx缺通过与第三方基于协议实现,即通过某种特定协议将客户端请求转发给第三方服务处理,第三方服务器会新建新的进程处理用户的请求,处理完成后返回数据给Nginx并回收进程,最后nginx在返回给客户端,那这个约定就是通用网关接口(common gateway interface,简称CGI),CGI(协议)是web服务器和外部应用程序之间的接口标准,是cgi程序和web服务器之间传递信息的标准化接口。

FastCGI

  CGI协议虽然解决了语言解析器和web server之间通讯的问题,但是它的效率很低,因为web server每收到一个请求都会创建一个CGI进程,PHP解析器都会解析php.ini文件,初始化环境,请求结束的时候再关闭进程,对于每一个创建的CGI进程都会执行这些操作,所以效率很低,而FastCGI是用来提高CGI性能的,FastCGI每次处理完请求之后不会关闭掉进程,而是保留这个进程,使这个进程可以处理多个请求。这样的话每个请求都不用再重新创建一个进程了,大大提升了处理效率。

什么是PHP-FPM

  PHP-FPM(FastCGI Process Manager:FastCGI进程管理器)是一个实现了Fastcgi的程序,并且提供进程管理的功能。进程包括master进程和worker进程。master进程只有一个,负责监听端口,接受来自webserver的请求。worker进程一般会有多个,每个进程中会嵌入一个PHP解析器,进行PHP代码的处理。

FastCHI配置指令

  Nginx基于模块ngx_http_fastcgi_module实现通过fastcgi协议将指定的客户端请求转发至php-fpm处理,其配置指令如下:

fastcgi_pass address;
# 转发请求到后端服务器,address为后端的fastcgi server的地址,可用位置:location, if in location

fastcgi_index name;
# fastcgi默认的主页资源,示例:fastcgi_index index.php;

fastcgi_param parameter value [if_not_empty];
# 设置传递给FastCGI服务器的参数值,可以是文本,变量或组合,可用于将Nginx的内置变量赋值给自定义key
fastcgi_param REMOTE_ADDR $remote_addr; #客户端源IP
fastcgi_param REMOTE_PORT $remote_port; #客户端源端口
fastcgi_param SERVER_ADDR $server_addr; #请求的服务器IP地址
fastcgi_param SERVER_PORT $server_port; #请求的服务器端口
fastcgi_param SERVER_NAME $server_name; #请求的server name

Nginx默认配置示例:
    location ~ \.php$ {
        root html;
        fastcgi_pass 127.0.0.1:9000;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name; #默认脚本路径
        include fastcgi_params;
    }

缓存定义指令

fastcgi_cache_path path [levels=levels] [use_temp_path=on|off] keys_zone=name:size [inactive=time] [max_size=size] [manager_files=number] [manager_sleep=time] [manager_threshold=time] [loader_files=number] [loader_sleep=time] [loader_threshold=time] [purger=on|off] [purger_files=number] [purger_sleep=time]
[purger_threshold=time];
定义fastcgi的缓存;
    path # 缓存位置为磁盘上的文件系统路径
    max_size=size # 磁盘path路径中用于缓存数据的缓存空间上限
    levels=levels:缓存目录的层级数量,以及每一级的目录数量,levels=ONE:TWO:THREE,示例:leves=1:2:2
    keys_zone=name:size # 设置缓存名称及k/v映射的内存空间的名称及大小
    inactive=time # 缓存有效时间,默认10分钟,需要在指定时间满足fastcgi_cache_min_uses 次数被视为活动缓存。

缓存调用指令

fastcgi_cache zone | off;
# 调用指定的缓存空间来缓存数据,可用位置:http, server, location

fastcgi_cache_key string;
# 定义用作缓存项的key的字符串,示例:fastcgi_cache_key $request_uri;

fastcgi_cache_methods GET | HEAD | POST ...;
# 为哪些请求方法使用缓存

fastcgi_cache_min_uses number;
# 缓存空间中的缓存项在inactive定义的非活动时间内至少要被访问到此处所指定的次数方可被认作活动项

fastcgi_keep_conn on | off;
# 收到后端服务器响应后,fastcgi服务器是否关闭连接,建议启用长连接

fastcgi_cache_valid [code ...] time;
# 不同的响应码各自的缓存时长

fastcgi_hide_header field; # 隐藏响应头指定信息
fastcgi_pass_header field; # 返回响应头指定信息,默认不会将Status、X-Accel-...返回

FastCGI示例--Nginx与php-fpm在同一服务器上

php环境准备

# yum安装默认版本php
[root@CentOS7 ~]#yum install -y php-fpm php-mysql -y
# 启动php-fpm程序
[root@CentOS7 ~]#systemctl start php-fpm && systemctl enable php-fpm
Created symlink from /etc/systemd/system/multi-user.target.wants/php-fpm.service to /usr/lib/systemd/system/php-fpm.service.
# 查看php-fpm进程
[root@CentOS7 ~]#ps -ef | grep php-fpm
root       7457      1  1 10:44 ?        00:00:00 php-fpm: master process (/etc/php-fpm.conf)
apache     7459   7457  0 10:44 ?        00:00:00 php-fpm: pool www
apache     7460   7457  0 10:44 ?        00:00:00 php-fpm: pool www
apache     7461   7457  0 10:44 ?        00:00:00 php-fpm: pool www
apache     7462   7457  0 10:44 ?        00:00:00 php-fpm: pool www
apache     7463   7457  0 10:44 ?        00:00:00 php-fpm: pool www
root       7492   7278  0 10:44 pts/0    00:00:00 grep --color=auto php-fpm

php配置优化

[root@CentOS7 ~]#grep "^[a-Z]" /etc/php-fpm.conf
include=/etc/php-fpm.d/*.conf
pid = /run/php-fpm/php-fpm.pid
error_log = /var/log/php-fpm/error.log
daemonize = yes  #是否是后台启动

[root@CentOS7 ~]#vim /etc/php-fpm.d/www.conf
[root@CentOS7 ~]#grep -v "^;" /etc/php-fpm.d/www.conf | grep -v '^[ ]*$'
[www]
listen = 127.0.0.1:9000    # 监听地址及IP
listen.allowed_clients = 127.0.0.1   # 允许客户端从哪个源IP地址访问,要允许所有行首加 ;注释即可
user = nginx   # php-fpm启动的用户和组,会涉及到后期文件的权限问题
group = nginx
pm = dynamic    # 动态模式进程管理
pm.max_children = 500    # 静态方式下开启的php-fpm进程数量,在动态方式下他限定php-fpm的最大进程数
pm.start_servers = 100    # 动态模式下初始进程数,必须大于等于pm.min_spare_servers和小于等于pm.max_children的值。
pm.min_spare_servers = 100    # 最小空闲进程数
pm.max_spare_servers = 200    # 最大空闲进程数
pm.max_requests = 500000    # 进程累计请求回收值,会重启
pm.status_path = /pm_status    # 状态访问URL
ping.path = /ping    # ping访问地址
ping.response = ping-pong    # ping返回值
slowlog = /var/log/php-fpm/www-slow.log    # 慢日志路径
php_admin_value[error_log] = /var/log/php-fpm/www-error.log    # 错误日志
php_admin_flag[log_errors] = on
php_value[session.save_handler] = files    # phpsession保存方式及路径
php_value[session.save_path] = /var/lib/php/session    # 当时使用file保存session的文件路径

# 重新启动php-fpm以加载配置文件
[root@CentOS7 ~]#systemctl restart php-fpm

准备php测试页面

[root@CentOS7 ~]#mkdir /data/nginx/php
[root@CentOS7 ~]#vim /data/nginx/php/index.php
[root@CentOS7 ~]#cat /data/nginx/php/index.php
<?php
phpinfo();
?>

Nginx实现FastCGI

Nginx配置转发

Nginx安装完成之后默认生成了与fastcgi的相关配置文件,一般保存在nginx的安装路径的conf目录当中,比如/apps/nginx/conf/fastcgi.conf、/apps/nginx/conf/fastcgi_params。

[root@CentOS7 ~]#vim /apps/nginx/conf.d/pc.conf
[root@CentOS7 ~]#cat /apps/nginx/conf.d/pc.conf   # 在指定文件配置fastcgi
server {
  listen 80;
  server_name www.darius.com;
  charset utf-8;
  error_log /apps/nginx/logs/www_darius_com_error.log;
  access_log /apps/nginx/logs/www_darius_com_access.log access_json;
  location ~ \.php$ {
    root /data/nginx/php;    # $document_root调用root目录
    fastcgi_pass 127.0.0.1:9000;
    fastcgi_index index.php;
    #fastcgi_param SCRIPT_FILENAME /data/nginx/php$fastcgi_script_name;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;    # 如果SCRIPT_FILENAME是绝对路径则可以省略root /data/nginx/php;
    include fastcgi_params;
  }
}

[root@CentOS7 ~]#nginx -t
nginx: the configuration file /apps/nginx/conf/nginx.conf syntax is ok
nginx: configuration file /apps/nginx/conf/nginx.conf test is successful
[root@CentOS7 ~]#nginx -s reload

访问验证php测试页面

访问配置文件里面指定的路径,会返回php-fpm的当前运行状态。

Nginx配置

  location ~ ^/(pm_status|ping)$ {
    fastcgi_pass 127.0.0.1:9000;
    fastcgi_param PATH_TRANSLATED $document_root$fastcgi_script_name;
    include fastcgi_params;
  }

重启Nginx并测试

[root@CentOS7 ~]#nginx -t
nginx: the configuration file /apps/nginx/conf/nginx.conf syntax is ok
nginx: configuration file /apps/nginx/conf/nginx.conf test is successful
[root@CentOS7 ~]#nginx -s reload

[root@CentOS7 ~]#curl http://www.darius.com/pm_status
pool:                 www
process manager:      dynamic
start time:           02/Jun/2019:11:20:03 +0800
start since:          7
accepted conn:        1
listen queue:         0
max listen queue:     0
listen queue len:     128
idle processes:       99
active processes:     1
total processes:      100
max active processes: 1
max children reached: 0
slow requests:        0

[root@CentOS7 ~]#curl http://www.darius.com/ping
ping-pong
full格式状态页

Nginx实现FastCGI

html格式状态页

Nginx实现FastCGI

json格式状态页

Nginx实现FastCGI

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章