Nginx代理不正确的fastcgi_script_name用于静态文件

时间:2016-06-12 11:35:15

标签: php nginx yii2-advanced-app

server {
    listen loc.app:80;    

    root /app/frontend/web;

    index index.php;

    location / {        
        try_files $uri $uri/ /index.php$is_args$args;
    }

    location ~ ^/admin {
        proxy_pass http://127.0.0.1:81;     
    }

    location ~* \.php$ {    
        #php conf
    }                    
}

server {
    listen 127.0.0.1:81;

    root /app/backend/web;

    index index.php;

    location / {        
        try_files $uri $uri/ /index.php$is_args$args;
    }

    location ~ \.(js|css)$ {    
        echo "$document_root"; # /app/backend/web;

        echo "$fastcgi_script_name"; # /admin/assets/569a8b41/css/bootstrap.css         
        ############################## ISSUE ##############################
        # $fastcgi_script_name must be /assets/569a8b41/css/bootstrap.css #
        ###################################################################
    }

    location ~* \.php$ {    
        #php conf
    }
}

http://loc.app/admin - 确定
http://loc.app/admin/style.css - 返回404

如何强制nginx正确处理静态文件?

3 个答案:

答案 0 :(得分:4)

js和css等静态文件与fastcgi无关。

但是,由于该文件位于/admin/assets/569a8b41/css,但您的conf有/app/backend/web作为文档根目录,因此永远不会找到它,因为您要求nginx查找,所以您将始终获得404 /app/backend/web/admin/assets/569a8b41/css/bootstrap.css不存在。

由于您的设置的复杂性,您可以添加另一个仅内部位置块来处理请求的实际服务,并从原始位置块重定向到此。

location ~ /admin/assets/569a8b41 {
    root /admin/assets/569a8b41;        
}
location ~ ^/admin/(.+)\.(js|css)$ {    
    rewrite ^/admin/(.+)\.css$ /admin/assets/569a8b41/css/$1.css last;
    rewrite ^/admin/(.+)\.js$ /admin/assets/569a8b41/js/$1.js last;
}

http://loc.app/admin/style.css之类的请求会在/admin/assets/569a8b41/css/style.css中查看,如果存在,则会提供此信息。

请注意,这假设您在css下有单独的js/admin/assets/569a8b41个文件夹。

答案 1 :(得分:1)

如果您使用〜符号,则表示以下模式是正则表达式,因此在这种情况下,nginx将采用所有URI并传递它,因此您需要摆脱后端配置中的“admin”部分,我很高兴/ app / backend / web在这条路径上只有管理面板运行,所以这里是我的建议:

class User
  # …

  def lock_access_based_on_superadmin_limit!
    if failed_attempts >= superadmin.maximum_attempts
      lock_access! unless access_locked?
    end
  end
end

将此更改为:

location ~ ^/admin {
    proxy_pass http://127.0.0.1:81;     
}

在这种情况下,你的style.css文件位于/ app / backend / web path

当你打电话时

loc.app/admin/style.js

在后台nginx将发出此请求127.0.0.1:81/style.css 如果你在/ app / backend / web中有一些css目录,那么你的主网址应该是loc.app/admin/css/style.js => 127.0.0.1:81/css/style.css文件应该在/app/backend/web/css/style.css

我希望这能给出一个想法。

答案 2 :(得分:0)

proxy_pass获取请求的uri并将其发送到上游服务器。如果uri在上游服务器上看起来不同,那么在将它传递给代理之前应该rewrite uri(例如:摆脱/admin部分)。但是对于你的情况来说这可能不是一个好主意,因为在我看来你也需要你的后端php应用程序的/admin部分才能工作,因为它似乎被宣告为你的php框架中的路由。因此,对您而言,最好的解决方案可能是仅删除静态文件的/admin部分。更新后端服务器的nginx配置,使其包含以下内容:

location ~* \.(jpg|jpeg|gif|png|bmp|ico|pdf|flv|swf|exe|html|htm|txt|css|js) {
    rewrite ^/admin/(.*) /$1 last;
}

请务必删除您添加的echo