AgentStack
MCP verified MIT Self-run

Mikrotik Mcp

mcp-ali-master-mikrotik-mcp · by ali-master

A Bun-native MCP server that turns one or more MikroTik routers into 706 tools your AI can drive. Firewall · routing · DHCP/DNS · wireless · QoS · and a complete VPN suite — over SSH, with transactional Safe Mode.

No reviews yet
0 installs
19 views
0.0% view→install

Install

$ agentstack add mcp-ali-master-mikrotik-mcp

✓ scanned · ✓ verified — works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access No
  • Shell / process execution No
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

Are you the author of Mikrotik Mcp? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

A Bun-native MCP server that turns one or more MikroTik routers into 706 tools your AI can drive. Firewall · routing · DHCP/DNS · wireless · QoS · and a complete VPN suite — over SSH, with transactional Safe Mode.


@usex/mikrotik-mcp exposes MikroTik RouterOS as 706 Model Context Protocol tools across 111 modules, so an AI client (Claude Desktop, Claude Code, any MCP client) can read and configure your router in plain language. It speaks to the device over SSH — no agent, no API package to install on RouterOS — runs on Bun, and validates every tool call against a Zod schema.

Every tool is risk-annotated (read / write / destructive) so clients can gate what runs, and risky changes can be wrapped in Safe Mode — RouterOS holds them in memory and auto-reverts if your session drops, so you can't lock yourself out.

// claude_desktop_config.json
{
  "mcpServers": {
    "mikrotik": {
      "command": "mikrotik-mcp",
      "env": {
        "MIKROTIK_HOST": "192.168.88.1",
        "MIKROTIK_USERNAME": "admin",
        "MIKROTIK_PASSWORD": "your-password",
      },
    },
  },
}

> "Show me the firewall input chain, then block SSH from the WAN under safe mode." > "Build an IKEv2 site-to-site tunnel to 203.0.113.5 for 192.168.20.0/24." > "Why can't VLAN 50 reach the internet?"

Why it's different

  • 🧰 Breadth — 706 tools covering the whole device: L2 (bridge, VLAN, wireless,

PoE), L3 (addressing, routing, DHCP, DNS), security (firewall, NAT, address-lists, certificates), QoS (queues), and system ops (users, logs, backups, scheduler).

  • 🔐 A complete VPN suite — WireGuard, IPsec (IKEv1/IKEv2), L2TP, PPTP, SSTP,

OpenVPN, plus GRE/IPIP/EoIP/VXLAN tunnels. With a choose-vpn-solution prompt that picks the right one for you. See the [VPN guide](docs/vpn-guide.md).

  • 🛟 Safe Mode — a real transactional window (enable_safe_mode

changes → commit_safe_mode/rollback_safe_mode) backed by a persistent SSH session. Auto-reverts on disconnect.

  • 🚦 Risk-annotated toolsreadOnlyHint / destructiveHint let clients

auto-approve reads and prompt on writes.

  • 🧱 Injection-safe by construction — a command builder quotes/escapes every

value, so a hostname like LAN; /system reset can never split into a second command.

  • 🖧 Multiple devices — define named routers and the AI targets one per call

(a validated device argument). Configure both ends of a tunnel from one conversation. See [docs/multi-device.md](docs/multi-device.md).

  • 🪜 SSH jump hosts — reach a router with no exposed port by tunnelling

through another via jumpVia (ProxyJump/bastion) — commands, Safe Mode and file upload all ride the hop. No new WAN port.

  • Connection pooling — one persistent SSH session per device, reused

across tool calls. Saves ~200-500 ms handshake per command (double through jump hosts). Idle connections auto-close after 30 s.

  • 🤖 Guided prompts — 9 built-in workflows (harden, diagnose, guest Wi-Fi, VPNs,

cross-device tunnels, backup & document) that turn an intent into tool calls.

Quickstart

# 1. Install (requires Bun ≥ 1.3 — https://bun.sh)
bun add -g @usex/mikrotik-mcp

# 2. Point it at your router and verify SSH connectivity
MIKROTIK_HOST=192.168.88.1 MIKROTIK_USERNAME=admin MIKROTIK_PASSWORD=•••• \
  mikrotik-mcp auth-check

# 3. List the catalog (name · risk · title)
mikrotik-mcp tools

# 4. Run it (stdio by default — wire it into your MCP client)
mikrotik-mcp serve

Try it without an AI client — open the official [MCP Inspector](docs/inspector.md) against the server (from source):

bun run inspect        # opens the Inspector UI to browse/run all 706 tools

Prefer SSH keys over a password? Point the server at a key file instead — and add a passphrase if the key is encrypted:

