apache php的几种运行方式

摘要:PHP的所有应用程序都是通过WEB服务器(如IIS或Apache)和PHP引擎程序解释执行完成的, 工作过程 (1)当用户在浏览器地址中输入要访问的PHP页面文件名,然后回车就会触发这个PHP请求,并将请求传送化支持PHP的WEB服务器。 (2)WEB服务器接受这个请求,并根据其后缀进行判断如果是一个PHP请求,WEB服务器从硬盘或内存中取出用户要访问的PHP应用程序,并将其发送给 PHP引

apache php的几种运行方式,by 5lulu.com

 

PHP的所有应用程序都是通过WEB服务器(如IIS或Apache)和PHP引擎程序解释执行完成的,

工作过程

(1)当用户在浏览器地址中输入要访问的PHP页面文件名,然后回车就会触发这个PHP请求,并将请求传送化支持PHP的WEB服务器。
(2)WEB服务器接受这个请求,并根据其后缀进行判断如果是一个PHP请求,WEB服务器从硬盘或内存中取出用户要访问的PHP应用程序,并将其发送给 PHP引擎程序。
(3)PHP引擎程序将会对WEB服务器传送过来的文件从头到尾进行扫描并根据命令从后台读取,处理数据,并动态地生成相应的HTML页面。
(4)PHP引擎将生成HTML页面返回给WEB服务器。WEB服务器再将HTML页面返回给客户端浏览器。

php本身是一个php代码的脚本执行程序,运行方式是指其运行的方法。整理归纳为一下五种方法:

模块加载运行方式 (Apache) CGI运行方式 (Apache) FastCGI运行方式 (几乎通用Apache nginx lighttp) ISAPI运行方式 (window下Apache) cli运行方式 (就是命令行)

前四种是提供给web服务器来处理php代码文件,其中模块加载的方式其实是最快的的,但FastCGI配合nginx WEB服务是目前的主流,下面主要配合Apache做说明。

1模块加载运行方式

以模块加载的方式运行,其实就是将PHP集成到web服务器,以同一个进程运行。
此运行模式在使用apache服务器经常使用,通过加载模块(linux SO,window DLL)中,PHP是与Web服务器(Apache)一起启动并运行的,是apache在CGI的基础上进行的一种扩展,加快PHP的运行效率。

以linux为例编译PHP,在./configure步骤需要指定--with-apxs2=/path/to/apache/bin/apxs表示告诉编译器通过Apache的mod_php5/apxs来提供对PHP5的解析。

在make install的时候我们会看到将动态链接库libphp5.so(Apache模块)拷贝到apache2的安装目录的modules目录下(编译Apache 时要带--enable-modules=so,不实际编译模块但允许加载模块),然后在httpd.conf配置文件中添加LoadModule语句来动态将libphp5.so 模块加载进来,从而实现Apache对php的支持。

LoadModule php5_module /path/to/module/modules/libphp5.so//windows下载PHP一般为php5apache2_2.dll PHPinidir "/path/to/php.ini"
DirectoryIndex index.html index.php
AddType application/x-httpd-php .php

PHP作为Apache模块,Apache服务器在系统启动后,预先生成多个进程副本驻留在内存中,一旦有请求出现,就立即使用这些空余的子进程进行处理,这样就不存在生成子进程造成的延迟了。这些服务器副本在处理完一次HTTP请求之后并不立即退出,而是停留在计算机中等待下次请求。对于客户浏览器的请求反应更快,性能较高。

2CGI运行方式

CGI即通用网关接口(Common Gateway Interface),它是一段程序,通俗的讲CGI就象是一座桥,把网页和WEB服务器中的执行程序连接起来,它把HTML接收的指令传递给服务器的执行程序,再把服务器执行程序的结果返还给HTML页。CGI 的跨平台性能极佳,几乎可以在任何操作系统上实现。

CGI方式在遇到连接请求(用户 请求)先要创建cgi的子进程,激活一个CGI进程,然后处理请求,处理完后结束这个子进程。这就是fork-and-execute模式。所以用cgi方式的服务器有多少连接请求就会有多少cgi子进程,子进程反复加载是cgi性能低下的主要原因。都会当用户请求数量非常多时,会大量挤占系统的资源如内 存,CPU时间等,造成效能低下。

修改PHP配置php.ini

cgi.force_redirect = 0 //本来是 1 并且去掉注释符号;

