概要
wg-easyを利用して WireGuard VPNを構築します。
構築する環境
Client PC と Wireguard 間でVPN接続をおこない、Wireguard サーバを経由して、GCPのLAN内にあるApp Serverに接続します。GCP Networkは 10.50.0.0/24 で設定します。

用意するサーバはGCPでなくても構いません。Networkについても 10.50.0.0/24 で設定していますが、ご自身の環境に合わせて設定してください。
事前準備
- GCP FIrewallで
51820/udpと51821/tcpのIngress通信(外部 → GCP)を解放します。 - Wireguard Serverのインスタンスに外部IPをアタッチして、外部通信ができるようにしておきます。
- Wireguard ServerのインスタンスでIP転送を有効にしておきます。(GCPではデフォルトでオフに設定されています。)
- Wireguard Serverのインスタンスに Docker と Docker Compose をインストールします。(参考:https://docs.docker.com/engine/install/)
Wireguard VPN Serverのネットワーク
wg-easyでは、Wireguard Server を Docker bridge Network 上で構築しています。以下でネットワークを整理します。

ホストに元々付与されている Interface が ens4 (10.50.0.1/16)で、他サーバーとの通信はこのInterfaceを利用します。 docker0(172.19.0.1/16)はdockerをインストールすると自動的に作成される bridge network のInterfaceです。新たにcontainerを実行した時にデフォルトでは 172.19.0.0/16 ネットワーク帯のIPが付与されたInterfaceが作成されます。上図では、 wg-easy container の eth0(172.19.0.2/16) に対応します。 wg0(192.168.250.1/24) はwireguard用のInterfaceでこのInterfaceを利用してクライアントPCの 192.168.250.2/24 とVPN接続を行います。
wg-easyの設定方法
wg-easyのリポジトリに docker-compose.yaml のサンプルファイルがあります。こちらを参考に、ファイルを作成します。
version: "3.8"
volumes:
etc_wireguard:
services:
wg-easy:
environment:
- LANG=en
# ⚠️ Required:
# Change this to your host's public address
- WG_HOST=<Host Public IP>
- WG_DEVICE=eth0
- PASSWORD=foobar123
- WG_DEFAULT_ADDRESS=192.168.250.x
- WG_ALLOWED_IPS=192.168.250.0/24, 10.50.0.0/24
image: ghcr.io/wg-easy/wg-easy
container_name: wg-easy
volumes:
- ~/.wg-easy:/etc/wireguard
ports:
- "51820:51820/udp"
- "51821:51821/tcp"
restart: unless-stopped
cap_add:
- NET_ADMIN
- SYS_MODULE
sysctls:
- net.ipv4.ip_forward=1
- net.ipv4.conf.all.src_valid_mark=1環境変数については、最小限の設定にしています。必要な変数がある場合は、こちらを参考に設定します。WG_DEFAULT_ADDRESS は、クライアントIPの取りうるレンジです。末尾の .x の部分がレンジになるので、もしクライアント数が多くてこのレンジに収まらない場合は、 .x.x のように指定する必要があります。 WG_ALLOWED_IPS には、VPN通信に利用するネットワーク192.168.250.0/24とGCP Network 10.50.0.0/24を指定します。このAllowedIPsはクライアントのconfを作成する際に利用されます。
また、上記の設定には表れていませんが、パケットをVPNサーバから他サーバに転送する際には、iptables で FORWARD と MASQUERADE の設定が必要になりますが、wg-easy の Default設定 で実施されるためそのまま利用します。
この設定ファイルを利用して、wg-easyコンテナを起動します。
# docker-compose up -d
# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
ab7211443733 ghcr.io/wg-easy/wg-easy "docker-entrypoint.s…" 13 minutes ago Up 13 minutes 0.0.0.0:51820->51820/udp, :::51820->51820/udp, 0.0.0.0:51821->51821/tcp, :::51821->51821/tcp wg-easy51820->51820/udp がWireguard用のportで、 51821->51821/tcpがWeb UIのためのPortです。
コンテナが起動したらbashで接続します。
docker exec -it wg-easy /bin/bashWireguardとInterfaceを確認します。以下、コマンドの結果を載せます。 eth0(172.19.0.2/16)とwg0(192.168.250.1/24)インターフェースが作成され、iptablesでFORWARDとMASQUERADEが設定されています。
// wireguard 設定確認
# wg
interface: wg0
public key: YtPrFXdBAXKm2cWT3EuRXht/bF0raECsmNZqQLMMrGQ=
private key: (hidden)
listening port: 51820
// eth0 interface 確認
# ip a show eth0
8: eth0@if9: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
link/ether 02:42:ac:13:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 172.19.0.2/16 brd 172.19.255.255 scope global eth0
valid_lft forever preferred_lft forever
// wg0 interface 確認
# ip a show wg0
2: wg0: <POINTOPOINT,NOARP,UP,LOWER_UP> mtu 1420 qdisc noqueue state UNKNOWN group default qlen 1000
link/none
inet 192.168.250.1/24 scope global wg0
valid_lft forever preferred_lft forever
// FORWARD設定確認
# iptables -L -v
...
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
pkts bytes target prot opt in out source destination
0 0 ACCEPT all -- wg0 any anywhere anywhere
0 0 ACCEPT all -- any wg0 anywhere anywhere
// nat テーブル確認
# iptables -L -v -t nat
...
Chain POSTROUTING (policy ACCEPT 0 packets, 0 bytes)
pkts bytes target prot opt in out source destination
0 0 MASQUERADE all -- any eth0 192.168.250.0/24 anywhere
クライアントの設定
サーバーの設定が終わったので、クライアントの設定をします。 WireguardのInstallページから各OSに対応するリンクからインストールします。
先ほど構築したサーバのWeb UI にアクセスします。Web UI にはVPNサーバにアクセスできるPublic IPを使って、 <Public IP>:51821 でアクセスできます。パスワードは、docker-compose.yaml に設定したPASSWORD=foobar123を利用します。
あとは、画面に従ってクライアント用の設定ファイルをダウンロードしてインポートします。

動作確認
クライアント端末から、VPNサーバ、App サーバにアクセスして疎通できるか確認します。
// Wireguard VPN Server
# ping -c 3 192.168.250.1
PING 192.168.250.1 (192.168.250.1): 56 data bytes
64 bytes from 192.168.250.1: icmp_seq=0 ttl=64 time=465.156 ms
64 bytes from 192.168.250.1: icmp_seq=1 ttl=64 time=378.526 ms
64 bytes from 192.168.250.1: icmp_seq=2 ttl=64 time=408.049 ms
// App server
# ping -c 10.50.0.11
PING 10.50.0.11 (10.50.0.11): 56 data bytes
64 bytes from 10.50.0.11: icmp_seq=0 ttl=62 time=605.980 ms
64 bytes from 10.50.0.11: icmp_seq=1 ttl=62 time=390.996 ms
64 bytes from 10.50.0.11: icmp_seq=2 ttl=62 time=366.563 ms以上で設定完了です。複数クライアントを管理したい場合は、wg-easyを使うことで、Web UIからclientファイルの作成ができるため便利そうです。 ~/.wg-easy:/etc/wireguard の設定で、ホストにファイルを保存しているため、このファイルをバックアップすることで簡単に再構築が可能です。