jpskill.com
📦 その他 コミュニティ

routeros-firewall

RouterOSのファイアウォール設定(フィルタ、NAT、mangle、アドレスリスト)を記述、設定、管理する際に、DNSリダイレクトやポートフォワード、MikroTik関連の設定を効率的に行うためのスクリプトを作成するSkill。

📜 元の英語説明(参考)

RouterOS firewall filter, NAT, mangle, and address-list configuration. Use when: writing firewall rules in RouterOS, configuring NAT, setting up address-lists or interface-lists, writing idempotent firewall scripts, configuring DNS redirect or port forwarding, or when the user mentions /ip/firewall, chain=forward, chain=input, connection-state, address-list, interface-list, or layer7-protocol on MikroTik.

🇯🇵 日本人クリエイター向け解説

一言でいうと

RouterOSのファイアウォール設定(フィルタ、NAT、mangle、アドレスリスト)を記述、設定、管理する際に、DNSリダイレクトやポートフォワード、MikroTik関連の設定を効率的に行うためのスクリプトを作成するSkill。

※ jpskill.com 編集部が日本のビジネス現場向けに補足した解説です。Skill本体の挙動とは独立した参考情報です。

⚡ おすすめ: コマンド1行でインストール(60秒)

下記のコマンドをコピーしてターミナル(Mac/Linux)または PowerShell(Windows)に貼り付けてください。 ダウンロード → 解凍 → 配置まで全自動。

🍎 Mac / 🐧 Linux
mkdir -p ~/.claude/skills && cd ~/.claude/skills && curl -L -o routeros-firewall.zip https://jpskill.com/download/20952.zip && unzip -o routeros-firewall.zip && rm routeros-firewall.zip
🪟 Windows (PowerShell)
$d = "$env:USERPROFILE\.claude\skills"; ni -Force -ItemType Directory $d | Out-Null; iwr https://jpskill.com/download/20952.zip -OutFile "$d\routeros-firewall.zip"; Expand-Archive "$d\routeros-firewall.zip" -DestinationPath $d -Force; ri "$d\routeros-firewall.zip"

完了後、Claude Code を再起動 → 普通に「動画プロンプト作って」のように話しかけるだけで自動発動します。

💾 手動でダウンロードしたい(コマンドが難しい人向け)
  1. 1. 下の青いボタンを押して routeros-firewall.zip をダウンロード
  2. 2. ZIPファイルをダブルクリックで解凍 → routeros-firewall フォルダができる
  3. 3. そのフォルダを C:\Users\あなたの名前\.claude\skills\(Win)または ~/.claude/skills/(Mac)へ移動
  4. 4. Claude Code を再起動

⚠️ ダウンロード・利用は自己責任でお願いします。当サイトは内容・動作・安全性について責任を負いません。

🎯 このSkillでできること

下記の説明文を読むと、このSkillがあなたに何をしてくれるかが分かります。Claudeにこの分野の依頼をすると、自動で発動します。

📦 インストール方法 (3ステップ)

  1. 1. 上の「ダウンロード」ボタンを押して .skill ファイルを取得
  2. 2. ファイル名の拡張子を .skill から .zip に変えて展開(macは自動展開可)
  3. 3. 展開してできたフォルダを、ホームフォルダの .claude/skills/ に置く
    • · macOS / Linux: ~/.claude/skills/
    • · Windows: %USERPROFILE%\.claude\skills\

Claude Code を再起動すれば完了。「このSkillを使って…」と話しかけなくても、関連する依頼で自動的に呼び出されます。

詳しい使い方ガイドを見る →
最終更新
2026-05-18
取得日時
2026-05-18
同梱ファイル
3

📖 Skill本文(日本語訳)

※ 原文(英語/中国語)を Gemini で日本語化したものです。Claude 自身は原文を読みます。誤訳がある場合は原文をご確認ください。

RouterOS ファイアウォール

ルールの順序付け — 優先度ではなくシーケンシャル

ルールは上から下へ評価され、最初に一致したものが適用されます。これは iptables の混乱の最大の原因です。

  • place-before=0 は一番上に挿入します。デフォルトの add は一番下に追加します。
  • action=accept ルールは、同じトラフィックに対する action=drop ルールよりも前に記述する必要があります。
  • 非終端アクションは評価を停止しません: action=add-src-to-address-listaction=add-dst-to-address-listaction=log、および passthrough=yes を持つすべてのルールは、次のルールに進みます。add-src-to-address-list の下にある drop ルールは引き続き実行されます。