MIKROTIK_HOST=192.168.88.1 MIKROTIK_USERNAME=admin \
MIKROTIK_KEY_FILENAME=~/.ssh/id_ed25519 \
MIKROTIK_KEY_PASSPHRASE=•••• \
  mikrotik-mcp auth-check     # prints "Auth mode: SSH key"

The key (file via --key-filename or inline PEM via --private-key) takes precedence over a password. Full configuration reference: [docs/configuration.md](docs/configuration.md).

From source

git clone https://github.com/ali-master/mikrotik-mcp && cd mikrotik-mcp
bun install
bun run start            # serve from source
bun run build            # bundle to dist/

The tool catalog

706 tools across 111 modules. Full, always-current reference (parameters + risk per tool) is generated from source: [docs/tools-reference.md](docs/tools-reference.md).

| Group | Tools | Modules | | ------------------------ | ----: | ---------------------------------------------------------------------------------------------------------- | | Interfaces | 41 | interfaces, VLAN, bridge, wireless, PoE | | Addressing & Routing | 46 | IP addresses, IP pools, routing, DHCP, DNS | | Dynamic Routing | 99 | router-id, settings, tables, rules, next-hops, filters, BFD, BGP, OSPF, RIP, PIM-SM, IGMP proxy, GMP, RPKI | | Security | 34 | firewall filter, NAT, address-lists, certificates, IP services | | VPN & Tunneling | 96 | WireGuard, IPsec, PPP, L2TP, PPTP, SSTP, OpenVPN, GRE/IPIP/EoIP/VXLAN | | QoS | 19 | queue types, queue trees, simple queues | | System & Ops | 102 | system, network tools, scheduler/scripts, users, logs, backup, Safe Mode |

VPN & tunneling — expert coverage

Every MikroTik VPN technology, modeled the way RouterOS actually layers them (the PPP-based VPNs share one /ppp backend for users and addressing):

| Need | Use | Build it with | | ----------------------------------- | ----------------------- | -------------------------------------------------------------------------------------- | | MikroTik ↔ MikroTik, modern clients | WireGuard | create_wireguard_interface, add_wireguard_peer, generate_wireguard_client_config | | Interop site-to-site / native IKEv2 | IPsec | create_ipsec_{profile,peer,identity,proposal,policy}, get_ipsec_active_peers | | Built-in OS VPN clients | L2TP/IPsec | set_l2tp_server, create_ppp_secret, create_ppp_profile | | Through restrictive firewalls | SSTP (TLS) | set_sstp_server, create_sstp_client | | Cross-platform OpenVPN | OpenVPN | set_ovpn_server, create_ovpn_client | | Route / L2-bridge between sites | GRE/IPIP/EoIP/VXLAN | create_gre_tunnel, create_eoip_tunnel, create_vxlan_tunnel |

Not sure which? Invoke the choose-vpn-solution prompt and the server recommends one and outlines the build. Details: [docs/vpn-guide.md](docs/vpn-guide.md).

Manage multiple devices

Give each router a name and the AI can drive them all from one conversation — exactly what you need to set up a tunnel between two MikroTiks and test it from both ends. Point the server at a JSON file (or MIKROTIK_DEVICES):

// devices.json
{
  "defaultDevice": "site-a",
  "devices": {
    "site-a": { "host": "203.0.113.10", "username": "admin", "keyFilename": "/keys/site-a" },
    "site-b": { "host": "198.51.100.20", "username": "admin", "password": "••••" },
  },
}
mikrotik-mcp serve --config ./devices.json
mikrotik-mcp devices        # site-a (default) · site-b
mikrotik-mcp auth-check     # probes every device

When more than one device is configured, every tool gains an optional device argument (a validated enum of your names); omit it to use the default. The AI discovers names with list_mikrotik_devices, and Safe Mode is per-device so each router commits independently. The setup-tunnel-between-sites prompt drives the whole both-ends flow. Full guide: [docs/multi-device.md](docs/multi-device.md).

// the AI calls a tool against a specific router:
// create_wireguard_interface { "device": "site-a", "name": "wg-to-b", "listen_port": 13231 }

Behind a bastion? Reach a router with no exposed SSH port by jumping through another (OpenSSH-style ProxyJump) — jumpVia names a configured device to tunnel through; commands, Safe Mode and SFTP upload all ride the hop:

"home-ax3": { "host": "10.10.30.100", "username": "admin", "jumpVia": "hex" }

