Nginx反向代理功能-实现FastCGI实战案例
Nginx反向代理功能-实现FastCGI实战案例
作者:尹正杰
版权声明:原创作品,谢绝转载!否则将追究法律责任。
一.FastCGI概述
1>.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服务器之间传递信息的标准化接口。
2>.为什么FastCGI
CGI协议虽然解决了语言解析器和seb server之间通讯的问题,但是它的效率很低,因为web server每收到一个请求都会创建一个CGI进程,PHP解析器都会解析php.ini文件,初始化环境,请求结束的时候再关闭进程,对于每一个创建的CGI进程都会执行这些操作,所以效率很低,而FastCGI是用来提高CGI性能的,FastCGI每次处理完请求之后不会关闭掉进程,而是保留这个进程,使这个进程可以处理多个请求。这样的话每个请求都不用再重新创建一个进程了,大大提升了处理效率。
3>.什么是PHP-FPM
PHP-FPM(FastCGI Process Manager:FastCGI进程管理器)是一个实现了Fastcgi的程序,并且提供进程管理的功能。进程包括master进程和worker进程。master进程只有一个,负责监听端口,接受来自webserver的请求。worker进程一般会有多个,每个进程中会嵌入一个PHP解析器,进行PHP代码的处理。
二.Nginx与php-fpm在同一服务器实战案例
1>.安装php相关软件环境
[root@node101.yinzhengjie.org.cn ~]# yum -y install php-fpm php-mysql Loaded plugins: fastestmirror Loading mirror speeds from cached hostfile epel/x86_64/metalink | 8.7 kB 00:00:00 * base: mirrors.tuna.tsinghua.edu.cn * epel: mirrors.tuna.tsinghua.edu.cn * extras: mirror.bit.edu.cn * updates: mirrors.tuna.tsinghua.edu.cn base | 3.6 kB 00:00:00 epel | 5.4 kB 00:00:00 extras | 2.9 kB 00:00:00 updates | 2.9 kB 00:00:00 (1/3): epel/x86_64/group_gz | 90 kB 00:00:00 (2/3): epel/x86_64/updateinfo | 1.0 MB 00:00:00 (3/3): epel/x86_64/primary_db | 6.9 MB 00:00:00 Resolving Dependencies --> Running transaction check ---> Package php-fpm.x86_64 0:5.4.16-46.1.el7_7 will be installed --> Processing Dependency: php-common(x86-64) = 5.4.16-46.1.el7_7 for package: php-fpm-5.4.16-46.1.el7_7.x86_64 ---> Package php-mysql.x86_64 0:5.4.16-46.1.el7_7 will be installed --> Processing Dependency: php-pdo(x86-64) = 5.4.16-46.1.el7_7 for package: php-mysql-5.4.16-46.1.el7_7.x86_64 --> Running transaction check ---> Package php-common.x86_64 0:5.4.16-46.1.el7_7 will be installed --> Processing Dependency: libzip.so.2()(64bit) for package: php-common-5.4.16-46.1.el7_7.x86_64 ---> Package php-pdo.x86_64 0:5.4.16-46.1.el7_7 will be installed --> Running transaction check ---> Package libzip.x86_64 0:0.10.1-8.el7 will be installed --> Finished Dependency Resolution Dependencies Resolved ============================================================================================================================================================================ Package Arch Version Repository Size ============================================================================================================================================================================ Installing: php-fpm x86_64 5.4.16-46.1.el7_7 updates 1.4 M php-mysql x86_64 5.4.16-46.1.el7_7 updates 101 k Installing for dependencies: libzip x86_64 0.10.1-8.el7 base 48 k php-common x86_64 5.4.16-46.1.el7_7 updates 565 k php-pdo x86_64 5.4.16-46.1.el7_7 updates 99 k Transaction Summary ============================================================================================================================================================================ Install 2 Packages (+3 Dependent packages) Total download size: 2.2 M Installed size: 8.8 M Downloading packages: (1/5): libzip-0.10.1-8.el7.x86_64.rpm | 48 kB 00:00:00 (2/5): php-common-5.4.16-46.1.el7_7.x86_64.rpm | 565 kB 00:00:00 (3/5): php-mysql-5.4.16-46.1.el7_7.x86_64.rpm | 101 kB 00:00:00 php-pdo-5.4.16-46.1.el7_7.x86_ FAILED http://mirror.lzu.edu.cn/centos/7.7.1908/updates/x86_64/Packages/php-pdo-5.4.16-46.1.el7_7.x86_64.rpm: [Errno 14] curl#56 - "Recv failure: Connection reset by peer":-- ETA Trying other mirror. (4/5): php-fpm-5.4.16-46.1.el7_7.x86_64.rpm | 1.4 MB 00:00:06 (5/5): php-pdo-5.4.16-46.1.el7_7.x86_64.rpm | 99 kB 00:00:05 ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------- Total 358 kB/s | 2.2 MB 00:00:06 Running transaction check Running transaction test Transaction test succeeded Running transaction Installing : libzip-0.10.1-8.el7.x86_64 1/5 Installing : php-common-5.4.16-46.1.el7_7.x86_64 2/5 Installing : php-pdo-5.4.16-46.1.el7_7.x86_64 3/5 Installing : php-mysql-5.4.16-46.1.el7_7.x86_64 4/5 Installing : php-fpm-5.4.16-46.1.el7_7.x86_64 5/5 Verifying : php-common-5.4.16-46.1.el7_7.x86_64 1/5 Verifying : libzip-0.10.1-8.el7.x86_64 2/5 Verifying : php-pdo-5.4.16-46.1.el7_7.x86_64 3/5 Verifying : php-mysql-5.4.16-46.1.el7_7.x86_64 4/5 Verifying : php-fpm-5.4.16-46.1.el7_7.x86_64 5/5 Installed: php-fpm.x86_64 0:5.4.16-46.1.el7_7 php-mysql.x86_64 0:5.4.16-46.1.el7_7 Dependency Installed: libzip.x86_64 0:0.10.1-8.el7 php-common.x86_64 0:5.4.16-46.1.el7_7 php-pdo.x86_64 0:5.4.16-46.1.el7_7 Complete! [root@node101.yinzhengjie.org.cn ~]#
2>. php相关参数优化
[root@node101.yinzhengjie.org.cn ~]# egrep -v "^;|^$|^ " /etc/php-fpm.d/www.conf #查看默认配置 [www] listen = 127.0.0.1:9000 #监听地址及IP地址 listen.allowed_clients = 127.0.0.1 #允许客户端从哪个源IP地址访问,要允许所有IP地址,行首加";"注释即可 user = apache #PHP-FPM启动的用户,会涉及到后期文件的权限问题 group = apache #PHP-FPM启动的组,会涉及到后期文件的权限问题 pm = dynamic #动态模块进程管理 pm.max_children = 50 #静态方式下开启的php-fpm进程数量,在动态模式下他限定php-fpm的最大进程数 pm.start_servers = 5 #动态模式下初始进程数,必须大于等于pm.min_spare_servers和小于等于pm.max_children的值 pm.min_spare_servers = 5 #最小空闲进程数 pm.max_spare_servers = 35 #最大空闲进程数 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 #php session保存方式及路径 php_value[session.save_path] = /var/lib/php/session #当时使用file保存session的文件路径 [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]# vim /etc/php-fpm.d/www.conf [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]# egrep -v "^;|^$|^ " /etc/php-fpm.d/www.conf #优化后的配置 [www] listen = 127.0.0.1:9000 listen.allowed_clients = 127.0.0.1 user = nginx group = nginx pm = dynamic pm.max_children = 500 pm.start_servers = 100 pm.min_spare_servers = 100 pm.max_spare_servers = 200 pm.max_requests = 500000 #进程累计请求回收值,会重新生成进程。 pm.status_path = /my_php_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 php_value[session.save_path] = /var/lib/php/session [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]#
3>.启动php
[root@node101.yinzhengjie.org.cn ~]# ss -ntl State Recv-Q Send-Q Local Address:Port Peer Address:Port LISTEN 0 128 *:22 *:* LISTEN 0 128 :::22 :::* [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]# systemctl start php-fpm [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]# ss -ntl State Recv-Q Send-Q Local Address:Port Peer Address:Port LISTEN 0 128 127.0.0.1:9000 *:* LISTEN 0 128 *:22 *:* LISTEN 0 128 :::22 :::* [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]#
4>.配置nginx转发php程序
[root@node101.yinzhengjie.org.cn ~]# cat /yinzhengjie/softwares/nginx/conf/nginx.conf worker_processes 4; worker_cpu_affinity 00000001 00000010 00000100 00001000; events { worker_connections 100000; use epoll; accept_mutex on; multi_accept on; } http { include mime.types; default_type text/html; server_tokens off; charset utf-8; log_format my_access_json '{"@timestamp":"$time_iso8601",' '"host":"$server_addr",' '"clientip":"$remote_addr",' '"size":$body_bytes_sent,' '"responsetime":$request_ti me,' '"upstreamtime":"$upstream_response_time",' '"upstreamhost":"$upstream_addr",' '"http_host":"$host",' '"uri":"$uri",' '"domain":"$host",' '"xff":"$http_x_forwarded_for",' '"referer":"$http_referer",' '"tcp_xff":"$proxy_protocol_addr",' '"http_user_agent":"$http_user_agent",' '"status":"$status"}'; access_log logs/access_json.log my_access_json; ssl_certificate /yinzhengjie/softwares/nginx/certs/www.yinzhengjie.org.cn.crt; ssl_certificate_key /yinzhengjie/softwares/nginx/certs/www.yinzhengjie.org.cn.key; ssl_session_cache shared:sslcache:20m; ssl_session_timeout 10m; include /yinzhengjie/softwares/nginx/conf.d/*.conf; } [root@node101.yinzhengjie.org.cn ~]# [root@node101.yinzhengjie.org.cn ~]# nginx -t nginx: the configuration file /yinzhengjie/softwares/nginx/conf/nginx.conf syntax is ok nginx: configuration file /yinzhengjie/softwares/nginx/conf/nginx.conf test is successful [root@node101.yinzhengjie.org.cn ~]#