TunnelMesh Admin Guide
This guide explains how admin authorisation works in TunnelMesh, what functionality requires admin access, and security best practices.
Overview
TunnelMesh uses a configuration-based admin model where admin privileges are granted via the
coordinator's admin_peers field. There is no "first user becomes admin" behaviour - admins must be
explicitly configured.
Key points:
- Admin peers are configured in the coordinator's config file
- Matching is done by peer name OR peer ID (16 hex characters)
- Peer IDs are preferred for security (immutable, tied to SSH key)
- Network functionality works without admin access
- Admin access enables mesh/data plane configuration
Configuring Admin Peers
Admin peers are specified in the coordinator's configuration file:
# coordinator.yaml
coordinator:
enabled: true
listen: ":8443"
# Admin peers - match by name or peer ID
admin_peers:
- "coordinator" # Peer name (convenient but mutable)
- "alice" # Peer name
- "a1b2c3d4e5f6g7h8" # Peer ID (preferred - 16 hex chars)
Peer Name vs Peer ID Matching
TunnelMesh supports two methods for identifying admin peers:
Peer Name Matching
Format: Any valid peer name (hostname-style, e.g., "alice", "server-1")
Pros:
- Easy to configure before peers join
- Human-readable
Cons:
- Users can change their peer name
- Less secure
- Coordinator logs a warning when using name matching
Example:
admin_peers: ["alice", "bob", "coordinator"]
Peer ID Matching (Recommended)
Recommended: Use peer IDs for security. They're immutable and tied to SSH keys.
Format: 16 hexadecimal characters (SHA256 of SSH public key, first 8 bytes)
Example peer ID: a1b2c3d4e5f6g7h8
Pros:
- Immutable (tied to SSH key)
- Cannot be changed by user
- More secure
- Coordinator logs "matched by peer ID (secure)"
Cons:
- Must obtain peer ID first (requires peer to join once, or copy from
tunnelmesh status)
Example:
admin_peers: ["a1b2c3d4e5f6g7h8", "i9j0k1l2m3n4o5p6"]
How to Get Peer IDs
There are two methods to obtain a peer's ID:
Method 1: After First Join
- Have the peer join the mesh (with or without admin rights)
- Run
tunnelmesh statuson the peer - Copy the peer ID from the output (16 hex characters)
- Update coordinator config with the peer ID
# On the peer
tunnelmesh status
# Output includes:
# Peer ID: a1b2c3d4e5f6g7h8
Method 2: Calculate from SSH Key
If you have access to the peer's SSH public key:
# Extract peer ID from public key
ssh-keygen -l -f ~/.tunnelmesh/id_ed25519.pub | awk '{print $2}' | \
base64 -d | xxd -p | head -c 16
This gives you the 16-character peer ID before the peer joins.
How Admin Authorisation Works
When a peer joins the mesh, the coordinator performs the following steps:
- Peer Registers: Peer sends join request with public key
- Generate Peer ID: Coordinator computes
SHA256(public_key)[:8]as hex (16 chars) - Check admin_peers: Coordinator checks if peer name OR peer ID is in admin_peers list
- Grant Admin Access: If matched:
- Peer is added to "admins" group
- Full admin RBAC role is granted
- Admin-only panels become accessible
- Logs show match reason: "matched by peer ID (secure)" or "matched by name (warning: mutable)"
- Regular Access: If not matched:
- Peer is added to "everyone" group only
- Network functionality works normally
- Admin features are denied
Implementation location: internal/coord/server.go:1547-1573
What Works Without Admin Access
All core mesh networking features work for non-admin peers:
Network Layer (Always Available)
- ✅ Join the mesh and register with coordinator
- ✅ Establish encrypted tunnels (SSH, UDP, or relay)
- ✅ Route IP traffic through the mesh
- ✅ Access services on other peers
- ✅ Use mesh DNS resolution (
peer.tunnelmesh) - ✅ NAT traversal (UDP hole-punching)
- ✅ Automatic transport fallback
- ✅ Network monitoring and reconnection
Performance & Diagnostics
- ✅ Speed test to other peers (
tunnelmesh benchmark) - ✅ Check own connection status (
tunnelmesh status) - ✅ Resolve mesh hostnames (
tunnelmesh resolve)
VPN Features
- ✅ Use exit peers for split-tunnel VPN
- ✅ Serve as exit peer (if
allow_exit_traffic: true)
Storage (With RBAC Permissions)
- ✅ Access S3 buckets (if granted via RBAC bindings)
- ✅ List/read/write objects (based on role)
- ✅ Use file shares (if granted permissions)
Dashboard (Limited)
- ✅ View non-admin panels: visualizer, map, alerts, s3, shares
- ✅ View mesh topology
- ✅ See geographic map (if location data available)
Summary: Non-admin peers can fully participate in the mesh network and access services. They just cannot configure or manage mesh-wide settings.
What Requires Admin Access
Admin access is required for mesh/data plane configuration and management:
Peer Management
- ❌ View detailed peer stats (bandwidth, latency, connection types)
- ❌ Force transport changes for peers
- ❌ View peer logs via admin panel
- ❌ View peer connection history
Network Configuration
- ❌ Configure packet filter rules (port-based firewall)
- ❌ Create/modify/delete filter rules
- ❌ Set global filter policies
- ❌ View filter metrics
Storage Management
- ❌ Create S3 buckets
- ❌ Delete S3 buckets
- ❌ Create file shares
- ❌ Delete file shares
- ❌ Configure bucket policies
User & Access Management
- ❌ View users and groups
- ❌ Create/delete users
- ❌ Manage group memberships
- ❌ Create RBAC role bindings
- ❌ Grant/revoke permissions
Docker Orchestration
- ❌ View Docker containers
- ❌ Start/stop/restart containers
- ❌ View container stats and logs
DNS Management
- ❌ Configure mesh DNS records
- ❌ View DNS resolver stats
Dashboard Access
- ❌ Access admin panels (Mesh: peers, logs, filter; App: docker; Data: peers-mgmt, groups, bindings, dns)
Summary: Admin access is for configuration, not for basic mesh usage. If you just need to use the mesh network and access services, you don't need admin rights.
Admin Panel Access
The admin dashboard is accessible at https://this.tm/ from within the mesh.
Panel Visibility
Panels are controlled by the RBAC system. The dashboard has three tabs: Mesh, App, and Data.
Mesh Tab
| Panel ID | Display Name | Admin Only | Grantable to Non-Admins |
|---|---|---|---|
visualizer |
Network Topology | No | N/A (public) |
map |
Node Locations | No | N/A (public) |
alerts |
Active Alerts | No | N/A (public) |
peers |
Connected Peers | Yes | Yes (role binding) |
logs |
Peer Logs | Yes | Yes (role binding) |
filter |
Packet Filter | Yes | Yes (role binding) |
App Tab
| Panel ID | Display Name | Admin Only | Grantable to Non-Admins |
|---|---|---|---|
s3 |
Objects | No | N/A (public) |
shares |
Shares | No | N/A (public) |
docker |
Docker Containers | Yes | Yes (role binding) |
Data Tab
| Panel ID | Display Name | Admin Only | Grantable to Non-Admins |
|---|---|---|---|
peers-mgmt |
Peers | Yes | Yes (role binding) |
groups |
Groups | Yes | Yes (role binding) |
bindings |
Role Bindings | Yes | Yes (role binding) |
dns |
DNS Records | Yes | Yes (role binding) |
Granting Panel Access to Non-Admins
You can grant access to specific admin panels without full admin rights:
# Grant access to Docker panel only
tunnelmesh role bind alice panel-viewer --panel-scope docker
# Grant access to filter panel
tunnelmesh role bind bob panel-viewer --panel-scope filter
# Grant multiple panel access via group
tunnelmesh group create monitoring-users
tunnelmesh group add-member monitoring-users alice
tunnelmesh group bind monitoring-users panel-viewer --panel-scope peers
tunnelmesh group bind monitoring-users panel-viewer --panel-scope logs
See the User Identity and RBAC Guide for complete RBAC documentation.
Security Considerations
Use Peer IDs, Not Names
Security Best Practice: Always use peer IDs, not names, for admin_peers in production. Peer names can be changed by users, while peer IDs are immutable and tied to SSH keys.
Recommended configuration:
coordinator:
admin_peers: ["a1b2c3d4e5f6g7h8"] # Peer ID - immutable
Avoid (except for initial setup):
coordinator:
admin_peers: ["alice"] # Name - can be changed by user
Why?
- Peer names can be changed by users (via config or CLI)
- Peer IDs are derived from SSH keys (immutable)
- An attacker with SSH key access can change their peer name to match admin_peers
- Peer ID matching ensures only the correct SSH key holder gets admin access
Initial Setup Pattern
For convenience during initial setup, you can use names temporarily:
Bootstrap coordinator with name:
admin_peers: ["coordinator"]Start coordinator and join:
tunnelmesh joinGet peer ID:
tunnelmesh status # Note the peer ID (16 hex chars)Update config with peer ID:
admin_peers: ["a1b2c3d4e5f6g7h8"] # Replace name with IDRestart coordinator:
sudo systemctl restart tunnelmesh
Now admin access is tied to the SSH key, not the mutable peer name.
Protect Coordinator Config
Protect your coordinator config file: The admin_peers list controls who gets admin access. Set restrictive permissions to prevent unauthorised modifications.
# Set restrictive permissions
sudo chown root:root /etc/tunnelmesh/coordinator.yaml
sudo chmod 600 /etc/tunnelmesh/coordinator.yaml
Only root (or the coordinator service user) should be able to read/write this file.
Audit Admin Actions
Admin actions are logged by the coordinator. Monitor logs for suspicious activity:
# View coordinator logs
sudo journalctl -u tunnelmesh -f
# Grep for admin matches
sudo journalctl -u tunnelmesh | grep "matched by"
Look for:
matched by peer ID (secure)- Normal, secure matchingmatched by name (warning: mutable)- Name matching (consider switching to peer ID)
Revoke Admin Access
To revoke admin access:
Remove from admin_peers list:
admin_peers: # - "alice" # Removed - "a1b2c3d4e5f6g7h8"Restart coordinator:
sudo systemctl restart tunnelmeshPeer must re-join to lose admin privileges:
- Peer's existing session retains admin until reconnect
- On next heartbeat/reconnect, coordinator will not grant admin
- Peer is moved from "admins" group to "everyone" group only
To force immediate revocation, use the admin panel to disconnect the peer.
Examples
Example 1: Single Admin (Peer ID)
Scenario: Coordinator peer is the only admin.
# coordinator.yaml
name: "coordinator"
coordinator:
enabled: true
listen: ":8443"
admin_peers:
- "a1b2c3d4e5f6g7h8" # Coordinator's peer ID
Steps:
- Bootstrap coordinator:
tunnelmesh join - Get peer ID:
tunnelmesh status - Update config with peer ID
- Restart:
sudo systemctl restart tunnelmesh
Result: Only the coordinator peer (with specific SSH key) has admin access. All other peers have network access only.
Example 2: Multiple Admins (Mixed Mode)
Scenario: Coordinator and two trusted peers are admins.
# coordinator.yaml
coordinator:
enabled: true
listen: ":8443"
admin_peers:
- "a1b2c3d4e5f6g7h8" # Coordinator peer ID
- "i9j0k1l2m3n4o5p6" # Alice's peer ID
- "bob" # Bob's name (temporary)
Steps:
- Configure coordinator with coordinator's peer ID
- Add Alice's peer ID (obtained after first join or from SSH key)
- Temporarily add Bob's name until you get his peer ID
- After Bob joins, get his peer ID:
tunnelmesh status(run by Bob) - Replace "bob" with Bob's peer ID in config
- Restart coordinator
Result: Three peers with admin access, all using immutable peer IDs.
Example 3: Name-Based (Development Only)
Scenario: Local development mesh where security is not critical.
# coordinator.yaml
coordinator:
enabled: true
listen: ":8443"
admin_peers:
- "coordinator"
- "laptop"
- "desktop"
Name matching is convenient but less secure. Only use in development/testing environments.
Example 4: No Admins (Public Mesh)
Scenario: Public mesh where no one has admin access (monitoring only).
Advanced use case: With an empty admin_peers list, you won't be able to manage the mesh via UI. All configuration must be done via config files.
# coordinator.yaml
coordinator:
enabled: true
listen: ":8443"
admin_peers: [] # Empty list
Result:
- All peers have network functionality only
- No one can access admin panels or configure mesh settings
- Useful for read-only/monitoring deployments
Troubleshooting
"Access Denied" in Admin Panel
Symptoms: Can access visualizer/map panels, but admin panels show "Access Denied".
Cause: Your peer is not in the admin_peers list.
Solution:
Check if you're in admin_peers:
# On coordinator grep admin_peers /etc/tunnelmesh/coordinator.yamlGet your peer ID:
tunnelmesh status # Look for "Peer ID: abc123..."Add your peer ID to admin_peers:
admin_peers: - "your-peer-id-here"Restart coordinator:
sudo systemctl restart tunnelmeshReconnect your peer (or wait for next heartbeat)
Admin Access Works, Then Stops
Symptoms: Had admin access, now it's gone after restarting peer.
Cause: Coordinator config changed, or peer name changed.
Solution:
Check coordinator logs:
sudo journalctl -u tunnelmesh | grep "matched by"Look for:
- No match logged = not in admin_peers
- "matched by name" = using name matching (check if name changed)
Verify your peer ID hasn't changed (SSH key replacement):
tunnelmesh statusUpdate admin_peers with correct peer ID or name
Coordinator Logs "matched by name (warning: mutable)"
Symptoms: Admin access works, but logs show warning.
Cause: Using name matching instead of peer ID matching.
Solution: Switch to peer ID matching (recommended):
- Get peer ID:
tunnelmesh status - Replace name with peer ID in config
- Restart coordinator
This is not an error, just a security recommendation.
Multiple Peers, Wrong One Has Admin
Symptoms: Different peer than expected has admin access.
Cause: Name collision or peer ID mismatch.
Solution:
Check which peer matched:
sudo journalctl -u tunnelmesh | grep "admin peer matched"Verify peer IDs:
# On each peer tunnelmesh statusUpdate admin_peers with correct peer IDs (not names)
Can't Access Dashboard at All
Symptoms: Cannot access https://this.tm/ from mesh peer.
Cause: Not a part of the mesh, or DNS/routing issue.
Solution:
Verify mesh connectivity:
tunnelmesh status tunnelmesh peersCheck if coordinator is reachable:
ping this.tm curl -k https://this.tm/Check mesh DNS is working:
tunnelmesh resolve coordinatorVerify TUN interface is up:
ip addr show tun-mesh0
This is not an admin issue - it's a connectivity issue. See the Getting Started Guide for troubleshooting mesh connectivity.
Related Documentation
- User Identity and RBAC - User authentication, peer IDs, role-based access control
- Getting Started Guide - Initial setup and configuration
- CLI Reference - Command-line tools for management
- Internal Packet Filter - Port-based firewall configuration
Summary
Key takeaways:
- ✅ Admin access is explicitly configured via
admin_peersfield - ✅ Use peer IDs (16 hex chars) for security, not peer names
- ✅ Network functionality works without admin access
- ✅ Admin access enables configuration and management
- ✅ Get peer ID with
tunnelmesh status - ✅ Protect coordinator config file with restrictive permissions
- ✅ Monitor logs for admin matches and security events
For quick setup: use peer names initially, then switch to peer IDs for production security.
TunnelMesh is released under the AGPL-3.0 License.