首页 > 解决方案 > nginx 配置 / 文件夹从与 / 不同的路径运行

问题描述

我在从与主网站不同的路径运行 /folder 时遇到问题。

该部分的我的 nginx.conf 如下所示:

        location ~ \.php$ {
            try_files               $uri = 404;
            fastcgi_split_path_info ^(.+\.php)(/.+)$;
        fastcgi_param       SCRIPT_FILENAME $request_filename;
            fastcgi_pass            unix:/var/run/php/php7.2-fpm.sock;
            fastcgi_index           index.php;
           include                 fastcgi_params;
            include                 fastcgi.conf;
    }


location ~ /folder {
        alias /srv/http/folder;
    try_files $uri $uri/ @folder;

    location ~ \.php$ {
                fastcgi_param SCRIPT_FILENAME $request_filename;
                fastcgi_pass   unix:/var/run/php/php7.2-fpm.sock;
                include        fastcgi.conf;
        }
}

location @folder {
    rewrite /folder/(.*)$ /folder/index.php?/$1 last;
}

在 error.log 中,我可以看到以下内容:

2020/06/03 09:05:26 [error] 25966#25966: *1 FastCGI sent in stderr: "Primary script unknown" while reading response header from upstream, client: 172.21.2.46, server: example.com, request: "GET /folder/xxx_v6.15.11/Resources/images/redcaplogo.gif HTTP/1.1", upstream: "fastcgi://unix:/var/run/php/php7.2-fpm.sock:", host: "example.com"

任何建议如何解决这个问题?

标签: nginxsubdirectory

解决方案


正则表达式位置从第一个到最后一个匹配,第一个找到的匹配由 nginx 处理。当您收到对 的请求时/folder/script.php,它由第一个位置块处理。尝试交换这两个位置。另外,为什么不包括fastcgi_params在第二个位置块中?

更新

我做了一些调试,让我们看看你的代码(假设位置块已经交换):

location ~ /folder {
    alias /srv/http/folder;
    try_files $uri $uri/ @folder;

    location ~ \.php$ {
        fastcgi_param  SCRIPT_FILENAME $request_filename;
        fastcgi_pass   unix:/var/run/php/php7.2-fpm.sock;
        include        fastcgi_params;
        include        fastcgi.conf;
    }
}

location ~ \.php$ {
    try_files               $uri =404;
    fastcgi_split_path_info ^(.+\.php)(/.+)$;
    fastcgi_param           SCRIPT_FILENAME $request_filename;
    fastcgi_pass            unix:/var/run/php/php7.2-fpm.sock;
    fastcgi_index           index.php;
    include                 fastcgi_params;
    include                 fastcgi.conf;
}

location @folder {
    rewrite /folder/(.*)$ /folder/index.php?/$1 last;
}

如果我们收到一个请求/folder/some/path(并且里面没有some/path文件或目录folder),在嵌套位置内部 nginx 变量将具有以下值:

  • $request_filename/some/path: 空字符串(目录中没有真正的文件或文件夹folder);
  • $uri: /folder/check.php;
  • $document_root: /srv/http/folder.

如果我们收到一个请求/folder/some/path/script.php(并且有一个具有此名称的真实 PHP 脚本),在嵌套位置内部 nginx 变量将具有以下值:

  • $request_filename: /srv/http/folder/some/path/script.php;
  • $uri: /folder/some/path/check.php;
  • $document_root: /srv/http/folder.

此外,当您从文件夹中获取静态资源请求时,例如/folder/some/path/static.css,该try_files $uri ...指令将folder/some/path/static.css在目录中搜索文件/srv/http/folder,从而检查/srv/http/folder/folder/some/path/static.css文件是否存在。

在目录中获取文件子路径的一种可能解决方案folder

location ~ ^/folder(?<subpath>.*) {
    alias /srv/http/folder;
    try_files $subpath $subpath/ @folder;

    location ~ \.php$ {
        fastcgi_param  SCRIPT_FILENAME $document_root$subpath;
        fastcgi_pass   unix:/var/run/php/php7.2-fpm.sock;
        include        fastcgi_params;
        include        fastcgi.conf;
    }
}

location ~ \.php$ {
    try_files               $uri =404;
    fastcgi_split_path_info ^(.+\.php)(/.+)$;
    fastcgi_param           SCRIPT_FILENAME $request_filename;
    fastcgi_pass            unix:/var/run/php/php7.2-fpm.sock;
    fastcgi_index           index.php;
    include                 fastcgi_params;
    include                 fastcgi.conf;
}

location @folder {
    rewrite ^/folder/(.*)$ /folder/index.php?/$1 last;
}

如果您的真实目录名称与您的URI 前缀folder相同,这可以简化:/folder

location ~ ^/folder {
    root /srv/http;
    try_files $uri $uri/ @folder;

    location ~ \.php$ {
        fastcgi_param  SCRIPT_FILENAME $document_root$uri;
        fastcgi_pass   unix:/var/run/php/php7.2-fpm.sock;
        include        fastcgi_params;
        include        fastcgi.conf;
    }
}

...

正如 nginx 文档所述

当 location 与指令值的最后一部分匹配时:

location /images/ {
  alias /data/w3/images/;
}

最好使用 root 指令:

location /images/ {
  root /data/w3;
}

推荐阅读