Nginx应用与运维——Nginx HTTP模块详解(动态赋值功能模块)

Nginx HTTP模块详解

1、动态赋值功能模块

Nginx在核心模块及其他模块中都提供了内置变量,用户可以根据需要灵活调用。在Nginx的模块中除提供了rewrite指令以方便用户对变量进行静态赋值外,还提供了根据请求内容的变化为变量动态赋值的功能。

1.1、根据浏览器动态赋值

模块名称:ngx_http_browser_module

该模块的功能是根据客户端HTTP请求头中的属性字段User-Agent的值,按照用户的指令配置设置变量$modern_browser和$ancient_browser的值。用户可以根据变量$modern_browser和$ancient_browser的值对客户端浏览器进行区分,并对HTTP请求进行不同的处理。该模块的内置配置指令如表所示。

1.1.1、旧浏览器标识指令------ancient_browser

配置样例如下:

bash 复制代码
http {
    ancient_browser 'UCWEB';
}

变量$ancient_browser的值默认为1。

1.1.2、设置旧浏览器变量值指令------ancient_browser_value

配置样例如下:

bash 复制代码
http {
    ancient_browser 'UCWEB';
    ancient_browser_value oldweb;
    server {
        if ($ancient_browser) {
            rewrite ^ /${ancient_browser}.html; # 重定向到oldweb.html 
        }
    }
}
1.1.3、新浏览器标识指令------modern_browser

配置样例如下:

bash 复制代码
http {
    modern_browser msie  5.5;
}
  • 内置浏览器类型有msie、gecko(由Mozilla基金会维护,Mozilla及Netscape 6后续版本是基于Gecko开发的)、opera、safari、konqueror。
  • 当指令值为unlisted时,Nginx在HTTP请求头中的属性字段User-Agent的值为空或无法识别浏览器类型时,设置变量$modern_browser的值为1。

配置样例如下:

bash 复制代码
http {
    modern_browser msie  5.5;
    modern_browser unlisted;
}
1.1.4、设置新浏览器变量值指令------modern_browser_value

配置样例如下:

bash 复制代码
http {
    modern_browser msie 5.5;
    modern_browser_value newweb;
    server {
        if ($modern_browser) {
            rewrite ^ /${modern_browser}.html;
        }
    }
}

配置样例如下:

bash 复制代码
ancient_browser 'UCWEB';         # 必须使用单引号
ancient_browser_value oldweb;    # 设置$ancient_browser的值为oldweb

modern_browser_value newweb;     # 设置$ancient_browser的值为newweb
modern_browser unlisted;         # 设置$modern_browser的值为1, $ancient_browser的值为0

root /opt/nginx-web;
server {
    listen 8080;
    if ($ancient_browser) {
        rewrite ^ /${ancient_browser}.html; # 重定向到oldweb.html
    }
    if ($modern_browser) {
        rewrite ^ /${modern_browser}.html;  # 重定向到newweb.html
    }
}

1.2、根据IP动态赋值

模块名称:ngx_http_geo_module

该模块的功能是从源变量获取IP地址,并根据设定的IP与对应值的列表对新变量进行赋值。该模块只有一个geo指令,指令格式如下:

bash 复制代码
geo [源变量]新变量{}
  • geo指令的默认源变量是$remote_addr,新变量默认值为空。
  • geo指令的作用域只能是http。

该指令的指令值参数如表所示。

配置样例如下:

bash 复制代码
http{
    geo $country {
        proxy_recursive;                    # 启用代理递归查询
        default        ZZ;                  # 默认值为ZZ
        include        conf/geo.conf;       # 引入外部列表文件
        proxy          192.168.100.0/24;    # 上层代理地址为192.168.100.0/24的IP
        proxy          2001:0db8::/32;      # 上层代理地址为2001:0db8::/32的IP

        127.0.0.0/16   US;                  # 赋值US
        127.0.0.1/32   RU;                  # 赋值RU
        10.1.0.0/16    RU;                  # 赋值RU
        192.168.1.0/24 UK;                  # 赋值UK
    }
}