修改apache的配置,去掉原来的模块配置

AddType application/x-httpd-php .php
LoadModule php5_module "C:/php5/php5apache2_2.dll"
PHPinidir "C:/php5/php.ini"

加入以下配置

AddHandler cgi-script

然后在网站cgi-bin目录下新建一个cgi文件test.cgi编写如下代码:

#!/path/to/php/php-cgi(.exe) <? php php phpinfo(); ?>

在上述情况中,你可以想象CGI通常有多慢。每一个Web请求PHP都必须重新解析php.ini、重新载入全部扩展并重初始化全部数据结构。

3FastCGI运行方式

fast-cgi 是cgi的升级版本,FastCGI像是一个常驻(long-live)型的CGI,它可以一直执行着,只要激活后,不会每次都要花费时间去fork一 次。PHP使用PHP-FPM(FastCGI Process Manager),全称PHP FastCGI进程管理器进行管理。

php 5.3.29之后自带FPM,编译时带--enable-fpm,之前需另外加载模块。

PHP的fastcig方式运行,如果是Apache服务器首先需要去下载fastcgi模块,默认是没有带这个模块的,而cgi是自带的;下载地址http://httpd.apache.org/mod_fcgid/;解压复制其中的mod_fcgid.so和mod_fcgid.pdb,接下来做如下的配置:

LoadModule fcgid_module modules/mod_fcgid.so // line 128追加
FcgidInitialEnv PHPRC "c:/php5" //php配置文件 line 129追加 AddHandler
fcgid-script .php //添加句柄 即后缀 什么样的文件需要fastcgi解释 line 407追加 FcgidWrapper
"c:/php5/php-cgi.exe" .php //解释器路径 line 408 Options Indexes
FollowSymLinks ExecCGI //line 221 追加 ExecCGI 意思是目录允许执行CGI脚本

使用FastCGI,所有这些都只在进程启动时发生一次。一个额外的 好处是,持续数据库连接(Persistent database connection)可以工作。

4ISAPI运行方式

ISAPI即Internet Server Application Program Interface,是微软提供的一套面向Internet服务的API接口,一个ISAPI的DLL,可以在被用户请求激活后长驻内存,等待用户的另一个请求,还可以在一个DLL里设置多个用户请求处理函数,此外,ISAPI的DLL应用程序和WWW服务器处于同一个进程中,效率要显著高于CGI。(由于微软的排他性,只能运行于windows环境)

5cli运行方式

cli是php的命令行运行模式,大家经常会使用它,但是可能并没有注意到(例如:我们在linux下经常使用 “php -m”查找PHP安装了那些扩展就是PHP命令行运行模式;有兴趣的同学可以输入php -h去深入研究该运行模式)

一. 可以配置Apache将PHP解释器作为CGI脚本,或者作为Apache本身的一个模块(mod_php),还有就是FastCGI模式来运行。

CGI是比较原始的方式,Apache默认是以第二种方式运行PHP的,而配置FastCGI模式需要下载安装相关的包。

性能上,CGI模式每一次接到请求会调用php.exe,解析php.ini,加载DLL等,速度自然慢。

后两种方式会在Web程序启动时就作为启动,等待请求;其中FastCGI下,实现了类似连接池的技术特性,保持了对后台的连接,请求到来即可使用,结束即断开准备与下一个请求连接。

实际中,有人认为FastCGI比mod_php模式慢,有认为前者是后者性能的80%的,还有人测试后认为:对于匿名访问,前者约为后者性能的63%,认证访问时也低了18%。一般认为,FastCGI是适用于高并发使用场景下的,同时使用FastCGI可以使得程序在Web Server产品与代码两端都具有更好的选择自由度。

二.Nginx默认不支持CGI模式,它是以FastCGI方式运行的。所以使用Nginx+PHP就是直接配置为FastCGI模式。

For the most part, lack of CGI support in Nginx is not an issue and actually has an important side-benefit: because Nginx cannot directly execute external programs (CGI), a malicious person can\'t trick your system into uploading and executing an arbitrary script.

php在apache中一共有三种工作方式:CGI模式、Apache模块DLL、FastCGI模式)

以下分别比较:

1. CGI模式与模块模式比较:

php在apache中两种工作方式的区别(CGI模式、Apache模块DLL)
这两种工作方式的安装:

PHP在Apache 2.0中的CGI方式
ScriptAlias /php/ "c:/php/"
AddType application/x-httpd-php .php

