依据WCAG 2.2设计和检查Web、iOS及Android界面,核查读屏标签、键盘操作、配色对比度和操作目标尺寸,使界面支持辅助技术。
- 为纯图标按钮添加说明
- 检查键盘操作与模态框焦点
- 检查对比度与操作目标尺寸
帮助配置WireGuard服务器、生成各设备密钥、设置通信路由并排查连接故障,让外出的手机或笔记本电脑能够连接家庭网络。
WireGuard VPN server setup, peer configuration, key generation, split tunneling vs full tunnel routing, and remote access to a home network from mobile and laptop clients. Use when setting up WireGuard for remote access to a home network, or deciding between split and full tunnel routing.
homelab-wireguard-vpn帮助配置WireGuard,让外出的手机或笔记本电脑连接家庭网络。内容包括在Linux上搭建服务器、为每台设备生成公钥与私钥,以及创建客户端配置文件。还说明分流隧道与全隧道的区别:前者只转发访问家庭网络的流量,后者将全部流量经家庭网络转发。
适合从外部访问家中的NAS或Raspberry Pi,或为多台设备统一准备连接配置。无法连接时,可整理通信端口、密钥、IP转发和AllowedIPs等项目的检查步骤。
连接端点需要公网IP或DDNS。请根据实际环境核对示例中的网络名称和转发规则,并在维护时段修改配置。不要分享私钥或将其提交到Git,同时限制文件访问权限。使用全隧道时,家庭宽带的上传速度会限制通信速度。
本介绍由 AI(OpenAI Codex)根据公开的 SKILL.md 撰写。准确的规格请查看下方原文。
AI 仅根据 SKILL.md 的内容,从 4 个方面进行了评估。星标数和热度不计入评估。
总分按每项 A=25 分、B=15 分、C=5 分相加。 由 AI(OpenAI Codex)于 2026年10月19日 评估。仅供参考,安装前请同时查看原文。
安装前可以查看交给 AI 代理的指令内容。
WireGuard is a fast, modern VPN protocol. It is the right choice for remote access to a home network — simpler to configure than OpenVPN and faster than most alternatives.
All configuration examples show common setups. Review each command — especially the iptables forwarding rules and key file permissions — before applying them to your system, and make changes in a maintenance window.
Your phone (WireGuard client)
│
│ Encrypted UDP tunnel (port 51820)
│
Your home router (WireGuard server — needs a public IP or DDNS)
│
Your home network (192.168.1.0/24, NAS, Pi, etc.)
Every device has a keypair (public + private key).
The server knows each client's public key.
The client knows the server's public key + endpoint (IP:port).
Traffic is encrypted end-to-end with no central server or certificate authority.
# Install WireGuard
sudo apt update && sudo apt install wireguard -y
# Generate server keypair — create files with private permissions from the start
sudo mkdir -p /etc/wireguard
sudo sh -c 'umask 077; wg genkey > /etc/wireguard/server_private.key'
sudo sh -c 'wg pubkey < /etc/wireguard/server_private.key > /etc/wireguard/server_public.key'
# Write server config — substitute the actual private key value
# Do not store private keys in version control or share them
sudo tee /etc/wireguard/wg0.conf << 'EOF'
[Interface]
Address = 10.8.0.1/24 # VPN subnet — server gets .1
ListenPort = 51820
PrivateKey = <paste_server_private_key_here>
# Scoped forwarding rules: allow VPN traffic in/out, not a blanket FORWARD ACCEPT
PostUp = iptables -A FORWARD -i wg0 -o eth0 -j ACCEPT
PostUp = iptables -A FORWARD -i eth0 -o wg0 -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
PostUp = iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
PostDown = iptables -D FORWARD -i wg0 -o eth0 -j ACCEPT
PostDown = iptables -D FORWARD -i eth0 -o wg0 -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
PostDown = iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE
[Peer]
# Phone — replace with the actual phone public key
PublicKey = <phone_public_key>
AllowedIPs = 10.8.0.2/32
[Peer]
# Laptop — replace with the actual laptop public key
PublicKey = <laptop_public_key>
AllowedIPs = 10.8.0.3/32
EOF
sudo chmod 600 /etc/wireguard/wg0.conf
# Replace eth0 with your actual outbound interface name
# Check with: ip route show default
# Enable IP forwarding (required for routing traffic through the server)
echo "net.ipv4.ip_forward=1" | sudo tee /etc/sysctl.d/99-wireguard.conf
sudo sysctl --system
# Start WireGuard and enable on boot
sudo wg-quick up wg0
sudo systemctl enable wg-quick@wg0
# Generate a unique keypair for each client device
# Run on the client, or on the server and transfer the private key securely — never in plaintext
umask 077
wg genkey | tee phone_private.key | wg pubkey > phone_public.key
# Client config file (phone_wg0.conf):
[Interface]
PrivateKey = <phone_private_key>
Address = 10.8.0.2/32
DNS = 192.168.1.2 # Optional: use Pi-hole for DNS over the tunnel
[Peer]
PublicKey = <server_public_key>
Endpoint = your-home-ip.ddns.net:51820 # Your public IP or DDNS hostname
AllowedIPs = 192.168.1.0/24 # Split tunnel: only home network traffic
# AllowedIPs = 0.0.0.0/0, ::/0 # Full tunnel: all traffic through VPN
PersistentKeepalive = 25 # Keep NAT hole open (required for mobile clients)
# Split tunnel: AllowedIPs = 192.168.1.0/24
Only traffic destined for your home network goes through the VPN.
Internet traffic (YouTube, Spotify) goes directly — better performance on mobile.
Best for: "I just want to reach my NAS and Pi from anywhere."
# Full tunnel: AllowedIPs = 0.0.0.0/0, ::/0
ALL traffic goes through your home internet connection.
Useful for: piggybacking home DNS/Pi-hole ad blocking.
Downside: home upload speed becomes your bottleneck everywhere.
# Multi-subnet split tunnel (most common homelab use case):
AllowedIPs = 192.168.10.0/24, 192.168.20.0/24, 192.168.30.0/24, 10.8.0.0/24
Routes all your VLANs through the tunnel; internet stays direct.
import subprocess
def generate_keypair() -> tuple[str, str]:
"""Generate a WireGuard keypair. Returns (private_key, public_key)."""
private = subprocess.check_output(["wg", "genkey"]).decode().strip()
public = subprocess.run(
["wg", "pubkey"], input=private.encode(), capture_output=True
).stdout.decode().strip()
return private, public
def generate_preshared_key() -> str:
return subprocess.check_output(["wg", "genpsk"]).decode().strip()
def build_client_config(
client_private_key: str,
client_vpn_ip: str, # e.g. "10.8.0.3"
server_public_key: str,
server_endpoint: str, # e.g. "home.example.com:51820"
allowed_ips: str = "192.168.1.0/24",
dns: str = "",
) -> str:
dns_line = f"DNS = {dns}\n" if dns else ""
return f"""[Interface]
PrivateKey = {client_private_key}
Address = {client_vpn_ip}/32
{dns_line}
[Peer]
PublicKey = {server_public_key}
Endpoint = {server_endpoint}
AllowedIPs = {allowed_ips}
PersistentKeepalive = 25
"""
def build_server_peer_block(
client_public_key: str,
client_vpn_ip: str,
comment: str = "",
) -> str:
comment_line = f"# {comment}\n" if comment else ""
return f"""
{comment_line}[Peer]
PublicKey = {client_public_key}
AllowedIPs = {client_vpn_ip}/32
"""
Keep private keys out of source control. If you use this script, write key material to files with mode 600 and never log or print it.
# pfSense: VPN → WireGuard → Add Tunnel
Interface Keys: Generate (creates keypair automatically)
Listen Port: 51820
Interface Address: 10.8.0.1/24
# Add Peer (one per client):
Public Key: <client public key>
Allowed IPs: 10.8.0.2/32
# Assign the WireGuard interface:
Interfaces → Assignments → Add (select wg0)
Enable interface, no IP needed (it is set in the tunnel config)
# Firewall rules:
WAN → Allow UDP port 51820 inbound (so clients can reach the server)
WireGuard interface → Allow traffic to LAN networks you want reachable
Most home internet connections have a dynamic IP. Use DDNS so your VPN endpoint stays reachable after an IP change.
# Option 1: Cloudflare DDNS — store credentials in a secrets file, not inline
# docker-compose entry using an env file:
ddns-updater:
image: qmcgaw/ddns-updater
env_file: ./ddns.env # store zone_id and token here, not in compose
restart: unless-stopped
# ddns.env (chmod 600, not committed to git):
# SETTINGS_CLOUDFLARE_ZONE_ID=your_zone_id
# SETTINGS_CLOUDFLARE_TOKEN=your_api_token
# Option 2: DuckDNS (free, simple)
Sign up at duckdns.org → get a token and subdomain (myhome.duckdns.org)
Store token in /etc/ddns.env (mode 600), then use a small root-owned script:
# /usr/local/bin/update-duckdns
#!/bin/sh
set -eu
. /etc/ddns.env
curl --fail --silent --show-error --max-time 10 \
--get "https://www.duckdns.org/update" \
--data-urlencode "domains=myhome" \
--data-urlencode "token=${DUCKDNS_TOKEN}" \
--data-urlencode "ip="
# Cron job:
*/5 * * * * /usr/local/bin/update-duckdns >/dev/null 2>&1
# Check WireGuard status and last handshake
sudo wg show
# If "latest handshake" is never or very old, the tunnel is not connected.
# Check:
# 1. Is UDP port 51820 open on the router/firewall?
sudo ufw status # or check pfSense/UniFi firewall rules
# 2. Is the server public key in the client config correct?
sudo wg show wg0 public-key # Compare to what is in the client config
# 3. Is IP forwarding enabled on the server?
cat /proc/sys/net/ipv4/ip_forward # Should be 1
# 4. Does the client AllowedIPs cover the IP you are trying to reach?
# If AllowedIPs = 192.168.1.0/24 and you are trying to reach 192.168.3.5, it will not route.
# Check kernel logs for WireGuard errors
dmesg | grep wireguard
# Restart WireGuard
sudo wg-quick down wg0 && sudo wg-quick up wg0
# BAD: Storing private keys in version control or sharing them
# Private keys are equivalent to passwords — never commit them to git
# BAD: Using AllowedIPs = 0.0.0.0/0 on mobile without considering the impact
# Full tunnel routes all mobile traffic through your home upload — usually slow
# BAD: Not setting PersistentKeepalive on mobile clients
# Mobile clients behind NAT drop idle tunnels without it
# BAD: Opening port 51820 in the firewall but forgetting IP forwarding on the server
# Tunnel connects but no traffic routes — confusing to debug
# BAD: Sharing a keypair across multiple client devices
# Each device must have its own unique keypair — shared keys break the security model
# BAD: Using a broad "FORWARD ACCEPT" iptables rule
# Scope forwarding rules to the wg0 interface and direction only
AllowedIPs = <home subnets>) for mobilePersistentKeepalive = 25 on all mobile clientsDNS = in client configs to get ad blocking over the VPN还没有评价。欢迎分享你的使用感受。
无需登录即可发表。欢迎分享使用感受、提问,或说明在哪些环境下无法运行。
还没有评论。来写第一条吧。
依据WCAG 2.2设计和检查Web、iOS及Android界面,核查读屏标签、键盘操作、配色对比度和操作目标尺寸,使界面支持辅助技术。
从指令、记忆、工具执行和界面显示等十二个层面排查人工智能代理故障,依据代码和日志梳理原因,按严重程度列出问题并提出修复方案。
用实际开发任务比较多个编程智能体,记录成功率、可获取的API费用、耗时和重复运行的稳定性,为工具选型及更新后的性能评估提供数据。
设计和调整AI智能体使用的工具、输入与返回格式,明确出错后的恢复、重试和停止条件,管理上下文信息量,并以完成率、重试次数和成功任务成本评估改进。
根据错误信息和执行环境,分析AI代理反复失败或重复操作的原因。通过小范围、可撤销的恢复操作检验假设,并将结果与依据整理成可供交接的报告。
在AI代理反复失败或重复操作时,记录错误与环境前提、排查原因,采取影响有限的恢复操作,并汇总结果和证据,为有依据的重试与交接提供支持。