# 間違い — accept が一致する前に drop が実行される
/ip/firewall/filter/add chain=input action=drop
/ip/firewall/filter/add chain=input src-address=10.0.0.1 action=accept

# 正しい — accept が最初、残りは drop が処理する
/ip/firewall/filter/add chain=input src-address=10.0.0.1 action=accept place-before=0
/ip/firewall/filter/add chain=input action=drop

動的セレクターとしての Address-Lists

LLM はこのパターンを提案することはめったにありません。代わりに、IP アドレスごとに1つのルールを作成します。Address-lists は、単一のファイアウォールルールで数百の IP に対応できます。

# リストを作成する (静的または自動期限付きの動的)
/ip/firewall/address-list/add list=trusted-mgmt address=192.168.1.0/24
/ip/firewall/address-list/add list=trusted-mgmt address=10.0.0.5 timeout=1h

# 1つのルールですべてのリストメンバーを処理する
/ip/firewall/filter/add chain=input src-address-list=trusted-mgmt action=accept \
  comment="myapp-accept-mgmt"

timeout= を持つ動的エントリは自動的に期限切れになります。これは DoS ブラックリストの主要なパターンです。

ルールセレクターとしての Interface-Lists

in-interface-list= / out-interface-list= — LLM が決して提案しない強力な RouterOS パターンです。複数のインターフェースが同じ役割を果たす場合に、重複するルールを排除します。

# グループを一度定義する
/interface/list/add name=WAN
/interface/list/member/add list=WAN interface=ether1
/interface/list/member/add list=WAN interface=pppoe-out1

# 1つのルールがすべての WAN インターフェースに適用される
/ip/firewall/filter/add chain=input in-interface-list=WAN action=drop \
  comment="myapp-drop-all-wan"

コメントをタグとして使用するパターン (べき等スクリプト)

RouterOS には「upsert」がありません。クリーンアップせずにスクリプトを再実行すると、重複するルールが作成されます。コメントプレフィックスをタグとして使用してください。

# 自身が所有するルールのみを削除する — 他のツールからのルールは保持される
/ip/firewall/filter/remove [find comment~"myapp-"]
/ip/firewall/address-list/remove [find comment~"myapp-"]
/ip/firewall/nat/remove [find comment~"myapp-"]

# 一貫したタグで追加する — /print 出力で読みやすい
/ip/firewall/filter/add chain=input src-address-list=trusted-mgmt action=accept \
  comment="myapp-accept-mgmt"
/ip/firewall/filter/add chain=input in-interface-list=WAN action=drop \
  comment="myapp-drop-wan"

remove [find dynamic=no] は絶対に使用しないでください — これは、管理ツールによって追加されたものを含む、すべての静的ルールを削除します。一部のツール (例: OptiWize) は、ルールに comment~"#orchestrator-*" のマークを付けます。一括削除はリモート管理をサイレントに破壊します。

接続状態

RouterOS の connection-state= は iptables の -m state とは異なります。

/ip/firewall/filter/add chain=input connection-state=established,related action=accept
/ip/firewall/filter/add chain=input connection-state=invalid action=drop

RouterOS の状態: newestablishedrelatedinvaliduntracked

untracked/ip/firewall/raw action=notrack を介して明示的にマークされたパケットに一致します。FastTrack フローには一致しません。FastTrack は、フローを conntrack に保持しながら mangle をバイパスする別の高速パスです。fasttrack-connection と mangle ベースのルーティングマークを同じトラフィックで組み合わせないでください。mangle マークは fasttracked パケットには適用されません。

NAT パターン

# ポートフォワード (dst-nat)
/ip/firewall/nat/add chain=dstnat \
  dst-port=8080 protocol=tcp in-interface=ether1 \
  action=dst-nat to-addresses=192.168.1.10 to-ports=80 \
  comment="portfwd-web"

# DNS をルーター経由で強制する (DNS バイパスを防止)
/ip/firewall/nat/add chain=dstnat action=redirect \
  in-interface-list=LAN dst-port=53 protocol=udp to-ports=53 \
  comment="force-dns-udp"
