ファイアウォールでポートを開放する
RHEL/MiracleLinux系では firewalld が既定のファイアウォールで、外部からの通信を初期状態で多くしゃ断しています。Webサーバを立てても http サービス(80番)を許可しなければ、外からはアクセスできません。firewall-cmd で http や https のサービスを恒久的に許可し、--reload で反映します。設定は「ゾーン」単位で管理され、--permanent を付けないと再起動で消える点に注意します。
Webサーバを起動し、サーバ自身からは curl http://localhost で応答が返るのに、別の端末からはアクセスできない——サーバ構築でほぼ誰もが一度はぶつかる場面です。その犯人の多くがファイアウォールです。ファイアウォールは、ネットワークインターフェースを通ろうとするパケットを監視し、OSの内側へ通すか遮断するかを決める関所のような仕組みです。RHEL/MiracleLinux系では firewalld というサービスがこの役割を担い、インストール直後の状態では、外部からの通信のほとんどを初期設定でしゃ断するようになっています。これはセキュリティ上は望ましい初期値で、「必要な通信だけを明示的に許可して開ける」という考え方に基づいています。
まず firewalld の状態を確認する
firewalld 自体も systemd 管理下のサービスなので、まず systemctl status firewalld で動いているかを確かめます。Active: が active (running) なら機能しています。次に現在の許可状況を見るには sudo firewall-cmd --list-all を実行します。先頭に public (active) のように現在のゾーン名が表示され、services: の欄に許可済みのサービスが並びます。インストール直後はここに ssh と dhcpv6-client 程度しかなく、http や https は含まれていません。firewall-cmd は設定を扱うコマンドなので管理者権限が必要で、一般ユーザでは sudo を付けます。firewalld が動いていないと FirewallD is not running と表示されます。
ゾーンという考え方
firewalld の設定は「ゾーン」という単位で管理されます。ゾーンとは、ネットワークの信頼度に応じた設定のまとまりで、各ネットワークインターフェースがいずれかのゾーンに割り当てられます。firewalld にはあらかじめ public(公衆ネットワーク向けの既定)・home・work・trusted(すべて許可)など複数のゾーンが用意されており、用途に応じて使い分けます。標準的なサーバでは public ゾーンが使われ、許可ルールもこのゾーンに対して追加していきます。いまどのインターフェースがどのゾーンに属しているかは sudo firewall-cmd --get-active-zones で確認できます。ゾーンという仕組みがあるおかげで、たとえば社内向けインターフェースと外部向けインターフェースで、許可する通信を別々に管理する、といった使い分けができます。
サービス名で許可する — add-service
firewalld の便利な点は、ポート番号を直接覚えなくても「サービス名」で許可を指定できることです。Webサーバに必要なのはHTTP(80番)とHTTPS(443番)で、これらは http・https というサービス名で登録されています。HTTPを許可するには sudo firewall-cmd --permanent --zone=public --add-service=http、HTTPSなら同様に --add-service=https を実行します。success と表示されれば登録できています。--permanent は再起動後も残る恒久設定の指定、--zone=public は対象ゾーンの指定です。どんなサービス名が使えるかは sudo firewall-cmd --get-services で一覧でき、ssh・http・https・dns・ftp など主要なものはあらかじめ定義されています。もちろん sudo firewall-cmd --permanent --add-port=80/tcp のようにポート番号で直接指定することもできますが、標準的なサービスはサービス名で開けるほうが分かりやすく、間違いも起きにくくなります。誤って許可してしまったルールを取り消したいときは、--add-service を --remove-service に置き換えて実行し、同じく --reload で反映します。
--permanent と --reload の関係
ここが最大の落とし穴です。--permanent を付けて追加したルールは、その場では有効になりません。設定ファイルに書き込まれただけの状態で、実際に効かせるには sudo firewall-cmd --reload を実行して読み込ませる必要があります。逆に --permanent を付けずに add-service すると、その場ですぐ有効になりますが、サーバを再起動すると消えてしまいます。つまり「恒久化したいなら --permanent で追加してから --reload」「お試しで即時反映したいだけなら --permanent なし」という関係です。本番では恒久化と反映の両方が要るので、--permanent で追加 → --reload、という二段構えが定石になります。reload を忘れたまま「開けたはずなのに繋がらない」と悩むのが、典型的なつまずきです。
確認とよくある失敗、実務の使いどころ
反映できたら、もう一度 sudo firewall-cmd --list-all を実行し、services: の欄に http と https が加わっていることを確認します。あわせて、サービスが実際にそのポートで待ち受けているかは ss コマンドで、外部からの到達は別端末の curl やブラウザで確かめます。よくある失敗は、--reload を打ち忘れる、--permanent を付け忘れて再起動で設定が消える、ゾーンを取り違えて別ゾーンに許可を入れてしまう、の3つです。さらにクラウド(AWS や Azure など)で公開する場合は、サーバ内の firewalld を開けても、その手前にあるクラウド側のネットワークファイアウォール(セキュリティグループなど)が閉じていれば通信は届かないため、両方を開ける必要があります。実務の鉄則は「本当に必要なポートだけを開ける最小公開」で、不要なサービスは許可しないことが、そのままサーバの安全性につながります。