由于SS挂的厉害,网上的教程又语焉不详,这里记录一下。
原理:用Nginx(Caddy)解TLS,V2Ray处理里面的连接。
不建议初学者直接上手搞WebSocket+TLS+Web+Nginx+CDN:容易出错的地方太多。
请务必读完全文再操作,特别是注意部分。
Preparation
- SSL: https://freessl.cn
- 域名:https://www.freenom.com ,或者自己找一个
WebSocket
WebSocket可以直接连接,或者套CDN。
Server
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
{ "inbounds": [ { "port": 10001, # 本地端口,不冲突即可 "listen":"127.0.0.1", # V2Ray只监听本机 "protocol": "vmess", "settings": { "clients": [ { "id": "d111702d-8604-4358-b1fa-xxxxxxxxx", "alterId": 64 } ] }, "streamSettings": { "network": "ws", "wsSettings": { "path": "/ray/" # 注意最后的反斜杠必须和Nginx一致 } } } ], "outbounds": [ { "protocol": "freedom", "settings": {} } ] } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
server { server_name {subdomain.domain.tld}; listen 8.8.8.8 ssl; listen [2001::]:443 ssl; # 让Nginx也监听v6 ssl on; ssl_certificate /etc/nginx/ssl/xxx.pem; # SSL证书位置 ssl_certificate_key /etc/nginx/ssl/xxx.key; ssl_protocols TLSv1 TLSv1.1 TLSv1.2; ssl_ciphers HIGH:!aNULL:!MD5; location /ray/ { proxy_redirect off; proxy_pass http://127.0.0.1:10001; # 注意端口和上面一致 proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; # Show realip in v2ray access.log proxy_set_header X-Real-IP $remote_addr; proxy_set_header Host $host; # 必须有这条 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } } |
Client
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 |
{ "log": { "error": "", "loglevel": "debug", "access": "" }, "inbounds": [ { "listen": "127.0.0.1", "protocol": "socks", "settings": { "ip": "", "userLevel": 0, "timeout": 0, "udp": false, "auth": "noauth" }, "port": "8091" # SOCKS代理本地端口 } ], "outbounds": [ { "mux": { "enabled": false, "concurrency": 8 }, "protocol": "vmess", "streamSettings": { "wsSettings": { "path": "/ray/",# 注意和上面一致 "headers": { "host": "" } }, "tlsSettings": { "allowInsecure": true }, "security": "tls", "network": "ws" }, "tag": "", "settings": { "vnext": [ { "address": "上面的domain", "users": [ { "id": "和上面的UUID一样, "alterId": 64, "level": 0, "security": "auto" } ], "port": 443 # Nginx监听的端口 } ] } } ], "dns": { "servers": [ "" ] }, "routing": { "strategy": "rules", "settings": { "domainStrategy": "IPIfNonMatch", "rules": [ { "outboundTag": "direct", "type": "field", "ip": [ "geoip:cn", "geoip:private" ], "domain": [ "geosite:cn", "geosite:speedtest" ] } ] } }, "transport": {} } |
注意
- 如果挂Cloudflare:
- 如果自签证书(真的没必要),SSL必须设flexible:否则CF会报证书错误
- 如果使用正常SSL证书,SSL必须设Full:否则Nginx有可能随便丢一个站点过去
- 如果是新域名:等SSL生成后才能操作
- Cloudflare的免费证书只支持一级subdomain的SSL(*.domain.tld):如果域名是二级以上,请加钱或重新弄SSL。
- 利用
curl
进行debug。在任何情况下,错误码不应该是404.
HTTP2 with Caddy
Cloudflare的免费WebSocket优先级不高:HTTP2有可能看网页更快。当然了,这个方案没有什么CDN能支持。
Server
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
https://域名:2053 { root /usr/share/nginx/html/ tls /etc/nginx/ssl/公钥.pem /etc/nginx/ssl/私钥.key { # 也可以让Caddy自己找Letsencrypt生成 ciphers ECDHE-ECDSA-WITH-CHACHA20-POLY1305 ECDHE-ECDSA-AES256-GCM-SHA384 ECDHE-ECDSA-AES256-CBC-SHA curves p384 key_type p384 } proxy /v2ray https://localhost:12000 { # 端口号是V2Ray监听的本地端口 insecure_skip_verify transparent header_upstream X-Forwarded-Proto "https" header_upstream Host "域名 } header / { Strict-Transport-Security "max-age=31536000;" X-XSS-Protection "1; mode=block" X-Content-Type-Options "nosniff" X-Frame-Options "DENY" } } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
{ "inbounds": [ { "port": 12000, # 监听本地端口号 "listen": "127.0.0.1", # 只监听本地 "protocol": "vmess", "settings": { "clients": [ { "id": "UUID", "alterId": 64 } ] }, "streamSettings": { "network": "h2", "httpSettings": { "path": "/v2ray", "host": ["域名"] }, "security": "tls", "tlsSettings": { "certificates": [ { "certificateFile": "/etc/nginx/ssl/公钥.pem", "keyFile": "/etc/nginx/ssl/私钥.key" } ] } } } ], "outbounds": [ { "protocol": "freedom", "settings": {} } ] } |
Client
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
{ "inbounds": [ { "port": 8091, "listen": "127.0.0.1", "protocol": "socks" } ], "outbounds": [ { "protocol": "vmess", "settings": { "vnext": [ { "address": "域名", "port": 2053, # Caddy监听的端口 "users": [ { "id": "同一个UUID", "alterId": 64 } ] } ] }, "streamSettings": { "network": "h2", "httpSettings": { "path": "/v2ray", "host": ["域名"] }, "security": "tls" } } ] |
Note
- Nginx不能做HTTP 2转发:因为作者觉得没必要。只能用Caddy。
- 如果要使用CDN:虽然很多CDN支持HTTP2(例如Cloudflare),但是我们需要的是回源走HTTP2。目前还没有找到这种东西。
作者的需求挺奇怪的哈哈,相比于默认不开混淆,这样有什么优势吗?
优势是IP被墙不心疼。别的没有丝毫优势 速度只会更慢。
还有一个用途:服务器上又跑站又跑V2Ray。
虽然Caddy能当HTTP服务器 但是我还是习惯用Nginx。