2026年5月24日

2026年5月24日

ufw / iptables で接続元IPを絞ってアクセス制御する方法

サーバーへのアクセスを接続元IPで制御するときの基本は、「受信は既定で拒否し、必要な通信だけを、必要な相手からだけ許可する」ことです。この記事では、ufw と iptables のそれぞれで、既定ポリシーの設定、接続元IPによる許可・拒否、ルールの順番、締め出しを防ぐ手順、設定の永続化までを説明します。

ポートを開ける手順そのもの(待ち受け確認やクラウド側の設定)は別記事で扱う内容なので、ここでは「誰に何を許すか」を設計して設定する部分に絞っています。

ufw と iptables の関係を押さえる

ufw(Uncomplicated Firewall)は、Linux カーネルのパケットフィルター(netfilter)を操作するための、扱いやすい前段ツールです。内部では iptables 形式のルールを生成しています。近年の Ubuntu や Debian では iptables コマンド自体が nftables をバックエンドに使う構成(iptables-nft)になっていることが多く、どちらで書いても最終的にはカーネルの同じ仕組みで処理されます(2026年10月現在、構成はディストリビューションやバージョンで異なります)。

ここで大切なのは、1台のサーバーで管理方法を1つに決めることです。ufw で管理しているサーバーに手で iptables ルールを足したり、firewalld と ufw を同時に動かしたりすると、どのルールが効いているのか追えなくなります。普段の運用は ufw、細かい制御が必要な場面だけ ufw の設定ファイル(/etc/ufw/before.rules など)に書く、というように役割を分けるのが現実的です。

アクセス制御を設計する

設定を始める前に、次のような表を紙やメモに書き出しておくと、ルールの漏れや重複を防げます。

  • 22/tcp(SSH):管理者の固定IPやVPNの出口IPからだけ許可
  • 80/tcp・443/tcp(Web):全世界に公開
  • 3306/tcp(MySQL):同じネットワーク内のアプリサーバーからだけ許可。外部には出さない
  • それ以外の受信:拒否

管理者の自宅回線のようにIPアドレスが変わる環境から接続している場合、IP制限だけに頼ると、アドレスが変わった日に締め出されます。VPNや踏み台サーバーを経由する構成にして、そこの固定IPを許可するほうが運用は安定します。

ufw で設定する

既定ポリシーと許可ルール

# 既定ポリシー:受信は拒否、送信は許可
sudo ufw default deny incoming
sudo ufw default allow outgoing

# SSHは管理用IPからだけ許可(有効化より前に追加しておく)
sudo ufw allow from 203.0.113.10 to any port 22 proto tcp

# ネットワーク範囲で許可する例
sudo ufw allow from 192.0.2.0/24 to any port 3306 proto tcp

# Webは全体に公開
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp

sudo ufw enable
sudo ufw status verbose

既定ポリシーを deny incoming にしてから有効化すると、許可していない受信はすべて止まります。SSHを許可するルールが入っていない状態で有効化すると、その時点で接続が切れるので、有効化の前に sudo ufw show added で追加済みのルールを確認してください。

ルールの順番に注意する

ufw は上から順にルールを評価し、最初に一致したルールで処理を決めます。たとえば「443を全体に許可」のあとに「特定IPからの443を拒否」を追加しても、先に許可ルールに一致するため拒否は効きません。特定IPを遮断したいときは、insert で先頭側に入れます。

sudo ufw status numbered
# 1番目の位置に拒否ルールを挿入
sudo ufw insert 1 deny from 198.51.100.25

拒否には deny(黙って破棄)と reject(拒否したことを相手に返す)があります。外部に対しては deny が一般的ですが、社内ネットワーク内では reject にしておくと、接続できない理由がすぐ分かり切り分けが楽になります。

接続回数の制限

ufw には、同じIPから短時間に多数の接続があった場合に拒否する limit があります。ufw のマニュアルでは、30秒以内に6回以上の接続を試みたIPを拒否する動作と説明されています。

sudo ufw limit 22/tcp

これはパスワード総当たりの勢いを弱める程度のもので、本格的な対策にはなりません。SSHはパスワード認証を無効にして鍵認証にし、ログを見て自動で遮断する fail2ban などと組み合わせるのが一般的です。

IPv6 も対象にする

