本文作者:zhujue

V2Ray 配置指南-高级篇

zhujue 2023-12-26 19:42:27 34 抢沙发
V2Ray 配置指南-高级篇摘要: ...

1. 高级篇

恭喜大家来到高级篇。 使用基础篇当中的配置案例科学上网足够了,但 V2Ray 提供了许多额外的功能,若不利用着实可惜。在本篇当中,将针对某个功能简要介绍,并给出关键配置,因此可能不是完整的,也不会像基础篇那样详细,只会在关键之处作一些必要的介绍。

V2Ray 的相比其它工具有一大优点是可以自行选择传输层的形式,也就是说 V2Ray 服务器和客户端之间的传输的流量格式我们是可以选择的。如我们可以选择伪装成 HTTP(TCP)流量,如果使用了 mKCP 也可以伪装成 BT 下载、视频通话、微信视频通话。也可以选择使用 WebSokcs 或者 TLS。以上这个都是传输层的配置决定的。

V2Ray 中传输层配置在 transport 里设定,也可以在各个 inbound/outbound 中的 streamSettings 设定。这两者的区别是 inbound/outbound 的 streamSettings 只对当前的 inbound/outbound 有效(分连接配置),不影响其它的 inbound/outbound 的传输层配置,而 transport 是全局的,对整个配置所有的 inbound 和 outbound 都有效(全局配置),如果一个 inbound/outbound 中设定了 streamSettings,transport 的设定不会影响这个 inbound/outbound。

在本篇当中,大部分内容都涉及到了传输层,关于这部分内容使用的是 inbound/outbound 的 streamSettings(分连接配置),同时也建议大家使用分连接配置。因为如果你在全局配置中开启了伪装功能,会导致浏览器或者其它软件无法与 V2Ray 通信!这不是 bug,只是因为你设置不当。


  • 一、Mux

1. Mux

Mux 意为多路复用(multiplexing),在目前的科学上网工具中仅 V2Ray 有此功能(2018-03-15注:也有其他软件实现了类似的功能)。它能够将多条 TCP 连接合并成一条,节省资源,提高并发能力。

听众:呃?什么鬼?

好吧,翻译成人话就是:

从前,有一个人叫小白,他是骑行爱好者,还是网购狂人、DIY玩家,因此手中有点闲钱总会网购,也喜欢自己买配件组装自行车。有一次他组装自行车,在网上骑行之家买了头盗、手套、码表,在x诺专卖店买了指拨、变速器,在x特专卖买了车架,在xx车行买了刹车、踏板、坐垫,在xxx买了轮组、曲柄……

四天后……
9 点小白手机响了,接通,小白:喂,你好。对方:你好,申x快递,来取一下包裹。小白兴兴冲地取快递了。    
20 分钟后,小白:喂,你好。对方:你好,韵x,过来取快递。小白又去了。    
又过 15 分钟,小白:喂,你好。对方:你好,天x,来取快递。小白又去了。    
又过半个小时,小白:什么快递?对方:圆x,快点来。小白心里:我X。    
10 分钟后……

如果是你是小白,你累不累? 电脑也差不多,但要干的活要小白多得多:

浏览器:我要看 V2Ray 配置指南。
电脑:好,我发起一条 TCP 连接。
Telegram:我要进 V2Ray 的 Telegram 群向大佬学习。
电脑:好,发起了连接。
浏览器:我要看 V2Ray 的手册。
电脑:好。
浏览器:我要 Google 搜索 V2Ray 的教程。
电脑:好。
浏览器:我要……

如果正常的上网连接可以使用上面小白的例子类比的话,那么,V2Ray 的 Mux 就是:

小黑也与小白一样自行组装自行车,也是网购配件,但他无论什么东西都从xx车行这店里买。

4 天后,小黑接起电话:你好。
对方:你好,顺x,来取一下快递。
小黑顺路买了瓶饮料:大哥,天气这么热,喝点水解解渴。嘿嘿,这箱子太沉,辛苦一下帮帮我搬到屋里吧。

Mux 实质上不能提高网速,但对并发连接比较有效,如浏览图片较多的网页,看直播等。从使用效果来说,V2Ray 的 Mux 应该类似于 Shadowsocks 的 TFO(TCP Fast Open),因为两者的目的都是减小握手时间,只是实现方式不一样。只是 TFO 要设置系统内核才能打开,而 Mux 是纯粹在软件层面上实现,从配置难易度上 V2Ray 较好一些。(2018-09-19 注:刚更新这段话没多久,V2Ray 就加入了对 TFO 的支持,感觉要学不动了~)

1.1. 配置

Mux 只需在客户端开启,服务器会自动识别,所以只给客户端的配置。也就是只要在 outbound 或 outboundDetour 加入 "mux": {"enabled": true} 即可:

{  "inbound": {    "port": 1080, // 监听端口
    "protocol": "socks", // 入口协议为 SOCKS 5
    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth"  // 不认证
    }
  },  "outbound": {    "protocol": "vmess", // 出口协议
    "settings": {      "vnext": [
        {          "address": "serveraddr.com", // 服务器地址,请修改为你自己的服务器 ip 或域名
          "port": 16823,  // 服务器端口
          "users": [
            {              "id": "b831381d-6324-4d53-ad4f-8cda48b30811",  // 用户 ID,必须与服务器端配置相同
              "alterId": 64 // 此处的值也应当与服务器相同
            }
          ]
        }
      ]
    },    "mux": {"enabled": true}
  }
}

1.2. 更新历史

  • 2018-08-30 修改排版、描述


  • 二、mKCP

