如何正确配置Nginx+PHP:避免常见错误与安全漏洞的实用指南
对于许多人来说,配置的Nginx+PHP无非是搜索教程,然后复制和粘贴。听起来好像没有问题。不幸的是,实际上,很长一段时间以来,互联网本身上的许多信息一直在失业,并且存在许多漏洞。如果您不要求它,您将盲目复制并粘贴它。

假设我们使用PHP实现前端控制器,或者直接的入口是:将PHP请求发送到同一文件,然后在此文件中分析“ request_uri”以实现路线。
目前,许多教程将教您配置NGINX+PHP:
服务器 {
听80;
server_name foo.com;
root /path;
地点 / {
索引index.html index.htm index.php;
if(!-e $ request_filename){
改写。 /index.php last;
本地〜\ .php $ {
包括fastcgi_params;
fastcgi_param script_filename /path $ fastcgi_script_name;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
其中有很多错误,或者至少有一个不良的味道,让我们看看可以找到多少个。
割草
我们需要了解Nginx配置文件中指令的继承关系:Nginx配置文件分为许多部分。从外部到内部的常见是“ http”,“ server”,“ local”等。 (有例外,请参阅有关详细信息)。
参考:介绍NGINX配置继承模型
割草
让我们从“索引”指令开始。在问题的配置中,它在“本地”中定义:
地点 / {
索引index.html index.htm index.php;
将来需要加入新的“位置”后,重复的“索引”指令将不可避免,并且随着继承关系,“索引”指令将在所有“位置”中生效。
参考:nginx陷阱
割草
接下来,看一下“如果”指令,说这是对Nginx指令的最误会。
if(!-e $ request_filename){
改写。 /index.php last;
许多人喜欢使用“ IF”指令进行一系列检查,但这实际上是“ try_files”指令的职责:
try_files $ uri $ uri / / index.php;
此外,初学者经常认为“如果”指令是内核级别的指令,但实际上它是重写模块的一部分。此外,NGINX配置实际上是一种语句,而不是一个过程,因此它应该是和谐的,因此,当混合了非螺纹模块的指令时它是和谐的,结果可能是您希望的。
参考:ifisevil和nginx如何本地
割草
让我们看一下“ fastcgi_params”配置文件:
包括fastcgi_params;
NGINX有两个FastCGI配置文件,即“ FastCGI_Params”和“ fastcgi.conf”。他们没有太大的不同。唯一的区别是,后者的定义是“ script_filename”,而不是前者:
fastcgi_param script_filename $ document_root $ fastcgi_script_name;
注意:$ document_root和$ fastcgi_script_name之间没有/没有/。
最初Nginx只有“ fastcgi_params”。后来,发现许多人在定义“ script_filename”时使用了硬编码,因此他们介绍了“ fastcgi.conf”来调节用法。
但是,有一个问题:为什么必须介绍一个新的配置文件而不是修改旧配置文件?这是因为“ fastcgi_param”指令是一种数组类型,与普通指令相同:内层被外层代替;与普通说明不同:当在同一级别使用时,它是新的,而不是更换的。换句话说,如果您在同一级别上两次定义“ script_filename”,则将它们发送到后端,这可能会导致一些潜在的问题。为了避免这种情况,引入了一个新的配置文件。
参考:fastcgi_params vitus fastcgi.conf - nginx配置历史记录
割草
此外,我们需要考虑一个安全问题:当PHP打开“ CGI.FIX_PATHINFO”时,PHP可能会使用错误的文件类型作为PHP文件进行分析。如果在同一服务器上安装了NGINX和PHP,则最简单的解决方案是使用“ Try_files”指令来制作过滤器:
try_files $ uri = 404;
参考:NGINX文件类型错误分析漏洞
割草
根据先前的分析,改进的版本比开始版本更令人耳目一新:
服务器 {
听80;
server_name foo.com;
根 /路径;
索引index.html index.htm index.php;
地点 / {
try_files $ uri $ uri / / index.php;
本地〜\ .php $ {
try_files $ uri = 404;
包括fastcgi.conf;
fastcgi_pass 127.0.0.1:9000;
实际上,存在一些缺陷,主要是“ try_files”和“ fastcgi_split_path_info”。尽管可以解决,但该方案很丑陋,所以我不太说。如果您有兴趣,可以参考问题描述。
补充:因为“位置”受到限制,因此“ fastcgi_index”实际上不是必需的。
原始资料来源:huoting Note
原始链接: