[レポート] AWS Fargateにおけるセキュリティベストプラクティス #CON414 #reinvent

2019.12.30

CON414 Security best practices for AWS Fargate

はじめに

この記事はre:invent 2019 CON414 Security best practices for AWS Fargate のセッションレポートです。 セッションで使用されたコードはこちらで公開されています。

このセッションではシンプルなWebアプリを題材にFargateのセキュリティベストプラクティスについてデモを交えて解説が行われました。 記事と合わせてコードを参照して内容を確認するのをお勧めします。

セッション概要

In this session, we highlight several of the recommendations for container security on AWS Fargate. You learn about using a private registry and securing the cluster and your services. We also discuss network security basics and security monitoring using AWS solutions. Please bring your laptop.

スピーカー

  • Len Henry - Senior Solutions Architect, Amazon Web Services

アプリのアーキテクチャ

  • Basic認証を設定したnginxとSSHサーバを起動するコンテナをFargateタスクとして実行します
  • コンテナイメージはECRに登録されています
  • タスクはVPC内で起動します

インフラのセットアップとタスクの起動

デモの最初のステップではインフラのセットアップと最初のタスクの起動を行います。

この状態でもFargateではデフォルトで以下のセキュリティ対策が行われています。

  1. タスクの分離: コンピューティング、ストレージ、ネットワークはタスクごとに分離されている
  2. 不変な環境: タスクは一度実行される変更できない
  3. コンテナイメージはセキュアな方法でアクセスされる
  4. アプリケーションのログはセキュアな方法でアクセスされる

このステップでは起動したタスクにインターネットから以下のサービスが公開されています。 (実環境でSSHとWebを同じコンテナで動かすことはないと思いますが・・・)

  • Web(port 80)
  • SSH(port 23)

セキュリティグループ設定の変更

初期状態ではタスクに設定されるセキュリティグループは下記のように、インターネットからのアクセスがフルオープンになっているので、必要なポートだけに絞りこみます。これによりweb以外のポートのアクセスが制限されました。

変更前 00-cluster-fargate-vpc.yml

  ContainerSecurityGroup:
    Type: AWS::EC2::SecurityGroup
    Properties:
      GroupDescription: Access to the Fargate containers
      VpcId: !Ref 'VPC'
      SecurityGroupIngress:
        # Allow access to task from anywhere on the internet
        - CidrIp: 0.0.0.0/0
          IpProtocol: -1

変更後 01-cluster-fargate-vpc-asm.yml

  ContainerSecurityGroup:
    Type: AWS::EC2::SecurityGroup
    Properties:
      GroupDescription: Access to the Fargate containers
      VpcId: !Ref 'VPC'
      SecurityGroupIngress:
        # Allow access to task from anywhere on the internet, but only on port 80
        - CidrIp: 0.0.0.0/0
          FromPort: 80
          ToPort: 80
          IpProtocol: tcp

コンテナイメージ内の機密情報の保護

最初のバージョンのDockerfileではBasic認証用のhtpasswdファイルをCOPYコマンドでコピーしていました。 そのためコンテナイメージにパスワードが含まれています。これをAWS Secret Managerを使ってパスワードを取得するように変更します。 Secret Managerに保存したあんなことやこんなことはごっつ簡単にコンテナ内から環境変数として参照できます

次の変更を行います。

  • 以下のようにCloudFormationスタックを変更する
  • Dockerfileを変更してコンテナ実行時にhtpasswdファイルの中身を環境変数から取得するようにする 01-Dockerfile
  • タスク定義にSecret Managerへの参照を追加する 01-taskdefinition.json

追加のエクササイズ

セッションでも以下の追加エクササイズも出題されました。

まとめ

Fargate上でのタスクのアクセス制限とSecret Managerを使った機密情報の扱いについてデモを交えて学びました。 これまであまり考えていなかったのですが、改めてFargateであってもEC2で構成された環境と同じようにネットワーク設計をした機密情報の保護を行えばいいことのだなと気づきました。 re:Inventの前後でFargateに興味が湧いてきたのですが、実際のワークロードをコンテナ化するときにはこの辺りがEC2の時の知識が使いまわせると設計が捗る・・・気がします。