/ip/firewall/nat/add chain=dstnat action=redirect \
  in-interface-list=LAN dst-port=53 protocol=tcp to-ports=53 \
  comment="force-dns-tcp"

# 送信トラフィックをマスカレードする
/ip/firewall/nat/add chain=srcnat action=masquerade \
  out-interface=ether1 comment="nat-wan"

レイヤー7 プロトコル (L7)

L7 は、暗号化されていないペイロードコンテンツを POSIX 正規表現で照合します。CPU 負荷が高いため、控えめに使用してください。

/ip/firewall/layer7-protocol/add \
  name=captive-detect \
  regexp="^.*(gstatic|connectivitycheck|generate_204).*$" \
  comment="android-captive-portal"

L7 の選択: (a|b|c) が正しいです。(a)|(b)|(c) には POSIX ERE 演算子の優先順位のバグがあります。中央の分岐 (b) はストリーム内のどこにでも一致し、アンカーされません。括弧内でのみ | を使用したグループ化された形式を使用してください。

よくある LLM の間違い

間違い 正しい RouterOS の動作
priority= またはルールウェイトの使用 ルールはシーケンシャルです — 順序は位置であり、ウェイトではありません
IP アドレスごとに1つのルールを作成する src-address-list= または dst-address-list= を使用してください
スクリプトでの remove [find dynamic=no] タグベース: remove [find comment~"prefix-"] のみ
accept ルールでの place-before= の忘れ デフォルトは追加です — drop の下の accept ルールは決して実行されません
connection-state=new,established 有効な状態: newestablishedrelatedinvaliduntracked
action=log または passthrough=yes が評価を停止する 非終端アクションは次のルールに進みます — 下の drop は引き続き実行されます
fasttrack と mangle ルーティングマークの組み合わせ fasttrack は mangle をバイパスします — いずれかを選択してください
L7 正規表現での (a)|(b)|(c) の選択 (a|b|c) を使用してください — 1組の括弧内のグループ化された形式
インターフェースごとに1つのファイアウォールルール 名前付きインターフェースリストで in-interface-list= を使用してください
/ip/firewall で処理される IPv6 トラフィック IPv6 は se を使用します

(原文がここで切り詰められています)

📜 原文 SKILL.md(Claudeが読む英語/中国語)を展開

RouterOS Firewall

Rule Ordering — Sequential, Not Priority-Based

Rules are evaluated top-to-bottom — first match wins. This is the biggest source of iptables confusion.

  • place-before=0 inserts at the top; default add appends at the bottom
  • An action=accept rule must appear BEFORE any action=drop for the same traffic
  • Non-terminal actions do NOT stop evaluation: action=add-src-to-address-list, action=add-dst-to-address-list, action=log, and any rule with passthrough=yes continue to the next rule. A drop rule below an add-src-to-address-list will still fire.
# WRONG — drop fires before accept can match
/ip/firewall/filter/add chain=input action=drop
/ip/firewall/filter/add chain=input src-address=10.0.0.1 action=accept

# CORRECT — accept first, drop catches the rest
/ip/firewall/filter/add chain=input src-address=10.0.0.1 action=accept place-before=0
/ip/firewall/filter/add chain=input action=drop

Address-Lists as Dynamic Selectors

LLMs rarely suggest this pattern — they write one rule per IP address instead. Address-lists scale to hundreds of IPs with a single firewall rule.

# Build the list (static or dynamic with auto-expiry)
/ip/firewall/address-list/add list=trusted-mgmt address=192.168.1.0/24
/ip/firewall/address-list/add list=trusted-mgmt address=10.0.0.5 timeout=1h

# One rule handles all list members
/ip/firewall/filter/add chain=input src-address-list=trusted-mgmt action=accept \
  comment="myapp-accept-mgmt"

Dynamic entries with timeout= expire automatically — the primary pattern for DoS blacklists.

Interface-Lists as Rule Selectors

in-interface-list= / out-interface-list= — powerful RouterOS pattern LLMs never propose. Eliminates duplicate rules when multiple interfaces serve the same role.

# Define the group once
/interface/list/add name=WAN
/interface/list/member/add list=WAN interface=ether1
/interface/list/member/add list=WAN interface=pppoe-out1

# One rule applies to all WAN interfaces
/ip/firewall/filter/add chain=input in-interface-list=WAN action=drop \
  comment="myapp-drop-all-wan"