1. mKCP

V2Ray 引入了 KCP 传输协议,并且做了一些不同的优化,称为 mKCP,相对于常规的 TCP 来说,mKCP 在某些网络环境下具有更大的优势,但是 mKCP 有一个很明显的缺点就是会比 TCP 耗费更多的流量,所以请酌情使用。要了解的一点是,mKCP 与 KCPTUN 同样是 KCP 协议,但两者并不兼容。

1.1. 配置

mKCP 的配置比较简单,只需在服务器的 inbound 和 客户端的 outbound 添加一个 streamSettings 并设置成 mkcp 即可。

1.1.1. 服务器配置

{  "inbound": {    "port": 16823,    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "b831381d-6324-4d53-ad4f-8cda48b30811",          "alterId": 64
        }
      ]
    },    "streamSettings": {      "network": "mkcp", //此处的 mkcp 也可写成 kcp,两种写法是起同样的效果
      "kcpSettings": {        "mtu": 1350,        "tti": 20,        "uplinkCapacity": 5,        "downlinkCapacity": 100,        "congestion": true,        "readBufferSize": 1,        "writeBufferSize": 1,        "header": {          "type": "none"
        }
      }
    }
  },  "outbound": {    "protocol": "freedom",    "settings": {}
  }
}

1.1.2. 客户端配置

{  "inbound": {    "port": 1080,    "protocol": "socks",    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth"
    }
  },  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "serveraddr.com",          "port": 16823,          "users": [
            {              "id": "b831381d-6324-4d53-ad4f-8cda48b30811",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings": {      "network": "mkcp",      "kcpSettings": {        "mtu": 1350,        "tti": 20,        "uplinkCapacity": 5,        "downlinkCapacity": 100,        "congestion": ture,        "readBufferSize": 1,        "writeBufferSize": 1,        "header": {          "type": "none"
        }
      }
    }
  }
}

1.1.3. 说明

在上面的配置当中,与之前相比主要的变化在于多了一个 streamSettings,包含有不少参数:

  • network: 网络的选择,要像上面的配置写成 kcp 或 mkcp 才会启用 mKCP

  • kcpSettings: 包含一些关于 mKCP 设置的参数,有

    • type:要伪装成的数据包类型

    • uplinkCapacity: 上行链路容量,将决定 V2Ray 向外发送数据包的速率。单位为 MB

    • downlinkCapacity:下行链路容量,将决定 V2Ray 接收数据包的速率。单位同样是 MB

    • header:对于数据包的伪装

客户端的上行对于服务器来说是下行,同样地客户端的下行是服务器的上行,mKCP 设置当中服务器和客户端都有 uplinkCapacity 和 downlinkCapacity,所以客户端的上传速率由服务器的 downlinkCapacity 和客户端的 uplinkCapacity 中的最小值决定,客户端的下载速率也是同样的道理。因此,建议将服务器和客户端的 downlinkCapacity 设成一个很大的值,然后分别修改两端的 uplinkCapacity 以调整上下行速率。

还有一个 header 参数可以对 mKCP 进行伪装,这是 mKCP 的一个优势。具体的伪装类型在 type 参数设置,type 可以设置成 utp、srtp、wechat-video、dtls、wireguard 或者 none,这几个分别将 mKCP 数据伪装成 BT 下载、视频通话、微信视频通话、dtls、wireguard(一种新型 VPN)以及不进行伪装。这里的 type 参数,客户端与服务器要一致。还有要时刻记住伪装仅仅是伪装。

至于上述配置里有但是我没有说明的参数,是 V2Ray 的默认值,我个人建议是保持默认。如果你需要了解或者修改,请参考手册。

1.2. 更新历史

  • 2018-03-17 Update

  • 2018-08-30 Update


1. 动态端口

V2Ray 提供了一个叫动态端口的功能。顾名思义,就是可以动态变化端口,对于对抗封锁或许有效,请大家自行验证。

1.1. 基本动态端口

服务器 inbound 的端口作为主端口,在 inboundDetour 开动态监听的端口,客户端不用额外设定。

1.1.1. 服务器配置

{  "inbound":{    "port": 37192,    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "d17a1af7-efa5-42ca-b7e9-6a35282d737f",          "level": 1,          "alterId": 64
        }
      ],      "detour": {        
        "to": "dynamicPort"   
      }
    }
  },  "inboundDetour":[
    {      "protocol": "vmess",      "port": "10000-20000", // 端口范围
      "tag": "dynamicPort",       
      "settings": {        "default": {          "level": 1,          "alterId": 32
        }
      },      "allocate": {            // 分配模式
        "strategy": "random",  // 随机开启
        "concurrency": 2,      // 同时开放两个端口
        "refresh": 3           // 每三分钟刷新一次
      }
    }
  ]
}

1.1.2. 客户端配置

{  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "1.2.3.4",          "port": 37192,          "users": [
            {              "id": "d17a1af7-efa5-42ca-b7e9-6a35282d737f",              "alterId": 64
            }
          ]
        }
      ]
    }
  }
}

1.2. 动态端口使用 mKCP

在 inbound 和 inboundDetour 加入 streamSettings 并将 network 设置为 kcp 即可。

1.2.1. 服务器配置