为了加速加载IP来设定变量表,IP地址应按升序填写。

外部文件geo.conf的内容格式如下:

bash 复制代码
10.2.0.0/16    RU;
192.168.2.0/24 RU;

以地址段形式定义的IP地址中ranges参数的配置样例如下:

bash 复制代码
http{
    geo $country {
        ranges;                             # 使用以地址段的形式定义的IP地址
        default                   ZZ;
        10.1.0.0-10.1.255.255     RU;
        192.168.1.0-192.168.1.255 UK;
    }
}

自定义源变量配置样例如下:

bash 复制代码
geo $arg_ip $address {                      # 设置请求参数IP为源变量
    default           CN;
    127.0.0.0/24      US;
    127.0.0.10/32     RU;
    10.1.0.0/16       RU;
    delete 127.0.0.10/32;                   # 删除127.0.0.10/32的设定
}

server {
    listen 8081;
    server_name localhost;
    charset utf-8;
    root /opt/nginx-web;
    default_type text/xml;

    location / {
        rewrite ^ /${address}.html break;   # 重定向到$address.html
    }
}

1.3、根据IP动态获取城市信息

模块名称:ngx_http_geoip_module

该模块的功能是将客户端的IP地址与MaxMind数据库中的城市地址信息进行比对,然后将对应的城市地址信息赋值给内置变量。该模块的配置指令如表所示。

  • 国家信息数据库指令
  • 城市信息数据库指令
  • 机构信息数据库指令
  • 上层代理IP指令
  • 代理递归查询IP指令


    geo内置变量如表所示。

配置样例如下:

bash 复制代码
geoip_country     /usr/share/GeoIP/GeoIP.dat;
geoip_city         /usr/share/GeoIP/GeoIPCity.dat;
geoip_org         /usr/share/GeoIP/GeoIPASNum.dat;
geoip_proxy     192.168.2.145;
geoip_proxy_recursive   on;

server {
    listen 8081;
    server_name localhost;
    charset utf-8;
    root /opt/nginx-web;
    default_type text/xml;
    location / {
        if ( $geoip_country_code ) {
            rewrite ^ /$geoip_country_code/ break; # 重定向到$geoip_country_cod目录
        }
    }
}

1.4、比例分配赋值

模块名称:ngx_http_split_clients_module

该模块会按照配置指令将一个0~232之间的数值根据设定的比例分割为多个数值范围,每个数值范围会被设定一个对应的给定值。用户每次请求时,指定的字符串会被计算出一个数值,该模块会将该数值所在范围对应的给定值赋值给配置中定义的变量。该功能常用来按照用户的来源IP进行访问流量分流。该指令语法格式如下:

bash 复制代码
split_clients 字符串 新变量{}

配置样例如下:

bash 复制代码
split_clients "${remote_addr}AAA" $source {   # "${remote_addr}AAA"会被计算出一个数值
    0.5%             .one;      # 数值在0~21474835之间,$source被赋值".one"
    80.0%            .two;      # 数值在21474836~3435973836之间,$source被赋值".two"
    *                 "";       # 数值在3435973837~4294967295, $source被赋值""
}
server {
    location / {
        index index${source}.html;
    }
}
  • 该指令会将一个2的32次幂计算的值(数值范围为0~4294967295)按照指令域中的比例进行分割。
  • 客户端每次请求时,会将指定字符串使用MurmurHash2算法计算出一个0~232(0~4 294 967 295)之间的数值,该模块会将该数值所在范围对应的给定值赋值给配置中定义的变量。
  • 指定的字符串可以是Nginx内置变量。

1.5、变量映射赋值

模块名称:ngx_http_map_module