サーバーにIPv6アドレスがある場合、IPv4だけを制限してもIPv6側から接続できてしまいます。/etc/default/ufw の IPV6=yes を確認しておけば、ufw のルールはIPv4とIPv6の両方に作られます。

iptables で設定する

ufw を使わず iptables を直接扱う場合は、ルールを追加する順番がそのまま安全性に関わります。既定ポリシーを DROP にするのは、許可ルールを入れ終えた最後にします。

# ループバックと、確立済みの通信の戻りを許可
sudo iptables -A INPUT -i lo -j ACCEPT
sudo iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT

# SSHは管理用IPからだけ
sudo iptables -A INPUT -p tcp -s 203.0.113.10 --dport 22 -j ACCEPT

# Webは全体に公開
sudo iptables -A INPUT -p tcp -m multiport --dports 80,443 -j ACCEPT

# 最後に既定ポリシーを拒否へ
sudo iptables -P INPUT DROP

# 番号付きで確認
sudo iptables -L INPUT -n -v --line-numbers

ESTABLISHED,RELATED の許可を忘れると、サーバーから外へ出た通信(パッケージ更新やAPI呼び出し)の戻りが止まり、「外に出られない」という症状になります。IPv6 は ip6tables で別に設定が必要です。

再起動後も残す

iptables コマンドで追加したルールは、そのままでは再起動で消えます。Debian / Ubuntu では iptables-persistent(netfilter-persistent)パッケージを使って保存する方法がよく使われます。

sudo apt install iptables-persistent
sudo netfilter-persistent save
# 保存先の例:/etc/iptables/rules.v4 と rules.v6

締め出しを防ぐ工夫

リモートからファイアウォールを変更するときは、失敗しても元に戻れる仕組みを用意してから作業します。

  • SSHのセッションを2つ開き、片方は作業用、もう片方は変更後に新しい接続が通るかの確認用にする
  • at コマンドで、一定時間後にファイアウォールを無効化する予約を入れておき、問題がなければ予約を取り消す
  • VPSやクラウドの管理画面のコンソールから操作できることを、作業前に確かめておく
# 5分後に ufw を無効化する予約(問題なければ atrm で取り消す)
echo "ufw disable" | sudo at now + 5 minutes
sudo atq

iptables には、適用後に確認の入力がなければ元に戻す iptables-apply というスクリプトが用意されているディストリビューションもあります。

Docker を使っている場合の落とし穴

Docker は公開ポート(-p オプション)のために独自の iptables ルールを追加し、その通信は ufw の INPUT ルールより前に処理されます。このため「ufw で拒否しているのに、コンテナのポートには外からつながる」という状態が起こります。対策としては、コンテナのポートを 127.0.0.1 に限定して公開し、手前のリバースプロキシで制御する方法や、Docker が用意している DOCKER-USER チェーンに制限ルールを書く方法があります。

ネットワーク層とWebサーバー層の使い分け

ufw や iptables はポート単位の制御なので、「443番は公開しつつ、WordPress の管理画面だけ社内IPに限定したい」といった要件には向きません。この場合は Nginx の allow / deny や Apache の Require ip で、URLのパス単位に制限します。ネットワーク層では「そもそも外に出す必要のないポートを閉じる」、Webサーバー層では「公開しているサイトの一部を絞る」と役割を分けると、設定が整理しやすくなります。

設定後の確認とログ

設定後は、外部のマシンから許可したIP・許可していないIPの両方で接続を試し、意図どおりに通る・止まるかを確認します。ufw のログは sudo ufw logging on で有効にでき、Ubuntu では多くの場合 /var/log/ufw.log やカーネルログ(journalctl -k)に記録されます。拒否の記録を見れば、正規の利用者を誤って止めていないかの確認にも使えます。

まとめ

  • 受信は既定で拒否し、必要なポートを必要な相手からだけ許可するのが基本です
  • ufw も iptables も上から順に評価されるため、特定IPの拒否は許可ルールより前に置きます
  • iptables では既定ポリシーの DROP を最後に設定し、確立済み通信の戻りを許可します。再起動後も残るよう保存します
  • 作業前に締め出し対策(別セッション、時間差の無効化予約、管理画面のコンソール)を用意します
  • Docker の公開ポートは ufw を迂回することがあり、管理画面だけの制限はWebサーバー側で行います

お気軽にご相談ください

お見積りへ お問い合わせへ
▲