{  "inbound": {    "port": 37192,    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "d17a1af7-efa5-42ca-b7e9-6a35282d737f",          "level": 1,          "alterId": 64
        }
      ],      "detour": {        
        "to": "dynamicPort"   
      }
    },    "streamSettings": {      "network": "kcp"
    }
  },  "inboundDetour": [
    {      "protocol": "vmess",      "port": "10000-20000", // 端口范围
      "tag": "dynamicPort",       
      "settings": {        "default": {          "level": 1,          "alterId": 32
        }
      },      "allocate": {            // 分配模式
        "strategy": "random",  // 随机开启
        "concurrency": 2,      // 同时开放两个端口
        "refresh": 3           // 每三分钟刷新一次
      },      "streamSettings": {        "network": "kcp"
      }
    }
  ]
}

1.2.2. 客户端配置

{  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "1.2.3.4",          "port": 37192,          "users": [
            {              "id": "d17a1af7-efa5-42ca-b7e9-6a35282d737f",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings": {      "network": "kcp"
    }
  }
}

1.3. 更新历史

  • 2018-01-06 删除错误且不必要的部分


  • 四、代理转发

1. 代理转发

V2Ray 提供了代理转发功能,利用它可以实现中转(在没有中转服务器操作权限的情况下)。

1.1. 基本代理转发

使用代理转发可以实现由一个 Shadowsocks 服务器或者 V2Ray(VMess) 服务器来中转你的网络流量,并且中转服务器只能看到你加密的数据而不知道原始的数据是什么。

以下面的配置说明,它的工作原理是:

  1. 你在 Twitter 发了个帖子 f**k GFW,由 V2Ray 代理

  2. V2Ray 客户端收到浏览器发出的 f**k GFW 的帖子后,首先由对其进行加密(VMess,id: b12614c5-5ca4-4eba-a215-c61d642116ce,目的服务器: 1.1.1.1:8888)

  3. 加密后数据包将被转到 transit 这个 outbound 中,在这里数据包又会加密一次(Shadowsocks, password: password, 服务器: 2.2.2.2:1024)

  4. 两次加密后的数据包被发送到了 Shadowsocks 服务器,该服务器收到后解包后得到仍是加密的数据包(步骤 2 中加密后的数据包),然后将数据包发到 VMess 服务器。即便这个 Shadowsocks 服务器的主人是个偷窥狂魔,他也没办法看到你的原始数据。

  5. VMess 服务器收到 Shadowsocks 服务器发来的数据包,解密得到原始的数据包,然后把你这个帖子发到 Twitter 的网站中。

只要第 5 步中的服务器是自己掌控的就不用担心别人看到你的上网的内容。

客户端:

{  "outbound": {    "protocol": "vmess",    "settings": { // settings 的根据实际情况修改
      "vnext": [
        {          "address": "1.1.1.1",          "port": 8888,          "users": [
            {              "alterId": 64,              "id": "b12614c5-5ca4-4eba-a215-c61d642116ce"
            }
          ]
        }
      ]
    },    "proxySettings": {        "tag": "transit"  // 这里的 tag 必须跟作为代理 VPS 的 tag 一致,这里设定的是 "transit"
      }
  },  "outboundDetour": [
    {      "protocol": "shadowsocks",      "settings": {        "servers": [
          {            "address": "2.2.2.2",            "method": "aes-256-cfb",            "ota": false,            "password": "password",            "port": 1024
          }
        ]
      },      "tag": "transit"
    }
  ]
}

1.2. 链式代理转发

如果你有多个 Shadowsocks 或 VMess 账户,那么你可以这样:

{  "outbound": {    "protocol": "vmess",    "settings": { // settings 的根据实际情况修改
      "vnext": [
        {          "address": "1.1.1.1",          "port": 8888,          "users": [
            {              "alterId": 64,              "id": "b12614c5-5ca4-4eba-a215-c61d642116ce"
            }
          ]
        }
      ]
    },    "tag": "DOUS",    "proxySettings": {        "tag": "DOSG"  
      }
  },  "outboundDetour": [
    {      "protocol": "shadowsocks",      "settings": {        "servers": [
          {            "address": "2.2.2.2",            "method": "aes-256-cfb",            "ota": false,            "password": "password",            "port": 1024
          }
        ]
      },      "tag": "AliHK"
    },
    {      "protocol": "shadowsocks",      "settings": {        "servers": [
          {            "address": "3.3.3.3",            "method": "aes-256-cfb",            "ota": false,            "password": "password",            "port": 3442
          }
        ]
      },      "tag": "AliSG",      "proxySettings": {          "tag": "AliHK"  
      }
    },
    {      "protocol": "vmess",      "settings": {        "vnext": [
          {            "address": "4.4.4.4",            "port": 8462,            "users": [
              {                "alterId": 64,                "id": "b27c24ab-2b5a-433e-902c-33f1168a7902"
              }
            ]
          }
        ]
      },      "tag": "DOSG",      "proxySettings": {          "tag": "AliSG"  
      }
    },
  ]
}

那么数据包经过的节点依次为: PC -> AliHK -> AliSG -> DOSG -> DOUS -> 目标网站

这样的代理转发形成了一条链条,我称之为链式代理转发。

注意:如果你打算配置(动态)链式代理转发,应当明确几点:

  • 性能。链式代理使用了多个节点,可能会造成延时、带宽等网络性能问题,并且客户端对每一个加解密的次数取决于代理链的长度,理论上也会有一定的影响。

  • 安全。前文提到,代理转发会一定程度上提高安全性,但安全取决于最弱一环,并不意味着代理链越长就会越安全。如果你需要匿名,请考虑成熟的匿名方案。 另外,使用了代理转发 streamSettings 会失效,即只能是非 TLS、无 HTTP 伪装的 TCP 传输协议。

