内网穿透 Frp 与 NGINX 配置

这是我日常部署 frp 的一些配置方法,可以实现把 frp 的 http 映射到某个域名下的 80 端口,甚至可以简单实现支援证书。一次配置,支援所有 http 服务的内网穿透。

安装 Frp

首先,我们要安装 frp 到我们的服务器。到 GitHub 的 release 拉取最新版本即可https://github.com/fatedier/frp/releases 。比如我是 64 bit Ubuntu 系统,那么就在服务器下执行:

# 下载 frp
wget https://github.com/fatedier/frp/releases/download/v0.48.0/frp_0.48.0_linux_amd64.tar.gz
# 解压 frp
tar xzf frp_*.tar.gz
# 将 frp 拷贝到 /usr/local/src/ 目录下
sudo mv frp_0.48.0_linux_amd64 /usr/local/src/frp
# 创建 server 端 link 到  /usr/local/sbin/ 这样就可以全局直接调用
sudo ln -s /usr/local/src/frp/frps /usr/local/sbin/frps
# 创建 server config link 到 /etc/
sudo ln -s /usr/local/src/frp/frps.ini /etc/frps.ini

接着创建一个 frp 的 service,可以做到服务守护,开机自启。执行:

sudo vim /etc/systemd/system/frps.service

将如下内容贴入:

[Unit]
Description=FRP Server Daemon

[Service]
Type=simple
ExecStartPre=-/usr/sbin/setcap cap_net_bind_service=+ep /usr/local/sbin/frps
ExecStart=/usr/local/sbin/frps -c /etc/frps.ini
Restart=always
RestartSec=20s
User=nobody
PermissionsStartOnly=true
LimitNOFILE=infinity

[Install]
WantedBy=multi-user.target

配置 Frp

再编辑 /etc/frps.ini ,修改内容如下:

[common]
vhost_http_port=6002
bind_port = 7000
dashboard_port = 7500
dashboard_user = username
dashboard_pwd = password
token=your_token
subdomain_host=frp.domain.com

将 username 和 password 按照你们自己的需要修改,然后就可以启动服务了。token不是必须的,如果想要加上认证避免被别人盗连,则可以加上。

sudo systemctl start frps
# 开机自启
sudo systemctl enable frps

后面有修改 frps.ini ,就只需要执行 sudo systemctl restart frps

注意,如果你在使用云服务器,需要在安全组将 bind_port 的端口打开。

配置 NGINX

接着,我们再来配置 NGINX。假设我们的服务器上绑定的域名是 domain.com,那么我们将 frp.domain.com 及其子域都分配用于 frp 的 http 服务。如果你要支援 HTTPS,那么要需要申请一个 frp.domain.com 的证书和 *.frp.domain.com 的证书。现在假设你已经具备这两个证书,那么就只需要在 NGINX 中创建一个配置如下:

server {
    # 配置监听所有子域请求
    server_name  ~^(?<subdomain>[^.]+)\.frp\.domain\.com$;

    listen       443 ssl http2;
    # *.frp.domain.com 域名证书
    ssl_certificate      /etc/letsencrypt/live/frp.domain.com/fullchain.pem;
    ssl_certificate_key  /etc/letsencrypt/live/frp.domain.com/privkey.pem;

    listen 80;
    # 此处填写你服务器的 dns 或其他可以解析你域名的 dns
    resolver 8.8.8.8;
    # 反向代理 frp 内网穿透的 http 服务器
    location / {
        proxy_pass http://$subdomain.frp.domain.com:6002;
        proxy_buffering off;

        proxy_redirect http://$subdomain.frp.domain.com:6002/ http://$subdomain.frp.domain.com/;
        proxy_redirect ~^http://([^.]+)\.frp\.domain\.com:6002/(.*?)$ http://$1.frp.domain.com/$2;

        proxy_set_header X-Forwarded-For $proxy_protocol_addr;
        proxy_set_header X-Real_IP $remote_addr;
        proxy_set_header User-Agent $http_user_agent;
        proxy_set_header Accept-Encoding '';
        proxy_set_header referer "http://$proxy_host$request_uri";
    }
}

# 这个是反向代理 dashboard 。这样安全组就无需再打开 7500 端口
server {
    server_name frp.domain.com;

    listen 443 ssl http2;
    # frp.domain.com 域名证书
    ssl_certificate      /etc/letsencrypt/live/domain.com/fullchain.pem;
    ssl_certificate_key  /etc/letsencrypt/live/domain.com/privkey.pem;

    listen 80;

    location / {
        proxy_pass http://frp.domain.com:7500;
    }
}

添加配置后,重启 NGINX 服务。现在你就可以使用了。

使用示例

假设你现在有个 3000 端口的本地 http 服务。那么就只需要创建一个 frp 的 Client 配置如下:

[common]
server_addr = domain.com
server_port = 7000

[local01_http]
type = http
local_ip = 127.0.0.1
local_port = 3000
subdomain = local01

然后执行 frpc -c frpc.ini 即可。连接成功后,就可以通过 local01.frp.domain.com 来访问了。