Add Tailscale container and bridge setup
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
- Added mikrotik-containers-bridge-setup.rsc for shared container networking - Added mikrotik-tailscale-setup.rsc for Tailscale container - Added docs/10-MIKROTIK-TAILSCALE.md with full documentation - Both containers now use containers-br bridge (172.17.0.1/24) - AdGuard: 172.17.0.2, Tailscale: 172.17.0.3
This commit is contained in:
@@ -94,3 +94,11 @@ For detailed history before 2026-01-17, see archived changelogs:
|
||||
- Fix: Removed and recreated container, added mountlists, restarted
|
||||
- AdGuard config preserved (on separate mount)
|
||||
- Documented fix in 09-MIKROTIK-ADGUARD-DOT-DOH.md
|
||||
- [CONTAINERS] Created container bridge (containers-br) for shared networking
|
||||
- Both AdGuard and Tailscale containers now use the same bridge
|
||||
- Added NAT masquerade for container outbound traffic
|
||||
- [SERVICE] Tailscale container installed and running
|
||||
- Image: tailscale/tailscale:latest
|
||||
- IP: 172.17.0.3/24 on veth-tailscale
|
||||
- State persisted to usb1/tailscale/state
|
||||
- Userspace mode enabled
|
||||
|
||||
146
docs/10-MIKROTIK-TAILSCALE.md
Normal file
146
docs/10-MIKROTIK-TAILSCALE.md
Normal file
@@ -0,0 +1,146 @@
|
||||
# MikroTik Tailscale Container
|
||||
|
||||
**Status:** Completed
|
||||
**Implemented:** 2026-01-25
|
||||
|
||||
---
|
||||
|
||||
## Overview
|
||||
|
||||
Tailscale VPN running as a container on MikroTik for secure remote access to the home network.
|
||||
|
||||
## Architecture
|
||||
|
||||
```
|
||||
┌─────────────────────────────────────────────────────────────────────┐
|
||||
│ MikroTik hAP ax³ │
|
||||
│ │
|
||||
│ ┌───────────────────────────────────────────────────────────────┐ │
|
||||
│ │ containers-br (172.17.0.1/24) │ │
|
||||
│ │ ┌─────────────────┐ ┌─────────────────┐ │ │
|
||||
│ │ │ veth-adguard │ │ veth-tailscale │ │ │
|
||||
│ │ │ 172.17.0.2 │ │ 172.17.0.3 │ │ │
|
||||
│ │ └────────┬────────┘ └────────┬────────┘ │ │
|
||||
│ └───────────┼─────────────────────────┼─────────────────────────┘ │
|
||||
│ │ │ │
|
||||
│ ▼ ▼ │
|
||||
│ ┌─────────────────────┐ ┌─────────────────────┐ │
|
||||
│ │ AdGuard Home │ │ Tailscale │ │
|
||||
│ │ (DNS filtering) │ │ (VPN tunnel) │ │
|
||||
│ └─────────────────────┘ └─────────────────────┘ │
|
||||
│ │ │
|
||||
└─────────────────────────────────────┼────────────────────────────────┘
|
||||
│
|
||||
▼
|
||||
Tailscale Network
|
||||
(100.x.x.x)
|
||||
```
|
||||
|
||||
## Container Configuration
|
||||
|
||||
| Setting | Value |
|
||||
|---------|-------|
|
||||
| Image | tailscale/tailscale:latest |
|
||||
| Interface | veth-tailscale |
|
||||
| Container IP | 172.17.0.3/24 |
|
||||
| Gateway | 172.17.0.1 |
|
||||
| Root dir | usb1/tailscale/root |
|
||||
| Mount | ts-state → /var/lib/tailscale |
|
||||
| Start on boot | yes |
|
||||
|
||||
## Environment Variables
|
||||
|
||||
| Variable | Value | Purpose |
|
||||
|----------|-------|---------|
|
||||
| TS_USERSPACE | true | Run in userspace mode (no kernel module) |
|
||||
| TS_STATE_DIR | /var/lib/tailscale | State persistence directory |
|
||||
| TS_SOCKET | /var/run/tailscale/tailscaled.sock | Socket location |
|
||||
|
||||
## Mounts
|
||||
|
||||
| Name | Source | Destination |
|
||||
|------|--------|-------------|
|
||||
| ts-state | usb1/tailscale/state | /var/lib/tailscale |
|
||||
|
||||
## Setup
|
||||
|
||||
### Prerequisites
|
||||
1. Container bridge must exist (run `mikrotik-containers-bridge-setup.rsc` first)
|
||||
2. USB storage mounted as usb1
|
||||
|
||||
### Initial Setup
|
||||
1. Run `mikrotik-tailscale-setup.rsc` script
|
||||
2. Wait for image extraction
|
||||
3. Check logs for authentication URL:
|
||||
```routeros
|
||||
:log print where message~"login.tailscale"
|
||||
```
|
||||
4. Visit the URL to authenticate with your Tailscale account
|
||||
|
||||
### Manual Setup Commands
|
||||
|
||||
```routeros
|
||||
# Create veth
|
||||
/interface veth add name=veth-tailscale address=172.17.0.3/24 gateway=172.17.0.1
|
||||
|
||||
# Add to bridge
|
||||
/interface bridge port add bridge=containers-br interface=veth-tailscale
|
||||
|
||||
# Create mount
|
||||
/container/mounts/add list=ts-state src=usb1/tailscale/state dst=/var/lib/tailscale
|
||||
|
||||
# Create environment variables
|
||||
/container/envs/add list=ts-env key=TS_USERSPACE value=true
|
||||
/container/envs/add list=ts-env key=TS_STATE_DIR value=/var/lib/tailscale
|
||||
/container/envs/add list=ts-env key=TS_SOCKET value=/var/run/tailscale/tailscaled.sock
|
||||
|
||||
# Create container
|
||||
/container/add remote-image=tailscale/tailscale:latest interface=veth-tailscale root-dir=usb1/tailscale/root logging=yes start-on-boot=yes dns=8.8.8.8 name=tailscale
|
||||
|
||||
# After extraction completes
|
||||
/container/set [find name=tailscale] mountlists=ts-state envlists=ts-env
|
||||
|
||||
# Start
|
||||
/container/start [find name=tailscale]
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Check container status
|
||||
```routeros
|
||||
/container print
|
||||
```
|
||||
|
||||
### Check logs
|
||||
```routeros
|
||||
:log print where topics~"container" and message~"tailscale"
|
||||
```
|
||||
|
||||
### Find authentication URL
|
||||
```routeros
|
||||
:log print where message~"login.tailscale"
|
||||
```
|
||||
|
||||
### Container fails to reach internet
|
||||
1. Verify bridge exists: `/interface bridge print`
|
||||
2. Verify veth is in bridge: `/interface bridge port print`
|
||||
3. Verify NAT rule exists: `/ip firewall nat print where comment~"Container"`
|
||||
4. Check route: `/ip route print where dst-address~"172.17"`
|
||||
|
||||
### Re-authenticate
|
||||
If authentication expires, restart the container and check logs for new auth URL:
|
||||
```routeros
|
||||
/container stop [find name=tailscale]
|
||||
/container start [find name=tailscale]
|
||||
:delay 10s
|
||||
:log print where message~"login.tailscale"
|
||||
```
|
||||
|
||||
## Scripts
|
||||
|
||||
- `scripts/mikrotik-containers-bridge-setup.rsc` - Bridge setup (run first)
|
||||
- `scripts/mikrotik-tailscale-setup.rsc` - Tailscale container setup
|
||||
|
||||
## Related Documents
|
||||
|
||||
- [09-MIKROTIK-ADGUARD-DOT-DOH.md](09-MIKROTIK-ADGUARD-DOT-DOH.md) - AdGuard container setup
|
||||
43
scripts/mikrotik-containers-bridge-setup.rsc
Normal file
43
scripts/mikrotik-containers-bridge-setup.rsc
Normal file
@@ -0,0 +1,43 @@
|
||||
# MikroTik Container Bridge Setup Script
|
||||
# Created: 2026-01-25
|
||||
# Repository: https://git.xtrm-lab.org/jazzymc/infrastructure
|
||||
#
|
||||
# Run this FIRST before setting up containers
|
||||
# Creates shared bridge for all containers
|
||||
|
||||
#------------------------------------------------------------
|
||||
# Variables
|
||||
#------------------------------------------------------------
|
||||
:local bridgeName "containers-br"
|
||||
:local bridgeIP "172.17.0.1"
|
||||
:local bridgeNet "172.17.0.0/24"
|
||||
:local wanInterface "eth1_WAN"
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 1. Create bridge for containers
|
||||
#------------------------------------------------------------
|
||||
/interface bridge add name=$bridgeName
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 2. Add IP address to bridge
|
||||
#------------------------------------------------------------
|
||||
/ip address add address=$bridgeIP/24 interface=$bridgeName
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 3. Firewall - Allow container network traffic
|
||||
#------------------------------------------------------------
|
||||
# Input chain
|
||||
/ip firewall filter add chain=input action=accept dst-address=$bridgeNet comment="Allow container network"
|
||||
/ip firewall filter add chain=input action=accept src-address=$bridgeNet comment="Allow from container network"
|
||||
|
||||
# Forward chain
|
||||
/ip firewall filter add chain=forward action=accept dst-address=$bridgeNet comment="Allow to container network"
|
||||
/ip firewall filter add chain=forward action=accept src-address=$bridgeNet comment="Allow from container network"
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 4. NAT - Masquerade for container outbound traffic
|
||||
#------------------------------------------------------------
|
||||
/ip firewall nat add chain=srcnat action=masquerade src-address=$bridgeNet out-interface=$wanInterface comment="Container outbound NAT"
|
||||
|
||||
:log info "Container bridge setup complete"
|
||||
:log info "Bridge: $bridgeName with IP $bridgeIP/24"
|
||||
65
scripts/mikrotik-tailscale-setup.rsc
Normal file
65
scripts/mikrotik-tailscale-setup.rsc
Normal file
@@ -0,0 +1,65 @@
|
||||
# MikroTik Tailscale Setup Script
|
||||
# Created: 2026-01-25
|
||||
# Repository: https://git.xtrm-lab.org/jazzymc/infrastructure
|
||||
#
|
||||
# Prerequisites:
|
||||
# - RouterOS 7.4+ with container package
|
||||
# - USB storage mounted as usb1
|
||||
# - Container mode enabled: /system/device-mode/update container=yes
|
||||
# - containers-br bridge already exists (from adguard setup)
|
||||
|
||||
#------------------------------------------------------------
|
||||
# Variables
|
||||
#------------------------------------------------------------
|
||||
:local containerName "tailscale"
|
||||
:local containerImage "tailscale/tailscale:latest"
|
||||
:local vethName "veth-tailscale"
|
||||
:local containerIP "172.17.0.3"
|
||||
:local gatewayIP "172.17.0.1"
|
||||
:local containerBridge "containers-br"
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 1. Create veth interface
|
||||
#------------------------------------------------------------
|
||||
/interface veth add name=$vethName address=$containerIP/24 gateway=$gatewayIP
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 2. Add veth to container bridge
|
||||
#------------------------------------------------------------
|
||||
/interface bridge port add bridge=$containerBridge interface=$vethName
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 3. Create container mount for state persistence
|
||||
#------------------------------------------------------------
|
||||
/container/mounts/add list=ts-state src=usb1/tailscale/state dst=/var/lib/tailscale
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 4. Create environment variables
|
||||
#------------------------------------------------------------
|
||||
/container/envs/add list=ts-env key=TS_USERSPACE value=true
|
||||
/container/envs/add list=ts-env key=TS_STATE_DIR value=/var/lib/tailscale
|
||||
/container/envs/add list=ts-env key=TS_SOCKET value=/var/run/tailscale/tailscaled.sock
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 5. Create container
|
||||
#------------------------------------------------------------
|
||||
/container/add remote-image=$containerImage interface=$vethName \
|
||||
root-dir=usb1/tailscale/root logging=yes start-on-boot=yes \
|
||||
dns=8.8.8.8 name=$containerName
|
||||
|
||||
# Wait for image extraction
|
||||
:log info "Waiting for Tailscale image extraction..."
|
||||
:delay 60s
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 6. Add mountlists and envlists to container
|
||||
#------------------------------------------------------------
|
||||
/container/set [find name=$containerName] mountlists=ts-state envlists=ts-env
|
||||
|
||||
#------------------------------------------------------------
|
||||
# 7. Start container
|
||||
#------------------------------------------------------------
|
||||
/container/start [find name=$containerName]
|
||||
|
||||
:log info "Tailscale container started"
|
||||
:log info "Check logs for authentication URL: :log print where message~\"login.tailscale\""
|
||||
Reference in New Issue
Block a user