1.3. 更新历史

  • 2018-03-17 Update

  • 2018-07-08 Update


  • 五、HTTP 伪装

1. HTTP 伪装

2018-03-16 注:个人建议不要使用 HTTP 伪装) V2Ray 自 v2.5 版本开始提供 HTTP 伪装功能,后经作者不断完善,到现在已经非常成熟稳定了。V2Ray 的 HTTP 伪装功能可以可以将 V2Ray 的流量伪装成正常的 HTTP 协议的。这里给出一个 HTTP 伪装的服务器端与客户端配置文件示例。

配置中关于 HTTP 头字段的内容及含义,Wikipedia 有简要的说明,可参阅。

1.1. 配置

从 V2Ray 的实现角度来说,使用 HTTP 伪装的同时完全可以使用动态端口。但我个人并不建议这么做,因为从实际情况来看,基本上不会有人在一个服务器上开使用多个端口的 Web 服务。如果你觉得 HTTP 伪装的配置过于复杂不懂得如何修改,那请直接使用下面的配置即可。

1.1.1. 服务器

{  "log" : {    "access": "/var/log/v2ray/access.log",    "error": "/var/log/v2ray/error.log",    "loglevel": "warning"
  },  "inbound": {    "port": 80, //推荐80端口,更好地迷惑防火墙(好吧实际上并没有什么卵用
    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "b831381d-6324-4d53-ad4f-8cda48b30811",          "level": 1,          "alterId": 64
        }
      ]
    },    "streamSettings": {      "network": "tcp",      "tcpSettings": {        "header": { // header 这一项是关于数据包伪装的设置,可自定义合理的内容,但要确保服务器与客户端一致
          "type": "http",          "response": {            "version": "1.1",            "status": "200",            "reason": "OK",            "headers": {              "Content-Type": ["application/octet-stream", "application/x-msdownload", "text/html", "application/x-shockwave-flash"],              "Transfer-Encoding": ["chunked"],              "Connection": ["keep-alive"],              "Pragma": "no-cache"
            }
          }
        }
      }
    }
  },  "outbound": {    "protocol": "freedom",    "settings": {}
  },  "outboundDetour": [
    {      "protocol": "blackhole",      "settings": {},      "tag": "blocked"
    }
  ],  "routing": {    "strategy": "rules",    "settings": {      "rules": [
        {          "type": "field",          "ip": [            "0.0.0.0/8",            "10.0.0.0/8",            "100.64.0.0/10",            "127.0.0.0/8",            "169.254.0.0/16",            "172.16.0.0/12",            "192.0.0.0/24",            "192.0.2.0/24",            "192.168.0.0/16",            "198.18.0.0/15",            "198.51.100.0/24",            "203.0.113.0/24",            "::1/128",            "fc00::/7",            "fe80::/10"
          ],          "outboundTag": "blocked"
        }
      ]
    }
  }
}

1.1.2. 客户端

{  "log": {    "loglevel": "warning"
  },  "inbound": {    "port": 1080,    "protocol": "socks",    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth"
    }
  },  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "serveraddr.com",          "port": 80,          "users": [
            {              "id": "b831381d-6324-4d53-ad4f-8cda48b30811",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings": {      "network": "tcp",      "tcpSettings": {        "header": {  //这里的 header 要与服务器保持一致
          "type": "http",          "request": {            "version": "1.1",            "method": "GET",            "path": ["/"],            "headers": {              "Host": ["www.cloudflare.com", "www.amazon.com"],              "User-Agent": [                "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.75 Safari/537.36",                        "Mozilla/5.0 (iPhone; CPU iPhone OS 10_0_2 like Mac OS X) AppleWebKit/601.1 (KHTML, like Gecko) CriOS/53.0.2785.109 Mobile/14A456 Safari/601.1.46"
              ],              "Accept-Encoding": ["gzip, deflate"],              "Connection": ["keep-alive"],              "Pragma": "no-cache"
            }
          }
        }
      }
    }
  },  "outboundDetour": [
    {      "protocol": "freedom",      "settings": {},      "tag": "direct"
    }
  ],  "routing": {    "strategy": "rules",    "settings": {      "domainStrategy": "IPIfNonMatch",      "rules": [
        {          "type": "field",          "ip": [            "0.0.0.0/8",            "10.0.0.0/8",            "100.64.0.0/10",            "127.0.0.0/8",            "169.254.0.0/16",            "172.16.0.0/12",            "192.0.0.0/24",            "192.0.2.0/24",            "192.168.0.0/16",            "198.18.0.0/15",            "198.51.100.0/24",            "203.0.113.0/24",            "::1/128",            "fc00::/7",            "fe80::/10"
          ],          "outboundTag": "direct"
        },
        {          "type": "chinasites",          "outboundTag": "direct"
        },
        {          "type": "chinaip",          "outboundTag": "direct"
        }
      ]
    }
  }
}

1.2. 更新历史

  • 2017-08-05 删掉部分不必要的配置

  • 2018-03-16 Update


1. TLS

从 v1.19 起引入了 TLS,TLS 中文译名是传输层安全,如果你没听说过,请 Google 了解一下。以下给出些我认为介绍较好的文章链接:

SSL/TLS协议运行机制的概述

传输层安全协议

1.1. 注册一个域名

如果已经注册有域名了可以跳过。 TLS 需要一个域名,域名有免费的和有付费的,如果你不舍得为一个域名每年花点钱,用个免费域名也可以,但总体来说付费的会优于免费的。为了方便,在本文中我就忽略如何注册购买域名了。关于如何获取域名,具体搜索相关文章教程。