#对PHP 4用这行
Action application/x-httpd-php "/php/php.exe"

#对PHP 5用这行
Action application/x-httpd-php "/php/php-cgi.exe"
PHP在Apache 2.0中的模块方式
#对PHP 4用这两行:
LoadModule php4_module "c:/php/php4apache2.dll"
#别忘了从sapi目录中把php4apache2.dll拷贝出来!
AddType application/x-httpd-php .php
#对PHP 5用这两行:
LoadModule php5_module "c:/php/php5apache2.dll"
AddType application/x-httpd-php .php

#配置php.ini的路径
PHPIniDir "C:/php"

这两种工作方式的区别:
在CGI模式下,如果客户机请求一个php文件,Web服务器就调用php.exe去解释这个文件,然后再把解释的结果以网页的形式返回给客户机;
而在模块化(DLL)中,PHP是与Web服务器一起启动并运行的。
所以从某种角度上来说,以apache模块方式安装的PHP4有着比CGI模式更好的安全性以及更好的执行效率和速度。

2. FastCGI运行模式分析:

FastCGI的工作原理是:

(1)、Web Server启动时载入FastCGI进程管理器【PHP的FastCGI进程管理器是PHP-FPM(php-FastCGI Process Manager)】(IIS ISAPI或Apache Module);
(2)、FastCGI进程管理器自身初始化,启动多个CGI解释器进程(在任务管理器中可见多个php-cgi.exe)并等待来自Web Server的连接。
(3)、当客户端请求到达Web Server时,FastCGI进程管理器选择并连接到一个CGI解释器。Web server将CGI环境变量和标准输入发送到FastCGI子进程php-cgi.exe。
(4)、FastCGI子进程完成处理后将标准输出和错误信息从同一连接返回Web Server。当FastCGI子进程关闭连接时,请求便告处理完成。FastCGI子进程接着等待并处理来自FastCGI进程管理器(运行在WebServer中)的下一个连接。在正常的CGI模式中,php-cgi.exe在此便退出了。

在上述情况中,你可以想象CGI通常有多慢。每一个Web请求PHP都必须重新解析php.ini、重新载入全部dll扩展并重初始化全部数据结构。使用FastCGI,所有这些都只在进程启动时发生一次。一个额外的好处是,持续数据库连接(Persistent database connection)可以工作。

3.为什么要使用FastCGI,而不是多线程CGI解释器?
这可能出于多方面的考虑,例如:
(1)、你无论如何也不能在windows平台上稳定的使用多线程CGI解释器,无论是IIS ISAPI方式还是APACHE Module方式,它们总是运行一段时间就崩溃了。奇怪么?但是确实存在这样的情况!
当然,也有很多时候你能够稳定的使用多线程CGI解释器,但是,你有可能发现网页有时候会出现错误,无论如何也找不到原因,而换用FastCGI方式时这种错误的概率会大大的降低。我也不清楚这是为什么,我想独立地址空间的CGI解释器可能终究比共享地址空间的形式来得稳定一点点。
(2)、性能!性能?可能么,难道FastCGI比多线程CGI解释器更快?但有时候确实是这样,只有测试一下你的网站,才能最后下结论。原因嘛,我觉得很难讲,但有资料说在Zend WinEnabler的时代,Zend原来也是建议在Windows平台下使用FastCGI而不是IIS ISAPI或Apache Module,不过现在Zend已经不做这个产品了。

4. FastCGI模式运行PHP的优点

以FastCGI模式运行PHP有几个主要的好处。首先就是PHP出错的时候不会搞垮Apache,只是PHP自己的进程当掉(但FastCGI会立即重新启动一个新PHP进程来代替当掉的进程)。其次FastCGI模式运行PHP比ISAPI模式性能更好(我本来用ApacheBench进行了测试,但忘了保存结果,大家有兴趣可以自己测试)。

最后,就是可以同时运行PHP5和PHP4。参考下面的配置文件,分别建立了两个虚拟主机,其中一个使用PHP5,另一个使用PHP4。

