Closed msshn closed 1 year ago
I don't use the NGINX front SNI shunt approach myself. Here is my experienced guess as to why, you need to test it yourself.
Because you used the proxy_protocol; parameter in the nginx configuration to pass the IP to access both.
listen 127.0.0.1:20000 ssl proxy_protocol;
"streamSettings": {
"network": "tcp",
"security": "reality",
"realitySettings": {
"show": false,
"dest": 20000,
"xver": 2,
"serverNames": [
"xx.mydomain.com"
],
"privateKey": "...",
"shortIds": [
"123456789"
]
},
"tcpSettings": {
"acceptProxyProtocol": true
}
},
This parameter is being used incorrectly.
https://xtls.github.io/Xray-docs-next/config/transport.html#streamsettingsobject
"tcpSettings": {
"acceptProxyProtocol": true
"xver": 2,
I'm not sure if I should use 0 here, or if I should use 1 or 2
"streamSettings": {
"network": "tcp",
"security": "reality",
"realitySettings": {
"show": false,
"dest": 20000,
"xver": 1, // test
"serverNames": [
"xx.mydomain.com"
],
"privateKey": "...",
"shortIds": [
"123456789"
]
},
"sockopt": {
"acceptProxyProtocol": true // test
}
},
The way the sing-box configuration is written I think is correct, it doesn't work because the parameters that sing-box passes back to nginx don't belong to the proxy_protocol. So in your nginx configuration either don't use listen 127.0.0.1:20000 ssl proxy_protocol; remove proxy_protoco.
Since I haven't experimented with them, you'll need to test the above yourself.
"inbounds": [
{
"type": "vless",
"tag": "vless-in",
"listen": "::",
"listen_port": 10000,
"proxy_protocol": true,
"sniff": true,
"sniff_override_destination": true,
"users": [
{
"uuid": "532f45bd-7229-425e-8831-97a463eba428",
"flow": "xtls-rprx-vision"
}
],
"tls": {
"enabled": true,
"server_name": "xx.mydomain.com",
"reality": {
"enabled": true,
"handshake": {
"server": "127.0.0.1",
"server_port": 20000
},
"private_key": "...",
"short_id": [
"123456789"
]
}
}
}
],
https://github.com/chika0801/sing-box-examples/blob/main/VMess/WebSocket_nginx.conf#L74
I saw this configuration and it occurred to me that this one possibility NGINX front passes the port to the back when listen 127.0.0.1:20000 ssl proxy_protocol;, proxy_protocol This parameter should be added, but in the xray parameter of the back
"sockopt": {
"acceptProxyProtocol": false// test
Then you can test whether xver uses 0 or 1 and it works.
Since I didn't even test it, you need to test it yourself.
https://github.com/lxhao61/integrated-examples/tree/main/Xray(M%2BF%2BB%2BG%2BA)%2BNginx
I learned it by referring to the example linked above. And I tested it.
This is the configuration I used after testing it myself, you can refer to it.
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log notice;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
stream {
map $ssl_preread_server_name $name {
www.lovelive-chika.top backend;
}
upstream backend {
server 127.0.0.1:8004;
}
server {
listen 443;
proxy_pass $name;
proxy_protocol on;
ssl_preread on;
}
}
http {
log_format main '[$time_local] $proxy_protocol_addr "$http_referer" "$http_user_agent"';
access_log /var/log/nginx/access.log main;
map $http_upgrade $connection_upgrade {
default upgrade;
"" close;
}
map $proxy_protocol_addr $proxy_forwarded_elem {
~^[0-9.]+$ "for=$proxy_protocol_addr";
~^[0-9A-Fa-f:.]+$ "for=\"[$proxy_protocol_addr]\"";
default "for=unknown";
}
map $http_forwarded $proxy_add_forwarded {
"~^(,[ \\t]*)*([!#$%&'*+.^_`|~0-9A-Za-z-]+=([!#$%&'*+.^_`|~0-9A-Za-z-]+|\"([\\t \\x21\\x23-\\x5B\\x5D-\\x7E\\x80-\\xFF]|\\\\[\\t \\x21-\\x7E\\x80-\\xFF])*\"))?(;([!#$%&'*+.^_`|~0-9A-Za-z-]+=([!#$%&'*+.^_`|~0-9A-Za-z-]+|\"([\\t \\x21\\x23-\\x5B\\x5D-\\x7E\\x80-\\xFF]|\\\\[\\t \\x21-\\x7E\\x80-\\xFF])*\"))?)*([ \\t]*,([ \\t]*([!#$%&'*+.^_`|~0-9A-Za-z-]+=([!#$%&'*+.^_`|~0-9A-Za-z-]+|\"([\\t \\x21\\x23-\\x5B\\x5D-\\x7E\\x80-\\xFF]|\\\\[\\t \\x21-\\x7E\\x80-\\xFF])*\"))?(;([!#$%&'*+.^_`|~0-9A-Za-z-]+=([!#$%&'*+.^_`|~0-9A-Za-z-]+|\"([\\t \\x21\\x23-\\x5B\\x5D-\\x7E\\x80-\\xFF]|\\\\[\\t \\x21-\\x7E\\x80-\\xFF])*\"))?)*)?)*$" "$http_forwarded, $proxy_forwarded_elem";
default "$proxy_forwarded_elem";
}
server {
listen 80;
return 301 https://$host$request_uri;
}
server {
# http2 on; 这条指令出现在1.25.1版本中 https://nginx.org/en/docs/http/ngx_http_v2_module.html
# listen 127.0.0.1:8005 ssl proxy_protocol;
# http2 on;
listen 127.0.0.1:8005 ssl http2 proxy_protocol;
set_real_ip_from 127.0.0.1;
real_ip_header proxy_protocol;
ssl_certificate /etc/ssl/private/fullchain.cer;
ssl_certificate_key /etc/ssl/private/private.key;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers TLS13_AES_128_GCM_SHA256:TLS13_AES_256_GCM_SHA384:TLS13_CHACHA20_POLY1305_SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305;
ssl_session_timeout 1d;
ssl_session_cache shared:SSL:10m;
ssl_session_tickets off;
ssl_stapling on;
ssl_stapling_verify on;
ssl_trusted_certificate /etc/ssl/private/fullchain.cer;
resolver 1.1.1.1 valid=60s;
resolver_timeout 2s;
# 使用 https://www.digitalocean.com/community/tools/nginx 生成的反向代理配置
location / {
sub_filter $proxy_host $host;
sub_filter_once off;
set $website www.lovelive-anime.jp; # 反向代理的网站
proxy_pass https://$website;
resolver 1.1.1.1;
proxy_set_header Host $proxy_host;
proxy_http_version 1.1;
proxy_cache_bypass $http_upgrade;
proxy_ssl_server_name on;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_set_header X-Real-IP $proxy_protocol_addr;
proxy_set_header Forwarded $proxy_add_forwarded;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host;
proxy_set_header X-Forwarded-Port $server_port;
proxy_connect_timeout 60s;
proxy_send_timeout 60s;
proxy_read_timeout 60s;
}
}
}
{
"log": {
"loglevel": "warning"
},
"routing": {
"domainStrategy": "IPIfNonMatch",
"rules": [
{
"type": "field",
"ip": [
"geoip:cn",
"geoip:private"
],
"outboundTag": "block"
}
]
},
"inbounds": [
{
"listen": "127.0.0.1",
"port": 8004,
"protocol": "vless",
"settings": {
"clients": [
{
"id": "chika", // 执行 xray uuid 生成,或 1-30 字节的字符串
"flow": "xtls-rprx-vision"
}
],
"decryption": "none"
},
"streamSettings": {
"network": "tcp",
"security": "reality",
"realitySettings": {
"show": false, // 若为 true,输出调试信息
"dest": "8005", // 即 "127.0.0.1:8005"
"xver": 1, // 发送 PROXY protocol
"serverNames": [ // 客户端可用的 serverName 列表,暂不支持 * 通配符,建议填由 Nginx 加载的 SSL 证书中包含的域名,建议将此域名指向服务端的 IP
"www.lovelive-chika.top" // 也可填任意网址,建议是国外网站
],
"privateKey": "2KZ4uouMKgI8nR-LDJNP1_MHisCJOmKGj9jUjZLncVU", // 执行 xray x25519 生成,填 "Private key" 的值
"shortIds": [ // 客户端可用的 shortId 列表,可用于区分不同的客户端
"6ba85179e30d4fc2" // 0 到 f,长度为 2 的倍数,长度上限为 16,可留空,或执行 openssl rand -hex 8 生成
]
},
"sockopt": {
"acceptProxyProtocol": false
}
},
"sniffing": {
"enabled": true,
"destOverride": [
"http",
"tls",
"quic"
]
}
}
],
"outbounds": [
{
"protocol": "freedom",
"tag": "direct"
},
{
"protocol": "blackhole",
"tag": "block"
}
],
"policy": {
"levels": {
"0": {
"handshake": 2,
"connIdle": 120
}
}
}
}
If you change xray to sing-box, I looked at your Sing-box config and you added "proxy_protocol": true, which is correct. But I've tested sing-box when using the steal yourself form, sing-box doesn't have the xver:1 parameter inside xray. So if you use sing-box as a server, be careful to remove listen 127.0.0.1:8005 ssl http2; remove proxy_protocol from nginx configuration.
Sorry for late reply, been out of town for a couple days removing "proxy_protocol" from nginx did it! and it's working with sing-box server now. I was ready to pull my hair off, never suspected nginx is the issue, thank you so much!
Hello, and thanks for your great examples. I recently tried to divert traffic to sing-box based on SNI but was unsuccessful, however the same thing works with xray without problem. I wanted to know your opinion on this. SNI diversion works with other protocols in sing-box such as naive or trojan, but not reality. I am also using reality with my own domain. The reason for this is I have other services on the vps and i need nginx to listen on 443.
Here are configs
Nginx
xray: This config works
sing-box: does not work
sing-box Logs