注册好域名之后务必记得添加一个 A 记录指向你的 VPS!

以下假设注册的域名为 mydomain.me,请将之替换成自己的域名。

1.2. 证书生成

TLS 是证书认证机制,所以使用 TLS 需要证书,证书也有免费付费的,同样的这里使用免费证书,证书认证机构为 Let's Encrypt。 证书的生成有许多方法,这里使用的是比较简单的方法:使用 acme.sh 脚本生成,本部分说明部分内容参考于acme.sh README

证书有两种,一种是 ECC 证书(内置公钥是 ECDSA 公钥),一种是 RSA 证书(内置 RSA 公钥)。简单来说,同等长度 ECC 比 RSA 更安全,也就是说在具有同样安全性的情况下,ECC 的密钥长度比 RSA 短得多(加密解密会更快)。但问题是 ECC 的兼容性会差一些,Android 4.x 以下和 Windows XP 不支持。只要您的设备不是非常老的老古董,强烈建议使用 ECC 证书。

以下将给出这两类证书的生成方法,请大家根据自身的情况自行选择其中一种证书类型。

证书生成只需在服务器上操作。

1.2.1. 安装 acme.sh

执行以下命令,acme.sh 会安装到 ~/.acme.sh 目录下。

$ curl  https://get.acme.sh | sh
% Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                               Dload  Upload   Total   Spent    Left  Speed
100   671  100   671    0     0    680      0 --:--:-- --:--:-- --:--:--   679
% Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                               Dload  Upload   Total   Spent    Left  Speed
100  112k  100  112k    0     0   690k      0 --:--:-- --:--:-- --:--:--  693k
[Fri 30 Dec 01:03:32 GMT 2016] Installing from online archive.
[Fri 30 Dec 01:03:32 GMT 2016] Downloading https://github.com/Neilpang/acme.sh/archive/master.tar.gz
[Fri 30 Dec 01:03:33 GMT 2016] Extracting master.tar.gz
[Fri 30 Dec 01:03:33 GMT 2016] Installing to /home/user/.acme.sh
[Fri 30 Dec 01:03:33 GMT 2016] Installed to /home/user/.acme.sh/acme.sh
[Fri 30 Dec 01:03:33 GMT 2016] Installing alias to '/home/user/.profile'
[Fri 30 Dec 01:03:33 GMT 2016] OK, Close and reopen your terminal to start using acme.sh
[Fri 30 Dec 01:03:33 GMT 2016] Installing cron job
no crontab for user
no crontab for user
[Fri 30 Dec 01:03:33 GMT 2016] Good, bash is found, so change the shebang to use bash as preferred.
[Fri 30 Dec 01:03:33 GMT 2016] OK
[Fri 30 Dec 01:03:33 GMT 2016] Install success!

安装成功后执行 source ~/.bashrc 以确保脚本所设置的命令别名生效。

如果安装报错,那么可能是因为系统缺少 acme.sh 所需要的依赖项,acme.sh 的依赖项主要是 netcat(nc),我们通过以下命令来安装这些依赖项,然后重新安装一遍 acme.sh:

$ sudo apt-get -y install netcat

1.2.2. 使用 acme.sh 生成证书

证书生成

执行以下命令生成证书:

以下的命令会临时监听 80 端口,请确保执行该命令前 80 端口没有使用

$ sudo ~/.acme.sh/acme.sh --issue -d mydomain.me --standalone -k ec-256
[Fri Dec 30 08:59:12 HKT 2016] Standalone mode.
[Fri Dec 30 08:59:12 HKT 2016] Single domain='mydomain.me'
[Fri Dec 30 08:59:12 HKT 2016] Getting domain auth token for each domain
[Fri Dec 30 08:59:12 HKT 2016] Getting webroot for domain='mydomain.me'
[Fri Dec 30 08:59:12 HKT 2016] _w='no'
[Fri Dec 30 08:59:12 HKT 2016] Getting new-authz for domain='mydomain.me'
[Fri Dec 30 08:59:14 HKT 2016] The new-authz request is ok.
[Fri Dec 30 08:59:14 HKT 2016] mydomain.me is already verified, skip.
[Fri Dec 30 08:59:14 HKT 2016] mydomain.me is already verified, skip http-01.
[Fri Dec 30 08:59:14 HKT 2016] mydomain.me is already verified, skip http-01.
[Fri Dec 30 08:59:14 HKT 2016] Verify finished, start to sign.
[Fri Dec 30 08:59:16 HKT 2016] Cert success.
-----BEGIN CERTIFICATE-----
MIIEMTCCAxmgAwIBAgISA1+gJF5zwUDjNX/6Xzz5fo3lMA0GCSqGSIb3DQEBCwUA
MEoxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MSMwIQYDVQQD
ExpMZXQncyBFbmNyeXB0IEF1dGhvcml0eSBYMzAeFw0xNjEyMjkyMzU5MDBaFw0x
NzAzMjkyMzU5MDBaMBcxFTATBgNVBAMTDHdlYWtzYW5kLmNvbTBZMBMGByqGSM49
****************************************************************
4p40tm0aMB837XQ9jeAXvXulhVH/7/wWZ8/vkUUvuHSCYHagENiq/3DYj4a85Iw9
+6u1r7atYHJ2VwqSamiyTGDQuhc5wdXIQxY/YQQqkAmn5tLsTZnnOavc4plANT40
zweiG8vcIvMVnnkM0TSz8G1yzv1nOkruN3ozQkLMu6YS7lk/ENBN7DBtYVSmJeU2
VAXE+zgRaP7JFOqK6DrOwhyE2LSgae83Wq/XgXxjfIo1Zmn2UmlE0sbdNKBasnf9
gPUI45eltrjcv8FCSTOUcT7PWCa3
-----END CERTIFICATE-----
[Fri Dec 30 08:59:16 HKT 2016] Your cert is in  /root/.acme.sh/mydomain.me_ecc/mydomain.me.cer
[Fri Dec 30 08:59:16 HKT 2016] Your cert key is in  /root/.acme.sh/mydomain.me_ecc/mydomain.me.key
[Fri Dec 30 08:59:16 HKT 2016] The intermediate CA cert is in  /root/.acme.sh/mydomain.me_ecc/ca.cer
[Fri Dec 30 08:59:16 HKT 2016] And the full chain certs is there:  /root/.acme.sh/mydomain.me_ecc/fullchain.cer

