Nginx – alias与root的区别

Nginx – alias与root的区别

root

nginx会在硬盘中查找:root指定路径+ 访问的uri

这里提一个遇到的坑,就是root和index顺序问题,当root在location外边被所有location使用时,index一定要放在root后面,如果放前面,则nginx会去找nginx安装时的那个index而不是root里的index,但如果root放在location内部,外边的index虽然在root前面,但是却不会导致这个问题。

以下是一个vue dist的nginx配置(root放在index之前)

server {
    listen 80;
    server_name www.vue-element-admin.com;

    charset utf-8;
    default_type text/html;

    root /Users/bruce/www/personal/vue-element-admin/dist;
    index index.html index.htm index.php

    access_log /usr/local/var/log/nginx/www.vue-element-admin.com.access.log;
    error_log /usr/local/var/log/nginx/www.vue-element-admin.com.error.log;

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

    location ~ .*\.(jpg|jpeg|png|gif)$ {
        valid_referers none blocked www.vue-element-admin.com;
        if ($invalid_referer) {
            return "502" "Invalid Referer";
        }
    }
}

alias

  1. 当无修饰符或使用^~修饰location匹配的uri时,nginx会在硬盘中查找:alias指定路径+访问的uri中location匹配的部分之后的路径(不包括开头的斜杠/)
  2. 当使用~~*修饰时,它不会查找任何文件,而会查找它本身指定的目录(即这样的配置是不行的,除非你要显示目录中的文件)。

关于uri的说明

假设我访问:http://www.test.com/static/html/index.html?aa=bb,则访问的uri为:/static/html/index.html,即除去协议(http://或https://)及域名www.test.com之外的部分即为uri(注意不包括参数)

实例测试

注意,要保证access_log、error_log、root或alias指定的目录要存在并且有可读权限。

server {
    listen 80;
    server_name www.test.com;

    access_log /usr/local/var/log/nginx/www.test.com.error.log combined;
    error_log /usr/local/var/log/nginx/www.test.com.error.log error;

    location ^~ /static/ {
        root /Users/bruce/www/personal/test/static;
        index index.html;
        return 502 $request_filename;
    }
}

或者location不用修饰符:

location /static/ {
    root /Users/bruce/www/personal/test/static/;
    index index.html;
    return 502 $request_filename;
}

当使用root时:
访问:http://www.test.com/static/html/index.html
nginx会查找文件:/Users/bruce/www/personal/test/static/static/html/index.html。
验证:/Users/bruce/www/personal/test/static,而uri为:/static/html/index.html,它们相连接,即为:

/Users/bruce/www/personal/test/static + /static/html/index.html = /Users/bruce/www/personal/test/static/static/html/index.html

验证正确:

Xnip2019-01-09_17-16-58.jpg

注意:这里的root指定的路径最后并没有/,也就是static后面没有/,如果有斜杠其实也是正确的,即:

/Users/bruce/www/personal/test/static/ + /static/html/index.html = /Users/bruce/www/personal/test/static//static/html/index.html

其中重复的斜杠应该是nginx自己兼容处理,直接忽略掉了(因为实际测试,最后有斜杠跟没有斜杠是一样的)。


把location匹配规则改成:

location ~ /static/ {
    root /Users/bruce/www/personal/test/static;
    index index.html;
    return 502 $request_filename;
}

访问:http://www.test.com/static/html/index.html
nginx会查找文件:/usr/local/nginx/html/static/static/index.html


再把location的匹配规则改成:

location ~ /html/ {
    root /Users/bruce/www/personal/test/static;
    index index.html;
    return 502 $request_filename;
}

访问:http://www.test.com/static/html/index.html
nginx会查找文件:/usr/local/nginx/html/static/static/index.html


总结root:也就是说,root指定虚拟主机目录时,与location上的修饰符无关,nginx永远会去找这个路径的文件:root+uri。


把root换成alias时:

location ^~ /static/ {
    alias /Users/bruce/www/personal/test/static/;
    index index.html;
    return 502 $request_filename;
}

或无修饰符:

location /static/ {
    alias /Users/bruce/www/personal/test/static/;
    index index.html;
    return 502 $request_filename;
}

访问:http://www.test.com/static/html/index.html
nginx会查找文件:/Users/bruce/www/personal/test/static/html/index.html
验证:因为alias为/Users/bruce/www/personal/test/static/,uri为/static/html/index.html,uri中location匹配的部分是static,static之后的路径为:html/index.html(注意不是/html/index.html,即html前面没有/),所以最终路径为:

/Users/bruce/www/personal/test/static/ + html/index.html=/Users/bruce/www/personal/test/static/html/index.html

验证正确:

Xnip2019-01-09_16-51-32.jpg

还是上边的配置,访问:http://www.test.com/static/index.html(即static后面少了个html目录)
nginx会查找文件:/Users/bruce/www/personal/test/static/index.html
验证:这次的uri为/static/index.html,location匹配的还是static,static之后的部分是index.html(注意是不包括index.html前面的/的),而alias的值还是/Users/bruce/www/personal/test/static/,它们相连接即为:

/Users/bruce/www/personal/test/static/ + index.html = /Users/bruce/www/personal/test/static/index.html

验证正确:

Xnip2019-01-09_17-56-06.jpg


如果配置文件的^~改成~

location ~ /static/ {
    alias /Users/bruce/www/personal/test/static/;
    index index.html;
    return 502 $request_filename;
}

访问:http://www.test.com/static/html/index.html
nginx会查找alias指定的目录(不会查找文件):/Users/bruce/www/personal/test/static/

Xnip2019-01-09_16-55-01.jpg


如果你把return 502那句去掉(即不打印),则会跳转到:
http://www.test.com/static/html/index.html/

Xnip2019-01-09_16-58-43.jpg

查看日志,nginx读取的路径还是alias指定的目录

Xnip2019-01-09_16-59-40.jpg


再把location配置文件改成这样:

location ~ /html/ {
    alias /Users/bruce/www/personal/test/static/;
    index index.html;
    return 502 $request_filename;
}

location ~* /html/ {
    alias /Users/bruce/www/personal/test/static/;
    index index.html;
    return 502 $request_filename;
}

访问:http://www.test.com/static/html/index.html
nginx还是会查找alias指定的目录(不会查找文件):/Users/bruce/www/personal/test/static/

Xnip2019-01-09_16-55-01.jpg

总结alias:当不使用修饰符或修饰符使用^~时,是alias+location匹配的uri关键字之后部分(不包括/),当修饰符为~~*时,不管location匹配的是什么,nginx都会查找alias指定的目录而不会查找具体文件,即使有设置index index.html也没有用,所以这样配置一般是不能用的,但如果你要开启autoindex(即显示目录文件列表),倒是可以这么用。

以上所有配置均经过真机测试(nginx version: openresty/1.13.6.2),但难免会有疏漏,如有错误,恳请评论指正,我将立即修改。

打赏

订阅评论
提醒
guest

此站点使用Akismet来减少垃圾评论。了解我们如何处理您的评论数据

0 评论
内联反馈
查看所有评论
0
希望看到您的想法,请您发表评论x

扫码在手机查看
iPhone请用自带相机扫
安卓用UC/QQ浏览器扫

Nginx – alias与root的区别