LoadModule fastcgi_module modules/mod_fastcgi-2.4.2-AP13.dll ScriptAlias /fcgi-php5/ "d:/usr/local/php-5.0.4/" FastCgiServer "d:/usr/local/php-5.0.4/php-cgi.exe" -processes 3 ScriptAlias /fcgi-php4/ "d:/usr/local/php-4.3.11/" FastCgiServer "d:/usr/local/php-4.3.11/php.exe" Listen 80 NameVirtualHost *:80 DocumentRoot d:/www Options Indexes FollowSymlinks MultiViews ServerName php5.localhost AddType application/x-httpd-fastphp5 .php Action application/x-httpd-fastphp5 "/fcgi-php5/php-cgi.exe" IndexOptions FancyIndexing FoldersFirst Options Indexes FollowSymLinks MultiViews AllowOverride None Order allow,deny Allow from all Listen 8080 NameVirtualHost *:8080 DocumentRoot d:/www Options Indexes FollowSymlinks MultiViews ServerName php4.localhost AddType application/x-httpd-fastphp4 .php Action application/x-httpd-fastphp4 "/fcgi-php4/php.exe" Options Indexes FollowSymLinks MultiViews AllowOverride None Order allow,deny Allow from all

 

使用上面的配置,访问http://localhost/就使用PHP5,而访问http://localhost:8080/就使用PHP4。所以只要合理配置,就可以让不同的虚拟主机使用不同版本的PHP。

FastCGI模式的一些缺点:

说完了好处,也来说说缺点。从我的实际使用来看,用FastCGI模式更适合生产环境的服务器。但对于开发用机器来说就不太合适。因为当使用Zend Studio调试程序时,由于FastCGI会认为PHP进程超时,从而在页面返回500错误。这一点让人非常恼火,所以我在开发机器上还是换回了ISAPI模式。

最后,在Windows中以FastCGI模式存在潜在的安

二、php在nginx中运行模式(nginx+PHP-FPM )目前理想选择

使用FastCGI方式现在常见的有两种stack:ligthttpd+spawn-fcgi;另外一种是nginx+PHP-FPM(也可以用spawn-fcgi)。

(1)如上面所说该两种结构都采用FastCGI对PHP支持,因此HTTPServer完全解放出来,可以更好地进行响应和并发处理。因此lighttpd和nginx都有small, but powerful和efficient的美誉。

(2)该两者还可以分出一个好坏来,spawn-fcgi由于是lighttpd的一部分,因此安装了lighttpd一般就会使用spawn-fcgi对php支持,但是目前有用户说ligttpd的spwan-fcgi在高并发访问的时候,会出现上面说的内存泄漏甚至自动重启fastcgi。即:PHP脚本处理器当机,这个时候如果用户访问的话,可能就会出现白页(即PHP不能被解析或者出错)。

另一个:首先nginx不像lighttpd本身含带了fastcgi(spawn-fcgi),因此它完全是轻量级的,必须借助第三方的FastCGI处理器才可以对PHP进行解析,因此其实这样看来nginx是非常灵活的,它可以和任何第三方提供解析的处理器实现连接从而实现对PHP的解析(在nginx.conf中很容易设置)。

nginx可以使用spwan-fcgi(需要一同安装lighttpd,但是需要为nginx避开端口,一些较早的blog有这方面安装的教程),但是由于spawn-fcgi具有上面所述的用户逐渐发现的缺陷,现在慢慢减少使用nginx+spawn-fcgi组合了。

c.由于spawn-fcgi的缺陷,现在出现了新的第三方(目前还是,听说正在努力不久将来加入到PHP core中)的PHP的FastCGI处理器,叫做PHP-FPM(具体可以google)。它和spawn-fcgi比较起来有如下优点:

由于它是作为PHP的patch补丁来开发的,安装的时候需要和php源码一起编译,也就是说编译到php core中了,因此在性能方面要优秀一些;

同时它在处理高并发方面也优于spawn-fcgi,至少不会自动重启fastcgi处理器。具体采用的算法和设计可以google了解。

因此,如上所说由于nginx的轻量和灵活性,因此目前性能优越,越来越多人逐渐使用这个组合:nginx+PHP/PHP-FPM

IIS+ ISAPI模式

这种模式适合开发环境中,生产环境中用的较少。

6总结

目前在HTTPServer这块基本可以看到有三种stack比较流行:

(1)Apache+mod_php5
(2)lighttp+spawn-fcgi
(3)nginx+PHP-FPM

三者后两者性能可能稍优,但是Apache由于有丰富的模块和功能,目前来说仍旧是老大。有人测试nginx+PHP-FPM在高并发情况下可能会达到Apache+mod_php5的5~10倍,现在nginx+PHP-FPM使用的人越来越多。