-k 表示密钥长度,后面的值可以是 ec-256 、ec-3842048307240968192,带有 ec 表示生成的是 ECC 证书,没有则是 RSA 证书。在安全性上 256 位的 ECC 证书等同于 3072 位的 RSA 证书。

证书更新

由于 Let's Encrypt 的证书有效期只有 3 个月,因此需要 90 天至少要更新一次证书,acme.sh 脚本会每 60 天自动更新证书。也可以手动更新。

手动更新 ECC 证书,执行:

$ sudo ~/.acme.sh/acme.sh --renew -d mydomain.com --force --ecc

如果是 RSA 证书则执行:

$ sudo ~/.acme.sh/acme.sh --renew -d mydomain.com --force

由于本例中将证书生成到 /etc/v2ray/ 文件夹,更新证书之后还得把新证书生成到 /etc/v2ray。

1.2.3. 安装证书和密钥

ECC 证书

将证书和密钥安装到 /etc/v2ray 中:

$ sudo ~/.acme.sh/acme.sh --installcert -d mydomain.me --fullchainpath /etc/v2ray/v2ray.crt --keypath /etc/v2ray/v2ray.key --ecc

RSA 证书

$ sudo ~/.acme.sh/acme.sh --installcert -d mydomain.me --fullchainpath /etc/v2ray/v2ray.crt --keypath /etc/v2ray/v2ray.key

注意:无论什么情况,密钥(即上面的v2ray.key)都不能泄漏,如果你不幸泄漏了密钥,可以使用 acme.sh 将原证书吊销,再生成新的证书,吊销方法请自行参考 acme.sh 的手册

1.3. 配置 V2Ray

1.3.1. 服务器

{  "inbound": {    "port": 443, // 建议使用 443 端口
    "protocol": "vmess",    
    "settings": {      "clients": [
        {          "id": "23ad6b10-8d1a-40f7-8ad0-e3e35cd38297",  
          "alterId": 64
        }
      ]
    },    "streamSettings": {      "network": "tcp",      "security": "tls", // security 要设置为 tls 才会启用 TLS
      "tlsSettings": {        "certificates": [
          {            "certificateFile": "/etc/v2ray/v2ray.crt", // 证书文件
            "keyFile": "/etc/v2ray/v2ray.key" // 密钥文件
          }
        ]
      }
    }
  },  "outbound": {    "protocol": "freedom",    "settings": {}
  }
}

1.3.2. 客户端

{  "inbound": {    "port": 1080,    "protocol": "socks",    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth"
    }
  },  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "mydomain.me", // tls 需要域名,所以这里应该填自己的域名
          "port": 443,          "users": [
            {              "id": "23ad6b10-8d1a-40f7-8ad0-e3e35cd38297",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings": {      "network": "tcp",      "security": "tls" // 客户端的 security 也要设置为 tls
    }
  }
}

1.4. 验证

一般来说,按照以上步骤操作完成,V2Ray 客户端能够正常联网说明 TLS 已经成功启用。但要是有个可靠的方法来验证是否正常开启 TLS 无疑更令人放心。 验证的方法有很多,我仅介绍一种小白化一点的,便是 Qualys SSL Labs's SSL Server Test

注意:使用 Qualys SSL Labs's SSL Server Test 要求使用 443 端口,意味着你服务器配置的 inbound.port 应当是 443

打开 Qualys SSL Labs's SSL Server Test,在 Hostname 中输入你的域名,点提交,过一会结果就出来了。 V2Ray 配置指南-高级篇 科学上网 第1张

V2Ray 配置指南-高级篇 科学上网 第2张 这是对于你的 TLS/SSL 的一个总体评分,我这里评分为 A,看来还不错。有这样的界面算是成功了。

V2Ray 配置指南-高级篇 科学上网 第3张 这是关于证书的信息。从图中可以看出,我的这个证书有效期是从 2016 年 12 月 27 号到 2017 年的 3 月 27 号,密钥是 256 位的 ECC,证书签发机构是 Let's Encrypt,重要的是最后一行,Trusted 为 Yes,表明我这个证书可信。

1.5. 温馨提醒

V2Ray 的 TLS 不是伪装或混淆,这是完整、真正的 TLS。因此才需要域名和证书。后文提到的 WS(WebSocket) 也不是伪装。


1.6. 更新历史

  • 2017-08-06 加点提醒

  • 2017-12-31 修正文字错误

  • 2018-04-05 Update


1. WebSocket

WebSocket 的配置其实很简单,就跟 mKCP 一样把 network 一改就行了。话不多说,直接上配置。

1.1. 配置

1.1.1. 服务器配置

