background
最初の記事からかなり日が経ってしまいましたが、ついに本題の記事を書きます。日本語の情報はあまり無かったのでこの記事が他の方の役に立つことを願います。
今回は、ShadowSocksとSoftetherの共存環境を作成しました。
概要を説明すると、443ポートでHAProxyが待ち受けし、通信内容でShadowSocksとSoftetherに通信を振り分けています。SoftetherのクライアントアプリがSNIに対応しているため、HAProxyで判定しています。 また、HAProxyがUDP通信に対応していないため、今回の方法だとSoftetherのUDP高速化機能が使えません。(個人的にはあまり恩恵を受けた記憶がないというか・・・そもそも443ポートを使いたい理由ってセキュリティ的に443くらいしか使えない時だからあまり問題ないかも・・・)
ちなみにShadowSocks libevに拡張機能を追加することで似たようなことができるらしいですが、私の環境ではうまく動きませんでした。ちなみに、後日知人から聞いた話だとSentOS8だとパッケージ名が変わっているものがあるらしく、依存関係で正常動作しないことがあるそうなのでそれが原因だったかもしれません。
今回の記事は以下のことを前提に進めます。もし、一から構築するのであれば他の記事も参考にしてください。
CentOS8
ShadowSocksがインストールされている
Softetherがインストールされている サーバーにドメインが紐ついている
もし、インストールがまだであれば以下の記事を参考にインストールして下さい。
CentOS8にShadowSocks libevを構築する
ドメインの紐付けは、SNIとかは意識せずに通常の方法でサーバーIPとドメイン名を紐つけてあり、IPが正引き出来ればば大丈夫です。
SetUp HAProxy
今回の主役であるHAProxyをインストール設定していきます。上のリンクでインストールをしている場合既にShadowSocks、Softetherが443ポートを利用しています。このままだと起動時にポートが競合するので一度両ソフトを停止します。 以下のコマンドで停止できます。(上記記事で設定している場合)
#ShadowSocksの停止
systemctl stop ss.service
systemctl disable ss.service
#softetherの停止
systemctl stop vpnserver.service
systemctl disable vpnserver.service
#必要であれば停止の確認をする
systemctl status ss.service
systemctl status vpnserver.service
アプリを停止したら以下のコマンドでHAProxyをインストールします。
dnf -y install haproxy
インストール後、HAProxyのコンフィグファイルを書き換え設定します。
vi /etc/haproxy/haproxy.cfg
追記内容は以下です。
#---------------------------------------------------------------------
# main frontend which proxys to the backends
#---------------------------------------------------------------------
frontend https
mode tcp
bind *:443
tcp-request inspect-delay 5s
tcp-request content accept if { req.ssl_hello_type 1 }
acl vpn-server req_ssl_sni -i <サーバーのドメイン名>#ShadowSocksにドメイン名で接続する場合削除
acl vpn-server req_ssl_sni -i <サーバーのドメイン名>/tcp#NAT-T mode
use_backend bk-vpn-server if vpn-server
default_backend bk-ss-server
frontend ssl
mode tcp
bind *:443
tcp-request inspect-delay 5s
tcp-request content accept if HTTP
tcp-request content accept if { req.ssl_hello_type 1 }
acl vpn-server req_ssl_sni -i <サーバーのドメイン名>#ShadowSocksにドメイン名で接続する場合削除
acl vpn-server req_ssl_sni -i <サーバーのドメイン名>/tcp#NAT-T mode
use_backend bk-vpn-server if vpn-server
default_backend bk-ss-server
#---------------------------------------------------------------------
# static backend for serving up images, stylesheets and such
#---------------------------------------------------------------------
backend bk-vpn-server
mode tcp
server default 127.0.0.1:3000#Softetherのポート
backend bk-ss-server
mode tcp
server default 127.0.0.1:2000#ShadowSocksのポート
振り分けの設定は、Softetherが接続ドメイン名をサーバーに伝えるため、指定のドメイン名を取得した場合はSoftetherに通信を流し、そうでない場合はShadowSocksに通信を流しています。
ちなみにSoftetherは接続の際にhttpsで接続後SSLで通信をするようなので両方の通信を判定できるようにしないと途中で切断されてしまいます。また、前述の通りHAProxyがUDP通信に対応していないため、SoftetherのUDP高速化機能が使えません。そのため、通常の通信からNAT-Tモードと同じ通信になります。
もしShadowSocksにドメイン名で接続したいのであればコンフィグの指定の行を削除することで通信が可能ですが、Softetherの設定が分かりにくくなるのでおすすめはしません。
defaultsやglobalは変更した記憶がないのとバージョンによって違うので記述しません。
Setting Shadowsocks
ShadowSocksのコンフィグファイルから接続用のポート番号を変更します。 以下のコマンドで変更を行って下さい。(私と同じ設定の場合のパスです)
vi /snap/bin/config.json
{
"server"["[::1]", "127.0.0.1"],
"mode":"tcp_and_udp",
"server_port":2000,
"password":"password",
"timeout":60,
"method":"chacha20-ietf-poly1305",
"nameserver":"1.1.1.1",
"reuse_port": true,
"no_delay": true,
"fast_open": true,
"ipv6_first": true
}
変更箇所は”server_port”です。 “server_port”は任意のポートを指定して下さい。指定する際はHAProxyのShadowSocksのポート番号と同じになるようにして下さい。
Softetherの設定変更
Softetherは管理マネージャからサーバーに接続し、トップ画面左下にあるポートの削除、追加の項目からTCPポート3000を指定することで設定できます。この際、競合を避けるためTCP443ポートを無効、もしくは削除して下さい。
StartUP
全ての設定が終わったら起動していきます。順番はそこまで気にする必要はありませんが、 ベストはHAProxy→ShadowSocks→Softetherです。
以下のコマンドで起動と、自動起動の登録を行って下さい。
#HAProxyの起動
systemctl start haproxy
systemctl enable haproxy
#ShadowSocksの起動
systemctl stop ss.service
systemctl disable ss.service
#softetherの起動
systemctl stop vpnserver.service
systemctl disable vpnserver.service
#起動の確認をする
systemctl status haproxy
systemctl status ss.service
systemctl status vpnserver.service
ステータスにfaildeなどの表示がなく、各クライアントから同時に接続ができれば正常に設定ができています。
設定に間違えがあると想定外の通信が混じったり競合したりします。(実際競合してネットが途切れ途切れになったことがあります。) そんな時はログを見ることでどの通信がどこに割り振られたかを確認することで原因を究明することができるので参考までに記載しておきます。
以下のコマンドで設定を書き換えます。
vi /etc/rsyslog.conf
# Provides UDP syslog reception
# for parameters see http://www.rsyslog.com/doc/imudp.html
#module(load="imudp") # needs to be done just once #ここと
#input(type="imudp" port="514") #ここのコメントを外す
ログの出力先を設定します。
vi /etc/rsyslog.d/haproxy.conf
以下の内容を入力して下さい。
local2.info /var/log/haproxy.log
local2.* ~
最後にHAProxyを再起動して終わりです。
service rsyslog restart
service haproxy restart
ログは以下に保存されます。
cat /var/log/haproxy.log
brief Summary
今回のSoftetherとShadowSocksの共存サーバーは以前からやりたいと思っていたもので、日本語の情報があまりなかったため、英語の読めない自分は割と苦労しました。この記事が誰かの役に立つことを願います。