该模块的功能是在客户端每次请求时,Nginx按照map指令域中源变量的当前值把设定的对应值赋值给新变量。该指令语法格式如下:

bash 复制代码
map 源变量 新变量{}

map指令值参数如表所示。

配置样例如下:

bash 复制代码
map $remote_addr $name {
    hostnames;
    default       0;
    example.com   1;
    *.example.com 1; # 主机名前缀
    wap.*         4; # 主机名后缀
    include hostmap.conf;
}
  • map指令只能编辑在http指令域中。
  • map指令域中指定了源变量为不同值时与新变量值的对应关系。
  • map指令域中源变量的值可以是字符串或正则表达式的匹配。
  • map指令域中对源变量的值进行正则表达式匹配时,以"~"开头表示对源变量值的匹配,区分大小写,以"*"开头表示对源变量值的匹配不区分大小写。
bash 复制代码
map $http_user_agent $mobile  {
    "~Opera Mini" 1;
    "*UCWEB" 2;
}

map指令域中对源变量的值进行正则表达式匹配时,可以对源变量值进行正则捕获。

bash 复制代码
map $uri $new_uri {
    ~^/user/(.*) ucenter;         # 若URI为/user/login时,$new_uri被赋值为"ucenter"
}
server {
    listen       8080;
    location /user {
        default_type text/plain;
        rewrite ^ /$new_uri/$1;   # rewrite到/ucenter/login
    }
    location /ucenter {
        index index.html;
    }
}

若源变量值中包含特殊字符串"~"​,可以用"~"进行转义。

bash 复制代码
map $http_referer $flag {
    Mozilla    111;
    \~Mozilla  222;
}

新变量的值可以是字符串,也可以是另一个变量。

bash 复制代码
map $http_referer $value {
    Mozilla    'chrom';
    \~safity    $http_user_agent;
}

map指令域中,当源变量值存在相同匹配项时,匹配顺序如下:

  • 1)完全匹配的字符串。

  • 2)有主机前缀的最长字符串。

  • 3)有主机后缀的最长字符串。

  • 4)在指令域中按自上而下顺序最先匹配到的正则表达式。

  • 5)default参数给定的默认值。

  • map哈希表大小指令

  • map哈希桶大小指令

配置样例如下:

bash 复制代码
map $remote_addr $dir {
    default www;                 # 设置默认目录为www
    include conf.d/remoteip.list;# 以外部文件形式编写IP及对应新变量赋值列表
}
server {
    listen       8080;
    root /opt/nginx-web/$dir;
    index index.html;
}

remoteip.list文件内容:
192.168.2.145 blue;              # 源IP为192.168.2.145时,map的新变量值为blue
192.168.2.100 green;             # 源IP为192.168.2.100时,map的新变量值为green
相关推荐
..Dauntless..1 小时前
【Linux】进程地址空间初步理解
linux·运维·服务器
Julien20041 小时前
Docker 网络(一)
linux·运维·服务器·ssh·学习方法
字节跳动的猫2 小时前
LikeShop 积分体系全链路改造:获取规则、订单抵扣与积分商品兑换二开
运维·数据结构
杨云龙UP2 小时前
一次数据库查询缓慢故障复盘:大表数据增长、SQL全表扫描导致系统响应异常
linux·运维·服务器·数据库·sql·mysql
PellyKoo3 小时前
【linux运维】ubuntu+samba 用户组独占目录权限配置踩坑记
linux·运维·ubuntu
wtblszn3 小时前
空压机在线监测物联网方案
大数据·运维·物联网·自动化·能源
AR-26710-3 小时前
Linux Day15——系统管理复习
linux·运维
姜鱼问生3 小时前
三层防火墙排查:Nginx 配好了浏览器还打不开
nginx·安全
打工仔折腾 AI4 小时前
飞牛OS上用Docker Compose部署ExerciseDiary运动记录并配置远程访问
运维·人工智能·后端·python·docker·容器·ai agent 实战