Skip to content
hev edited this page Apr 13, 2024 · 3 revisions

使用NATMap在NAT-1私网IP宽带上部署Web服务

通过NATMap在运营商的NAT-1上打洞,分配私网IPv4的宽带可以部署Web服务,并能像具有公网IP一样在其它外部主机上访问。

拓扑结构

                  HTTPD                  NATMap(on gateway)                Browser

Internal:    (192.168.0.102:22) <-----> (100.65.11.55:6336)
                                               ^
                                               |
                                               v
External:                              (112.24.0.23:6348) <------------>
  • HTTPD: Web服务端运行在内网主机,侦听在192.168.0.102:8000端口。
  • NATMap: NATMap运行在网关,侦听在100.65.11.55:6336端口,打洞使公网地址112.24.0.23:6348映射至100.65.11.55:6336,同时又将100.65.11.55:6336映射至192.168.0.102:8000。从外部访问112.24.0.23:6348等同于访问192.168.0.102:8000。
  • Browser: 浏览器运行在外部主机上,通过NATMap打洞获得的公网地址112.24.0.23:6348访问Web服务。

域名访问

在具有动态公网IPv4的宽带上部署Web服务,只有公网IPv4因为重新拨号是在动态变化的,而端口则是固定的。利用动态DNS则可以通过固定的域名作为入口实时解析到动态变化的IP,进而访问到服务。

在NAT-1私网IPv4的宽带上,情况稍微有些不同,不仅打洞后获得的运营商侧公网IPv4是动态变化的,端口同样也是动态变化的。为了同样能够使用固定的域名入口访问服务,推荐使用支持自定义源站端口的CDN服务,比如Cloudflare的免费CDN服务。

安装部署

HTTPD

安装任意满足需求的Web服务端即可,没有额外的要求。

NATMap

安装

DDNS
Cloudflare

创建文件/usr/bin/wdns写入如下内容,并补充必要的变量值:

#!/bin/sh

ZONE=''
RECORD=''
RULE=''
EMAIL=''
AUTH=''
DOMAIN=''

ADDR=${1}
PORT=${2}

# DNS
while true; do
    curl -X PUT "https://api.cloudflare.com/client/v4/zones/${ZONE}/dns_records/${RECORD}" \
        -H "X-Auth-Email: ${EMAIL}" \
        -H "Authorization: Bearer ${AUTH}" \
        -H "Content-Type:application/json" \
        --data "{\"type\":\"A\",\"name\":\"${DOMAIN}\",\"content\":\"${ADDR}\",\"ttl\":60,\"proxied\":false}" > /dev/null 2> /dev/null
    if [ $? -eq 0 ]; then
        break
    fi
done

# Origin rule
while true; do
    curl -X PUT "https://api.cloudflare.com/client/v4/zones/${ZONE}/rulesets/${RULE}" \
        -H "Authorization: Bearer ${AUTH}" \
        -H "Content-Type:application/json" \
        --data "{\"rules\":[{\"expression\":\"(http.host eq \\\"${DOMAIN}\\\")\",\"description\":\"natmap\",\"action\":\"route\",\"action_parameters\":{\"origin\":{\"port\":${PORT}}}}]}" > /dev/null 2> /dev/null
    if [ $? -eq 0 ]; then
        break
    fi
done

再增加可执行权限:

chmod +x /usr/bin/wdns
OpenWrt 22.03 or later

从软件仓库安装natmap和luci-app-natmap软件包。

或命令行

opkg install natmap luci-app-natmap
其它系统

从项目发布页下载匹配的版本: https://github.com/heiher/natmap/releases

运行

OpenWrt 22.03 or later
1. 登录OpenWrt管理页面,进入「服务」->「NATMap」页面:

2. 点击「Add」按钮,输入如下配置:
  • Protocol: TCP
  • Interface: wan
  • STUN server: turn.cloudflare.com
  • HTTP server: qq.com
  • Bind port: 6336
  • Forward mode: ☑
  • Forward target: 192.168.0.102
  • Forward target port: 8000
  • Notify script: /usr/bin/wdns

3. 保存后NATMap会显示出打洞后的外部公网IPv4地址和端口记录:

4. 防火墙放行TCP协议目的端口6336的入站:

其它系统

将如下内容写入 /etc/rc.local 开机自动启动,或创建其它服务管理配置:

natmap -d -i pppoe-wan -s turn.cloudflare.com -h qq.com -b 6336 -t 192.168.0.102 -p 8000 -e /usr/bin/wdns

防火墙放行TCP协议目的端口6336的入站。

访问测试

域名解析结果

比如域名为: web.hev.cc

nslookup web.hev.cc

当配置正确且运行正常时,应当能够解析类似如下结果:

Server:		192.168.0.1
Address:	192.168.0.1#53

Non-authoritative answer:
Name:	web.hev.cc
Address: 112.24.0.23

HTTP访问

curl http://web.hev.cc
It works!