准备
- 云服务器一台,本次使用阿里云服务器centos8.5,需要在阿里云后台打开服务器安全组端口 7000、8000、6000,IP假定为12.12.12.12
- 备案域名一个,假定为:test.example.com
- 本地环境MacOS
- 文档:https://gofrp.org/docs/
- 客户端frpc与服务器端frps,下载地址:https://github.com/fatedier/frp/releases;找到对应机型的包下载解压即可
- mac可用 brew install frpc安装客户端
brew services restart frpc
或
/usr/local/opt/frpc/bin/frpc -c /usr/local/etc/frp/frpc.ini
wget https://github.com/fatedier/frp/releases/download/v0.39.1/frp_0.39.1_linux_386.tar.gz
tar -axf frp_0.39.1_linux_386.tar.gz
cd frp_0.39.1_linux_386
./frps -c frps.ini
cp systemd/frps.service /etc/systemd/system/
cp frps /usr/bin/frps
mkdir /etc/frp/
cp frps.ini /etc/frp/
systemctl enable frps
服务端配置
[common]
# listen 端口
bind_port = 7000
# 这两个端口可以和bind_port相同
vhost_http_port = 7000
vhost_https_port = 7000
# 配置服务器dashboard,监控服务器连接流量等,通过12.12.12.12:8000访问
dashboard_addr = 0.0.0.0
dashboard_port = 8000
dashboard_user = admin
dashboard_pwd = adminpasswd
# 设置token校验,客户端的token和它一致
authentication_method = token
token = admintoken
- 解析域名到服务器ip test.example.com 12.12.12.12
- 给域名申请ssl证书 test.example.com.pem 和 test.example.com.key
客户端配置
公共配置
[common]
server_addr = 12.12.12.12
server_port = 7000
token = admintoken
# 客户端监控
admin_addr = 127.0.0.1
admin_port = 7400
admin_user = admin
admin_pwd = admin
ssh,websocket
[ssh]
type = tcp
local_ip = 127.0.0.1
local_port = 22
remote_port = 6000
- ssh -p 6000 root@test.example.com :即可远程访问内网穿透主机
MacOS默认不能远程访问,需要System Preferences->Sharing->Remote Login勾选才能访问 - websocket配置和上面一样(底层为tcp协议),只需要换为对应的端口即可
http
[web01]
type = http
local_ip = 127.0.0.1
local_port = 10000
custom_domains = web01.test.example.com
[web02]
type = http
local_ip = 127.0.0.1
local_port = 10001
custom_domains = web02.test.example.com
- 服务端frps.ini需要配置vhost_http_port参数,此处配置为7000
- 则http://web01.test.example.com:7000指向访问本地127.0.0.1:10000的服务;http://web02.test.example.com:7000指向访问本地127.0.0.1:10001的服务
https
[api_https]
type = https
custom_domains = api.test.example.com
plugin = https2http
plugin_local_addr = 127.0.0.1:8080
# HTTPS 证书相关的配置
plugin_crt_path = /usr/local/etc/nginx/cert/test.example.com.pem
plugin_key_path = /usr/local/etc/nginx/cert/test.example.com.key
plugin_host_header_rewrite = 127.0.0.1
plugin_header_X-From-Where = frp
- 服务端frps.ini需要配置vhost_https_port参数,此处配置为7000
- 直接访问https://api.test.example.com:7000 可以访问 本地http://127.0.0.1:8080服务
虚拟主机服务
nginx通过Host Header来区分相同端口下的虚拟主机服务,此处使用host_header_rewrite改写host可以实现代理虚拟主机服务。 - frpc.ini
[api]
type = http
local_port = 80
custom_domains = api.test.example.com
host_header_rewrite = api.local.com
[m]
type = http
local_port = 80
custom_domains = m.test.example.com
host_header_rewrite = m.local.com
- nginx配置,可拿真实ip。
- $proxy_add_x_forwarded_for = $http_x_forwarded_for + $remote_addr
- 可以使用
http{
......
log_format access 'proxy_protocol_addr:$proxy_protocol_addr, remote_addr:$remote_addr, http_x_forwarded_for:$http_x_forwarded_for, proxy_add_x_forwarded_for:$proxy_add_x_forwarded_for';
access_log /Users/junmo/logs/nginx/access.log access;
......
server {
listen 80;
server_name m.local.com;
location / {
proxy_pass http://127.0.0.1:8080;
index index.html index.htm;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-Host $server_name;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
}
- nginx日志
- ps:对于正常的nginx访问,可以使用X-Forwarded-For头隐藏真实ip,但是要祈祷服务端不要使用$remote_addr来获取真实ip
$ curl m.test.example.com:7000
proxy_protocol_addr:-, remote_addr:127.0.0.1, http_x_forwarded_for:123.115.146.226, proxy_add_x_forwarded_for:123.115.146.226, 127.0.0.1
$ curl -H "X-Forwarded-For: 1.1.1.1" m.test.example.com:7000
proxy_protocol_addr:-, remote_addr:127.0.0.1, http_x_forwarded_for:1.1.1.1, 123.115.146.226, proxy_add_x_forwarded_for:1.1.1.1, 123.115.146.226, 127.0.0.1
http_proxy
- 使用服务器代理访问
- 在shell终端输入,即可在此终端使用服务器代理访问
- export http_proxy=12.12.12.12:6000
- export https_proxy=12.12.12.12:6000
- frpc.ini
[http_proxy]
type = tcp
remote_port = 6000
plugin = http_proxy
#plugin_http_user = abc
#plugin_http_passwd = abc
proxy protocol
- 使用proxy protocol,就可以配置ssl证书在nginx里,也可以拿到真实的客户端ip,当前版本0.39的https代理是不能拿到真实客户端ip的
- frpc.ini
[web]
type = https
local_port = 443
custom_domains = web.test.example.com
# 目前支持 v1 和 v2 两个版本的 proxy protocol 协议。
proxy_protocol_version = v2
- nginx配置,
使用 $proxy_protocol_addr可以获得真实的ip,而不是代理的ip
# 观察ip
http{
......
log_format access 'proxy_protocol_addr:$proxy_protocol_addr, remote_addr:$remote_addr, http_x_forwarded_for:$http_x_forwarded_for, proxy_add_x_forwarded_for:$proxy_add_x_forwarded_for';
access_log /Users/junmo/logs/nginx/access.log access;
......
server {
listen 443 proxy_protocol;
server_name web.test.example.com;
ssl_certificate cert/ web.test.example.com.pem;
ssl_certificate_key cert/ web.test.example.com.key;
ssl_session_timeout 5m;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_ciphers ALL:!ADH:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP;
ssl_prefer_server_ciphers on;
location / {
proxy_pass http://127.0.0.1:8080;
index index.html index.htm;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $proxy_protocol_addr;
proxy_set_header X-Forwarded-Host $server_name;
proxy_set_header X-Forwarded-For $proxy_protocol_addr;
}
}
}
proxy_protocol_addr:123.115.146.226, remote_addr:127.0.0.1, http_x_forwarded_for:-, proxy_add_x_forwarded_for:127.0.0.1
|