{  "inbound": {    "port": 16823,    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "b831381d-6324-4d53-ad4f-8cda48b30811",          "alterId": 64
        }
      ]
    },    "streamSettings": {      "network":"ws"
    }
  },  "outbound": {    "protocol": "freedom",    "settings": {}
  }
}

1.1.2. 客户端配置

{  "inbound": {    "port": 1080,    "protocol": "socks",    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth"
    }
  },  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "serveraddr.com",          "port": 16823,          "users": [
            {              "id": "b831381d-6324-4d53-ad4f-8cda48b30811",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings":{      "network":"ws"
    }
  }
}


1. WebSocket+TLS+Web

前文分别提到过 TLS 和 WebSocket 的配置方法,而本文搭配 Web 服务并同时实现 TLS 和 WebSocket。关于 Web 的软件本文给出了 Nginx,Caddy 和 Apache 三个例子,三选一即可,也可以选用其它的软件。

很多新手一接触 V2Ray 就想搞 WebSocket+TLS+Web 或 WebSocket+TLS+Web+CDN,我就想问 ssh 和 vim/nano 用利索了没,步子这么大不怕扯到蛋吗?使用 Nginx / Caddy / Apache 是因为 VPS 已经有 Nginx / Caddy / Apache 可以将 V2Ray 稍作隐藏,使用 WebSocket 是因为搭配 Nginx / Caddy / Apache 只能用 WebSocket,使用 TLS 是因为可以流量加密,看起来更像 HTTPS。 也许 WebSocket+TLS+Web 的配置组合相对较好,但不意味着这样的配置适合任何人。因为本节涉及 Nginx / Caddy / Apache,只给出了配置示例而不讲具体使用方法,也就是说你在阅读本节内容前得会使用这三个软件的其中之一,如果你还不会,请自行 Google。

注意: V2Ray 的 Websocket+TLS 配置组合并不依赖 Nginx / Caddy / Apache,只是能与其搭配使用而已,没有它们也可以正常使用。

1.1. 配置

1.1.1. 服务器配置

这次 TLS 的配置将写入 Nginx / Caddy / Apache 配置中,由这些软件来监听 443 端口(443 比较常用,并非 443 不可),然后将流量转发到 V2Ray 的 WebSocket 所监听的内网端口(本例是 10000),V2Ray 服务器端不需要配置 TLS。

服务器 V2Ray 配置

{  "inbound": {    "port": 10000,    "listen":"127.0.0.1",//只监听 127.0.0.1,避免除本机外的机器探测到开放了 10000 端口
    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "b831381d-6324-4d53-ad4f-8cda48b30811",          "alterId": 64
        }
      ]
    },    "streamSettings": {      "network": "ws",      "wsSettings": {      "path": "/ray"
      }
    }
  },  "outbound": {    "protocol": "freedom",    "settings": {}
  }
}

Nginx 配置

配置中使用的是域名和证书使用 TLS 小节的举例,请替换成自己的。

server {
  listen  443 ssl;
  ssl on;
  ssl_certificate       /etc/v2ray/v2ray.crt;
  ssl_certificate_key   /etc/v2ray/v2ray.key;
  ssl_protocols         TLSv1 TLSv1.1 TLSv1.2;
  ssl_ciphers           HIGH:!aNULL:!MD5;
  server_name           mydomain.me;
        location /ray {
        proxy_redirect off;
        proxy_pass http://127.0.0.1:10000;#假设WebSocket监听在环回地址的10000端口上
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_set_header Host $http_host;
        }
}

Caddy 配置

因为 Caddy 会自动申请证书并自动更新,所以使用 Caddy 不用指定证书、密钥。

mydomain.me
{
  log ./caddy.log
  proxy /ray localhost:10000 {
    websocket
    header_upstream -Origin
  }
}

Apache 配置

同样地,配置中使用的是域名和证书使用 TLS 小节的举例,请替换成自己的。

<VirtualHost *:443>
  ServerName mydomain.me
  SSLCertificateFile /etc/v2ray/v2ray.crt
  SSLCertificateKeyFile /etc/v2ray/v2ray.key

  SSLProtocol -All +TLSv1 +TLSv1.1 +TLSv1.2
  SSLCipherSuite HIGH:!aNULL

  <Location "/ray/">
    ProxyPass ws://127.0.0.1:10000/ray/ upgrade=WebSocket
    ProxyAddHeaders Off
    ProxyPreserveHost On
    RequestHeader append X-Forwarded-For %{REMOTE_ADDR}s
  </Location>
</VirtualHost>

1.1.2. 客户端配置

{  "inbound": {    "port": 1080,    "listen": "127.0.0.1",    "protocol": "socks",    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth",      "udp": false
    }
  },  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "mydomain.me",          "port": 443,          "users": [
            {              "id": "b831381d-6324-4d53-ad4f-8cda48b30811",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings": {      "network": "ws",      "security": "tls",      "wsSettings": {        "path": "/ray"
      }
    }
  }
}

1.1.3. 注意事项

  • V2Ray 暂时不支持 TLS1.3,如果开启并强制 TLS1.3 会导致 V2Ray 无法连接

  • 较低版本的nginx的location需要写为 /ray/ 才能正常工作

  • 如果在设置完成之后不能成功使用,可能是由于 SElinux 机制(如果你是 CentOS 7 的用户请特别留意 SElinux 这一机制)阻止了 Nginx 转发向内网的数据。如果是这样的话,在 V2Ray 的日志里不会有访问信息,在 Nginx 的日志里会出现大量的 "Permission Denied" 字段,要解决这一问题需要在终端下键入以下命令:

    setsebool -P httpd_can_network_connect 1
  • 请保持服务器和客户端的 wsSettings 严格一致,对于 V2Ray,/ray 和 /ray/ 是不一样的

