fix: restore cell WG peer blocks lost from wg0.conf on startup

Cell link [Peer] blocks can vanish from wg0.conf after a container
rebuild or config reset. The startup recovery previously only restored
VPN peer rules (iptables) but not the WireGuard peer blocks needed for
cell-to-cell tunnels, leaving the link red with no automatic recovery.

Add _restore_cell_wg_peers() called from _apply_startup_enforcement()
that reconciles wg0.conf against cell_links.json and re-adds any missing
[Peer] blocks, then calls _syncconf() to hot-reload the interface.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-05-02 01:52:47 -04:00
parent 68c27b4521
commit f2f15eb17e
+36
View File
@@ -264,6 +264,39 @@ def _configured_domain() -> str:
return config_manager.configs.get('_identity', {}).get('domain', 'cell') return config_manager.configs.get('_identity', {}).get('domain', 'cell')
def _restore_cell_wg_peers(cell_links):
"""Re-add any cell link [Peer] blocks that are missing from wg0.conf.
WireGuard peer blocks can be lost if the container is rebuilt or wg0.conf
is regenerated from scratch. Cell link data in cell_links.json is the
authoritative source — this function reconciles the conf file against it.
"""
try:
conf_content = wireguard_manager._read_config()
restored = 0
for link in cell_links:
pk = link.get('public_key', '')
if not pk or pk in conf_content:
continue
name = link.get('cell_name', '')
endpoint = link.get('endpoint', '')
vpn_subnet = link.get('vpn_subnet', '')
ok = wireguard_manager.add_cell_peer(
name=name, public_key=pk,
endpoint=endpoint, vpn_subnet=vpn_subnet,
)
if ok:
logger.info(f"Restored missing WG peer block for cell '{name}'")
restored += 1
else:
logger.warning(f"Failed to restore WG peer block for cell '{name}'")
if restored:
# Reload conf into the running WireGuard interface
wireguard_manager._syncconf()
except Exception as e:
logger.warning(f"_restore_cell_wg_peers failed (non-fatal): {e}")
def _apply_startup_enforcement(): def _apply_startup_enforcement():
try: try:
peers = peer_registry.list_peers() peers = peer_registry.list_peers()
@@ -272,6 +305,9 @@ def _apply_startup_enforcement():
firewall_manager.apply_all_peer_rules(peers) firewall_manager.apply_all_peer_rules(peers)
firewall_manager.apply_all_cell_rules(cell_links) firewall_manager.apply_all_cell_rules(cell_links)
firewall_manager.ensure_cell_api_dnat() firewall_manager.ensure_cell_api_dnat()
# Restore any cell link WireGuard peers that were lost from wg0.conf
# (happens if the container was rebuilt, wg0.conf was reset, etc.)
_restore_cell_wg_peers(cell_links)
wireguard_manager.sync_cell_routes() wireguard_manager.sync_cell_routes()
firewall_manager.apply_all_dns_rules(peers, COREFILE_PATH, _configured_domain(), firewall_manager.apply_all_dns_rules(peers, COREFILE_PATH, _configured_domain(),
cell_links=cell_links) cell_links=cell_links)