Comment-as-Tag Pattern (Idempotent Scripts)

RouterOS has no "upsert" — re-running a script without cleanup creates duplicate rules. Use a comment prefix as a tag:

# Remove only rules we own — preserves rules from other tools
/ip/firewall/filter/remove [find comment~"myapp-"]
/ip/firewall/address-list/remove [find comment~"myapp-"]
/ip/firewall/nat/remove [find comment~"myapp-"]

# Add with consistent tag — readable in /print output
/ip/firewall/filter/add chain=input src-address-list=trusted-mgmt action=accept \
  comment="myapp-accept-mgmt"
/ip/firewall/filter/add chain=input in-interface-list=WAN action=drop \
  comment="myapp-drop-wan"

Never use remove [find dynamic=no] — this deletes ALL static rules including those added by management tools. Some tools (e.g. OptiWize) mark their rules with comment~"#orchestrator-*" — a bulk remove silently breaks remote management.

Connection State

RouterOS connection-state= is not iptables -m state:

/ip/firewall/filter/add chain=input connection-state=established,related action=accept
/ip/firewall/filter/add chain=input connection-state=invalid action=drop

RouterOS states: new, established, related, invalid, untracked.

untracked matches packets explicitly marked via /ip/firewall/raw action=notrack — it does NOT match FastTrack flows. FastTrack is a separate fast-path that keeps flows in conntrack but bypasses mangle. Never combine fasttrack-connection with mangle-based routing marks on the same traffic — mangle marks are not applied to fasttracked packets.

NAT Patterns

# Port forward (dst-nat)
/ip/firewall/nat/add chain=dstnat \
  dst-port=8080 protocol=tcp in-interface=ether1 \
  action=dst-nat to-addresses=192.168.1.10 to-ports=80 \
  comment="portfwd-web"

# Force DNS through router (prevents DNS bypass)
/ip/firewall/nat/add chain=dstnat action=redirect \
  in-interface-list=LAN dst-port=53 protocol=udp to-ports=53 \
  comment="force-dns-udp"
/ip/firewall/nat/add chain=dstnat action=redirect \
  in-interface-list=LAN dst-port=53 protocol=tcp to-ports=53 \
  comment="force-dns-tcp"

# Masquerade outgoing traffic
/ip/firewall/nat/add chain=srcnat action=masquerade \
  out-interface=ether1 comment="nat-wan"

Layer7 Protocol (L7)

L7 matches unencrypted payload content with a POSIX regex — CPU-intensive, use sparingly:

/ip/firewall/layer7-protocol/add \
  name=captive-detect \
  regexp="^.*(gstatic|connectivitycheck|generate_204).*$" \
  comment="android-captive-portal"

L7 alternation: (a|b|c) is correct. (a)|(b)|(c) has POSIX ERE operator precedence bugs — the middle branch (b) matches anywhere in the stream, not anchored. Use grouped form with | inside parentheses only.

Common LLM Mistakes

Mistake Correct RouterOS behavior
Using priority= or rule weight Rules are sequential — order is position, not weight
Writing one rule per IP address Use src-address-list= or dst-address-list=
remove [find dynamic=no] in scripts Tag-based: remove [find comment~"prefix-"] only
Forgetting place-before= on accept rules Default appends — accept rules below drops never fire
connection-state=new,established Valid states: new, established, related, invalid, untracked
action=log or passthrough=yes stops evaluation Non-terminal actions continue to next rule — a drop below still fires
Combining fasttrack + mangle routing marks fasttrack bypasses mangle — pick one or the other
(a)|(b)|(c) alternation in L7 regexp Use (a|b|c) — grouped form inside one set of parentheses
One firewall rule per interface Use in-interface-list= with a named interface list
IPv6 traffic handled by /ip/firewall IPv6 uses a separate /ipv6/firewall — rules do not apply cross-protocol

Additional Resources

Related skills:

  • routeros-fundamentals — RouterOS CLI syntax, REST API, scripting basics
  • routeros-hotspot — hotspot chain interaction with firewall, walled garden

Reference files in this skill:

MCP tools:

  • rosetta MCP — /ip/firewall command tree inspection (routeros_search, routeros_get_page)

MikroTik docs:

同梱ファイル

※ ZIPに含まれるファイル一覧。`SKILL.md` 本体に加え、参考資料・サンプル・スクリプトが入っている場合があります。