1.1.4. 其他的话

  1. 开启了 TLS 之后 path 参数是被加密的,GFW 看不到;

  2. 主动探测一个 path 产生 Bad request 不能证明是 V2Ray;

  3. 不安全的因素在于人,自己的问题就不要甩锅,哪怕我把示例中的 path 改成一个 UUID,依然有不少人原封不动地 COPY;

  4. 使用 Header 分流并不比 path 安全, 不要迷信。


1.2. 更新历史

  • 2017-12-05 加一些提示

  • 2018-01-03 Update

  • 2018-08-19 Update

  • 2018-08-30 Add configuration for Apache2


1. HTTP/2

简单地说 HTTP/2 是 HTTP/1.1 的升级版(目前大多数网页还是 HTTP/1.1),点击这里可以直观地体会到 HTTP/2 相比于 HTTP/1.1 的提升(不代表 V2Ray 中 HTTP/2 相对于 TCP 的提升就是这样的)。

由于我不清楚 V2Ray 引入 HTTP/2 的意图是什么,V2Ray 的手册也没有对此进行说明,再加上我没怎么测试过 HTTP/2 ,所以呢关于 HTTP/2 有什么高级的姿势我也不甚了解。如果有网友发现了新姿势,欢迎告知。

1.1. 配置

与其它的传输层协议一样在 streamSettings 中配置,不过要注意的是使用 HTTP/2 要开启 TLS。

1.1.1. 服务器配置

{  "inbound": {    "port": 443,    "protocol": "vmess",    "settings": {      "clients": [
        {          "id": "b831381d-6324-4d53-ad4f-8cda48b30811",          "alterId": 64
        }
      ]
    },    "streamSettings": {      "network": "h2", // h2 也可写成 http,效果一样
      "httpSettings": { //此项是关于 HTTP/2 的设置
        "path": "/ray"
      },      "security": "tls", // 配置tls
      "tlsSettings": {        "certificates": [
          {            "certificateFile": "/etc/v2ray/v2ray.crt", // 证书文件,详见 tls 小节
            "keyFile": "/etc/v2ray/v2ray.key" // 密钥文件
          }
        ]
      }
    }
  },  "outbound": {    "protocol": "freedom",    "settings": {}
  }
}

1.1.2. 客户端配置

{  "inbound": {    "port": 1080,    "listen": "127.0.0.1",    "protocol": "socks",    "domainOverride": ["tls","http"],    "settings": {      "auth": "noauth",      "udp": false
    }
  },  "outbound": {    "protocol": "vmess",    "settings": {      "vnext": [
        {          "address": "mydomain.me",          "port": 443,          "users": [
            {              "id": "b831381d-6324-4d53-ad4f-8cda48b30811",              "alterId": 64
            }
          ]
        }
      ]
    },    "streamSettings": {      "network": "h2",      "httpSettings": { //此项是关于 HTTP/2 的设置
        "path": "/ray"
      },      "security": "tls"
    }
  }
}

1.2. 更新历史

  • 2018-03-18 初版

  • 2018-08-30 Update


1. CDN

Cloudflare 还是太慢了,用国内的吧,绝对能体验飞一般的速度,正好 V2Ray 已经支持 HTTP/2 了,又拍云、七牛、阿里都不错,腾讯的 h2 还在内测,百度不清楚。不过说真的,CDN 的话国外的还是有些水土不服,强烈建议使用国内的,速度提升非常大,也非常稳定,高峰期毫无压力,在重点 IP 段也无所畏惧。

1.1. 配置

懒得写怎么配置了,会用 Cloudflare,其他的 CDN 也不会有问题。

1.2. 更新历史

  • 2018-03-18 初版


1. 不推荐的配置

也许有一部分朋友发现了,高级篇的内容关于传输层的,各种配置的组合,可以搭配出非常多的配置。但是,有一些组合是我认为不值得或者是冗余的(仅代表个人意见),以下给出。

  • TLS+KCP

这是相当一部分人喜欢的组合。选用KCP的原因是为了在某些恶劣的网络环境下拥有比较好的上网体验。而使用 TLS 的原因大约有两种考虑:一是认为 TLS 拥有与 HTTPS 一样的特征不容易被墙;二是觉得TLS具有更好的加密效果不容易被墙。对于第一点,尽管 HTTPS 是基于 TLS,但并不等同与 TLS,因此 TLS 与 HTTPS 的特征一样的说法是错误的;对于第二点,使用更强的加密算法而被墙的几率更小这个观点并未得到论证。然而这并不是我不推荐的理由,真正的原因的是不使用 TLS 并没什么坏处,额外使用 TLS也没有足够的好处。

  • TLS+HTTP 伪装

我并没有测试过这个组合,不清楚最外层是 TLS 还是 HTTP 伪装。无论哪一种,处于内层的配置将会失去其意义。

  • 单纯使用 Websocket

理论上,使用 Websocket 会比 TCP 性能差一些,单纯所以如果不是搭配 CDN、nginx 或者在 PaaS 上使用,那还是使用 TCP 吧。


文章版权及转载声明

作者:zhujue本文地址:http://183.162.193.250:5900/post/427.html发布于 2023-12-26 19:42:27
文章转载或复制请以超链接形式并注明出处天云博客

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏

阅读
分享

发表评论

快捷回复:

评论列表 (暂无评论,34人围观)参与讨论

还没有评论,来说两句吧...