The bastion router needs SSH TCP forwarding enabled (/ip ssh set forwarding-enabled=local). See [docs/multi-device.md](docs/multi-device.md#ssh-jump-hosts-bastion--proxyjump).

Built-in prompts

MCP prompts are one-click guided workflows. This server ships 9 — authored as Markdown in [prompts/](prompts/), so you can edit or add your own without touching code:

harden-router · diagnose-connectivity · setup-guest-wifi · choose-vpn-solution · setup-wireguard-vpn · setup-ipsec-site-to-site · setup-l2tp-ipsec-roadwarrior · setup-tunnel-between-sites · backup-and-document

See [docs/prompts.md](docs/prompts.md).

Transports

| Transport | When | Run | | ------------------- | --------------------------------- | ---------------------------------------------------------------- | | stdio (default) | Claude Desktop, local MCP clients | mikrotik-mcp serve | | streamable-http | Remote / shared, behind a proxy | mikrotik-mcp serve --transport streamable-http --mcp-port 8000 | | sse | Legacy HTTP clients | mikrotik-mcp serve --transport sse |

HTTP transports expose POST /mcp and a GET /health check, with DNS-rebinding protection that reconciles with your bind host automatically. See [docs/transports.md](docs/transports.md).

SSH connection pooling

By default the server keeps one persistent SSH connection per device and opens a fresh exec channel for each tool call — eliminating the ~200-500 ms handshake overhead that a one-shot connection incurs on every command. Through a jump host the savings double (two handshakes avoided). Idle connections are closed automatically after 30 s.

# Disable pooling (revert to one-shot per tool call)
MIKROTIK_SSH__KEEP_ALIVE=false mikrotik-mcp serve

# Tune the idle timeout (ms)
mikrotik-mcp serve --ssh-idle-timeout 60000

In a JSON config file:

{
  "ssh": {
    "keepAlive": true, // default — set false to disable
    "keepAliveInterval": 10000, // SSH keepalive packet interval (ms)
    "idleTimeout": 30000, // close idle connections after (ms)
  },
}

Connection pooling is SSH-only; MAC-Telnet devices always use one-shot connections. Safe Mode still uses its own dedicated persistent session.

Safe Mode

enable_safe_mode → (make changes) → commit_safe_mode    # persist
                                   → rollback_safe_mode  # discard

While active, every change is held in memory; if the SSH session drops (e.g. a firewall rule that locks you out), RouterOS reverts everything automatically. Commands issued during the window are routed through the same persistent session. See [docs/safe-mode.md](docs/safe-mode.md).

Configuration

Connection and transport settings come from MIKROTIK_* env vars or matching CLI flags (highest precedence last: defaults → env → flags).

| Variable | Flag | Default | Purpose | | ----------------------------- | -------------------- | ----------- | ---------------------------------------------------------------------------------------------------- | | MIKROTIK_HOST | --host | 127.0.0.1 | RouterOS host | | MIKROTIK_USERNAME | --username | admin | SSH user | | MIKROTIK_PORT | --port | 22 | SSH port | | MIKROTIK_PASSWORD | --password | — | SSH password (or use a key →) | | MIKROTIK_KEY_FILENAME | --key-filename | — | SSH private-key file path | | MIKROTIK_PRIVATE_KEY | --private-key | — | Inline private key (PEM) | | MIKROTIK_KEY_PASSPHRASE | --key-passphrase | — | Passphrase for an encrypted key | | MIKROTIK_JUMP_HOST | --jump-host | — | SSH bastion to tunnel through ([jump hosts](docs/multi-device.md#ssh-jump-hosts-bastion--proxyjump)) | | MIKROTIK_CONFIG_FILE | --config | — | JSON file of named devices ([multi-device](docs/multi-device.md)) | | MIKROTIK_DEVICES | --devices | — | Inline JSON of named devices | | MIKROTIK_MCP__TRANSPORT | --transport | stdio | stdio / streamable-http / sse | | MIKROTIK_MCP__PORT | --mcp-port | 8000 | HTTP bind port | | MIKROTIK_SSH__KEEP_ALIVE | --ssh-keep-alive | true | SSH connection pooling (reuse connections across tool calls) | | MIKROTIK_SSH__IDLE_TIMEOUT | --ssh-idle-timeout | 30000 | Close idle pooled connections after (ms) | | MIKROTIK_DASHBOARD__ENABLED | --dashboard | false | Real-time observability dashboard ([docs](docs/observability.md)) |

Full table (incl. HTTP host, allow-lists, timeouts, MIKROTIK_LOG_LEVEL): [docs/configuration.md](docs/configuration.md).

Observability dashboard (optional)

A localhost-only web dashboard that intercepts every tool call the LLM makes — live feed of inputs/outputs (secrets redacted), latency percentiles, error rate and per-tool/risk/device analytics — persisted to a Bun-native SQLite store and served on its own port alongside any transport:

mikrotik-mcp serve --dashboard          # → http://127.0.0.1:9090

See [docs/observability.md](docs/observability.md).

Beyond the catalog

On top of the per-scope tools, the server ships higher-level workflows:

  • **[Change Plan & Dry-Run](docs/cha

Source & license

This open-source MCP server is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet — be the first.

Versions

  • v0.1.0 Imported from the upstream source.