AWSのセキュリティグループ、ネットワークACLのステートレスとステートフルを噛み砕いて具体的に行ってみる

クラウドソリューション事業部の倉岡です。1年目ということもあり学ぶことが多々あるのですが、つい先日AWS技術書を読んで悩んだ内容がありました。

”AWSのセキュリティグループはステートフル、ネットワークACLはステートレス”

と言った文言です。ステートフルは「状態を保持する」と言った意味合いがあり、ステートレスは「状態を保持しない」と言った意味合いがあります。その意味も踏まえて先ほどの文言を言い換えると

”AWSのセキュリティグループは状態を保持する、ネットワークACLは状態を保持しない”

となります。

ますます、わからなくなってきました。そこで様々なサイトの閲覧や解説書を読み進めていくことにしました。すると、

”セキュリティグループはステートフルで1つの通信を設定すれば戻りの通信は設定不要”、“ネットワークACLは送信受信の個々で設定が必要”

”ここでのステートフルとは「ステートフルパケットインスペクション」の略であり、出入りするパケットの通信状態を把握し動的に通信を可否を決める”

と言った内容を多々見つけました。

私は「セキュリティグループでインバウンドを許可してたとしてもアウトバウンドの通信を全部拒否してしまったら、通信が拒否されるのでは?」と思っていたため少しまだ疑問が残ります。

そこで実際にEC2を立ち上げて、セキュリティグループとネットワークACLを使って比較してみました。

セキュリティグループを使ってみる

EC2を立ち上げて、セキュリティグループを以下のように設定してみました。

セキュリティグループ
インバウンド(外から中)
22
アウトバウンド(中から外)
全て拒否

行きの通信(22番)が許可されるのなら、戻りの通信が動的なのでSSH接続ができるはずです。EC2にSSH接続してみます。

できました!22番ポートでインバウンドで入れば、アウトバウンドが仮に全拒否であっても、出ていく通信が動的に許可されているみたいです。これがセキュリティグループのステートフルであるという意味合いでした。なるほど…。

コンソールで

yum update

を叩いてみると

やはりアウトバウンド(中から外)が全拒否になってるのでエラーが出るみたいですね。

ネットワークACLを使用してみる

続いて、ステートレスと呼ばれるネットワークACLを使ってみます。全ての設定をデフォルトに戻してネットワークACLだけ設定を変えて実験してみます。

ネットワークACL
インバウンド(外から中)
22
アウトバウンド(中から外)
全て拒否

の設定を行いました。セキュリティグループはデフォルトのままです。(インバウンドは22番、アウトバウンドは全て許可)

※ちなみにネットワークACLの設定はVPCの左のメニュー項目にあります。

ネットワークACLがステートレスで行き帰りの通信の可否を確認しているのであれば、この通信は失敗するはずです。(外から中が許可でも中から外が拒否になっているから)

結果は

タイムアウトになりました。ステートレスでは、行きの通信が許可されても帰りの通信がダメなら通信は失敗するみたいですね。

※ちなみに通信を成功させるためには、ネットワークACLの設定を

ネットワークACL
インバウンド(外から中)
22
アウトバウンド(中から外)
49152 – 65535ポート(Ephemeralポート)

としてください。アウトバウンドを22番にしても通信は成功しないのでご注意ください。

実は行きの通信が22番でも帰りの通信は、Ephemeralポートの49152 – 65535ポートから出ていきます。

「行きが22ポートなら帰りも22ポート」とよく勘違いされがちなのですが、通信の帰りは実はEphemeralポートです。

EphemeralポートやネットワークACLについて詳しく知りたい方は、こちらの記事を参照ください。

Amazon VPCのネットワークACLについて | DevelopersIO

まとめ

”セキュリティグループはステートフルで行きの通信が許可されれば、戻りの通信は自動的に許可される”

“ネットワークACLは行きの通信、戻りの通信を個別で設定をする必要がある。でないと、行きの通信が許可されていても戻りの通信で拒否されていれば通信が失敗する”

これでステートフルとステートレスの違いがようやくすっきりしました。