Amazon Web Services ブログ

AWS Config 適合パックの紹介

AWS Config  適合パック(コンフォーマンスパック)を紹介できることを大変嬉しく思います。適合パックは、共通のフレームワークとパッケージモデルを用いて、ポリシー定義から監査、集計レポートに至るまで、大規模なAWS リソースのコンプライアンス設定を管理するのに役立ちます。

注:本記事の原文は2019年12月に公開されていますが、2020年4月に適合パックの追加(AWS Control Tower ガードレール適合パック、CIS コンプライアンスパック)が行われたことに伴い、今回改めて翻訳を実施致しました。

適合パックとは

適合パックを使用すると、コンプライアンスルールのパッケージを作成することができます。このパッケージはAWS Config ルールと修復アクションの両方を単一のエンティティにまとめたもので、大規模な展開を容易にします。そして、これらを組織全体に展開し、顧客や他のユーザーと共有できます。さらに、適合パックによりコンプライアンス・レポートも簡素化されます。これからは適合パックレベルでのレポートが可能になり、そこから従来通り個別のルールやリソースのレベルへ詳細化していくことも可能です。既存のレポート機能はすべてそのまま機能したままで、異なるチーム、異なるコンプライアンス体制、もしくは異なるガバナンス体制によって管理されたコンプライアンスセットを論理的にグルーピングすることができます。

適合パックは、AWS CloudFormation と同様にマークアップを使用して記述されます。必要なのはルールをResourcesセクション内で宣言するのみです。残りは AWS Config によって行われます。オプションで、AWS CloudFormation と同じようにParameters セクションを用いることで、より柔軟な適合パックを構築することもできます。なお、適合パックは YAML 形式のファイルで記述されます。

注意:適合パックの特徴は、それらが不変 (immutable)であることです。個々のルールは、アクセス権限やアカウントの権限に関係なく、デプロイされたパックを外部から変更することはできません。さらに、パックが組織のマスターアカウントによって展開されている場合、組織のメンバーアカウントによって変更することはできません。これにより、企業全体のコンプライアンスを管理する際に、セキュリティと確実性がさらに高まります。

適合パックはどのようなコンプライアンス体制に有効か

通常IT サービスを構成するコンプライアンスの管理は、顧客データのセキュリティと機密性を確保するために、社内チーム (IT部門や情報セキュリティ部門) および外部監査者(PCI、HIPAA、SOC2 など) が要求します。コンプライアンスの管理は、定められた標準や法規制、個々のポリシー定義、そして修復するための手順および例外手順を参照する複数のステップ等で構成されます。以前は、これは複数のツールによって処理されていました。それぞれのツールは1 つの領域 (HIPAA や PCI など) に特化しており、ポリシーを定義しコンプライアンス結果を報告する方法が統一されていなかったのです。そのため、コンプライアンス制度ごとに異なるツールを操作し、各ツールの結果を個別に解釈しなければならず、管理オーバーヘッドが発生していました。

AWS Config 適合パックにより、クラウドリソースの構成に対するコンプライアンス管理は、以前のアプローチと比較して大幅に簡素化されます。本機能を使って、一連の AWS Config ルールで構成される適合パックを作成できるようになりました。さらに、独自のグループに基づいてコンプライアンスを監視するだけでなく、自動的に修復することもできます。適合パックは、AWS Systems Manager Automation を使用した修復をサポートします。

本記事ではコンソールとコマンドラインインターフェイス(AWS CLI)、両方で適合パックをセットアップして使用する方法について説明します。

前提条件

適合パックを使用するには、次の要件を満たしていることを確認してください。

  1. AWS Config の記録がオンになっていること
  2. AWS Config 適合パックのサービスロールが存在すること(AWSServiceRoleForConfigConforms)
  3. Amazon S3 が、適合パックのコンプライアンス結果を保存および配信できるよう設定されていること(サービスロールによるアクセスを許可すること)
  4. 修復アクションも行う場合: AWS Config remediation(修復アクション)のためのサービスロールが存在すること

AWS Config の記録がオンになっていることを確認する

AWS Config に初めてアクセスする場合は、「コンソールによる AWS Config の設定」の手順に従います。

アクセスが初めてではない場合:

  • AWS にサインインし、AWS Config コンソールを開きます。
  • 設定を選択し、レコーダー記録はオンになっていることを確認します。もちろん、AWS CLI やプログラムコードを使用して同じ操作を実行できます。

AWS Config 適合パックのサービスロールを作成する

AWS Config 適合パックサービスを使うには、アカウントでの動作を許可する IAM ロールが必要です。
コンソールから IAM サービスロールを作成するには、このリンクもしくは以下の手順に従って下さい。

  • IAM サービスページにアクセスします。
  • [ロールの作成]をクリックします。
  • ロールを作成する AWS サービスとして[Config]を選択し、ユースケースの選択から [Config – Conformance Packs. ]を選択します。

サービスで使用される IAM サービスロールを作成するには、次の CLI コマンドを実行します。

aws iam create-service-linked-role --aws-service-name config-conforms.amazonaws.com --description "my service linked role for config-conforms"

Amazon S3 delivery バケットのパーミッションを更新する

AWS Config 適合パックの出力結果を保存するには、Amazon S3 バケットに次のバケットポリシー追加してアクセスを許可する必要があります。


{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "AWSConfigConformsBucketPermissionsCheck",
      "Effect": "Allow",
      "Principal": {
        "AWS": [
            "arn:aws:iam::AccountId:role/aws-service-role/config-conforms.amazonaws.com/AWSServiceRoleForConfigConforms"
        ]
      },
      "Action": "s3:GetBucketAcl",
      "Resource": "arn:aws:s3:::delivery-bucket-name"
    },
    {
      "Sid": "AWSConfigConformsBucketDelivery",
      "Effect": "Allow",
      "Principal": {
        "AWS": [
            "arn:aws:iam::AccountId:role/aws-service-role/config-conforms.amazonaws.com/AWSServiceRoleForConfigConforms"
        ]
      },
      "Action": "s3:PutObject",
      "Resource": "arn:aws:s3:::delivery-bucket-name/[optional] prefix/AWSLogs/AccountId/Config/*",
      "Condition": {
        "StringEquals": {
          "s3:x-amz-acl": "bucket-owner-full-control"
        }
      }
    },
    {
      "Sid": " AWSConfigConformsBucketReadAccess",
      "Effect": "Allow",
      "Principal": {
        "AWS": [
            "arn:aws:iam::AccountId:role/aws-service-role/config-conforms.amazonaws.com/AWSServiceRoleForConfigConforms"
        ]
      },
      "Action": "s3:GetObject",
      "Resource": "arn:aws:s3:::delivery-bucket-name/[optional] prefix/AWSLogs/AccountId/Config/*"
    }
  ]
}

詳細については、ドキュメントの前提条件を参照してください。

最初の適合パック展開

AWS Config では、マネージドルールを使用することも、AWS Lambda を使った独自のカスタムルールを作成することもできます。現在、AWS は 100 を超えるマネージドルールと、社内チームとカスタマーのパブリックリポジトリから選んだ 20 を超えるカスタムルールを持っています。ここでは最初の適合パックとして、Amazon DynamoDB 運用のベストプラクティス(Operational Best Practices for Amazon DynamoDB)を使用してみます。これには、リージョン内のすべての Amazon DynamoDB テーブルに対してチェックされる 3 つの AWS Config ルールが含まれています。この例の後半で、自動修復のしくみを追加し、コンプライアンス監視と適合性の維持を行えるようにします。。

サンプルテンプレートは、コンソールから直接使用できます。AWS CLI またはプログラムで使用するには、ローカルに保存し、保存したそのテンプレートを指定するか、Amazon S3 バケットにアップロードして参照します。

コンソールを使用してデプロイするには:

  • AWS Config コンソールに移動し、[適合パック]を選択し、[適合パックをデプロイ]ボタンを選択します。
  • [サンプルテンプレートを使用]オプションを選択し、使用可能なサンプルテンプレートのリストから Operational Best Practices for Amazon DynamoDB を選択します。
  • [適合パックの詳細の指定] ページで、パックに名前を付け、レポートの保存に使用する Amazon S3 バケット名を追加し、オプションでプレフィックスを追加します。サンプルの DynamoDB パックでは、追加のパラメーターは必要ありません。(入力パラメータを必要とするパックで作業する場合は、コンソール側で自動入力をしないため、適切なパラメータを入力する必要があります。
  • 最後に詳細を確認し、問題がない場合は、[適合パックをデプロイ] を選択します。パックは [進行中] 状態に移行し、数分以内に [完了] 状態に移行します。

適合パックをクリックすると、下記のように、パックを構成するルールとそのコンプライアンスステータスの状態を確認できます。

CLI を使用してデプロイするには:

1.Amazon DynamoDB 運用のベストプラクティス(Operational Best Practices for Amazon DynamoDB)をローカルに保存し、次のコマンドを実行します。

aws configservice put-conformance-pack --conformance-pack-name="MyFirstConformancePack" --template-body="file://<PATH TO YOUR TEMPLATE>/<TEMPLATE FILENAME>" --delivery-s3-bucket=<YOUR BUCKET>

プレースホルダは、それぞれが対応する値に置き換えてください。テンプレートのローカルソースを指定するか、--template-s3-uri という引数を使用して Amazon S3 バケットを指定することができます。

2.結果として次のような適合パックの ARNが返却されます。

arn:aws:config:us-west-2:123456789012:conformance-pack/ MyFirstConformancePack/conformance-pack-ababababa

新しく作成した適合パックのコンプライアンスをチェックするには、次のコマンドを使用します。

aws configservice describe-conformance-pack-compliance --conformance-pack-name="MyFirstConformancePack"

次のような出力が表示されます。


{
    "ConformancePackName": "MyFirstConformancePack", 
    "ConformancePackRuleComplianceList": [
        {
            "ComplianceType": "NON_COMPLIANT", 
            "ConfigRuleName": "DynamoDbAutoscalingEnabled-conformance-pack-l1thqp3tu"
        }, 
        {
            "ComplianceType": "COMPLIANT", 
            "ConfigRuleName": "DynamoDbTableEncryptionEnabled-conformance-pack-l1thqp3tu"
        }, 
        {
            "ComplianceType": "COMPLIANT", 
            "ConfigRuleName": "DynamoDbThroughputLimitCheck-conformance-pack-l1thqp3tu"
        }
    ]
}

カスタムルールの追加

適合パックにカスタムルールを追加することができます。カスタムルールは独自に作成したり、GitHub リポジトリにあるものが利用可能です。カスタムルールを追加するには、まず(ルールの評価処理を行う)Lambda関数をデプロイするAWS CloudFormation テンプレートを作成します。これは、Lambda 関数、Lambda 関数の IAM ロール、AWS Config への Lambda 関数呼び出し許可、を含みます。テンプレートではLambda 関数の ARN をエクスポートし、適合パックでは Fn::ImportValue で Lambda 関数を参照します。

次のパックでは、カスタムルールと、今回とは別のマネージドルールを使用します。マネージドルールに ”IAM Policy in Use” を選択し、”IAM Policy Exists“カスタムルールと組み合わせました。前述したように、1 つの AWS CloudFormation テンプレートでルール以外のすべてを設定し、2 つのルールを適合パックにパッケージングします。

1 番目のテンプレート

これにはLambda 関数(とそのIAMロール及び呼び出し許可)を記述します。作成した関数の ARN をエクスポートし、AWS CloudFormation でデプロイを行います。


---
Resources:
  ConfigPermissionToCallLambda:
    DependsOn: [IAMPolicyExistsLambda]
    Type: AWS::Lambda::Permission
    Properties:
      FunctionName: !GetAtt IAMPolicyExistsLambda.Arn
      Action: "lambda:InvokeFunction"
      Principal: "config.amazonaws.com"
  LambdaExecutionRole:
    Type: AWS::IAM::Role
    Properties:
      ManagedPolicyArns:
        - arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole
      AssumeRolePolicyDocument:
        Statement:
          - Action: ['sts:AssumeRole']
            Effect: Allow
            Principal:
              Service: [lambda.amazonaws.com]
        Version: '2012-10-17'
      Policies:
        - PolicyName: "PutEvaluationsPermission"
          PolicyDocument:
            Version: "2012-10-17"
            Statement:
              - Effect: "Allow"
                Action:
                  - "config:PutEvaluations"
                Resource: '*'
              - Effect: "Allow"
                Action:
                  - "iam:GetPolicy"
                Resource: '*'
  IAMPolicyExistsLambda:
    DependsOn: [LambdaExecutionRole]
    Type: "AWS::Lambda::Function"
    Properties:
      Handler: "index.lambda_handler"
      Role: !GetAtt LambdaExecutionRole.Arn
      Code:
        ZipFile: !Sub |
          #
          # This file made available under CC0 1.0 Universal (https://creativecommons.org/publicdomain/zero/1.0/legalcode)
          #
          # Ensure one or several specific IAM policies exist
          # Description: Checks that defined IAM policies have been defined in AWS IAM.
          #
          # Trigger Type: Periodic
          # Scope of Changes: N/A
          # Required Parameter name: PoliciesToCheck
          # Required Parameter value example: policy-name1,policy-name2 (split multiple rule name with a ",")

          import boto3
          import json

          def evaluate_compliance(rule_parameters, account_id):
            fails = 0
            client = boto3.client("iam")
            
            if 'PoliciesToCheck' in rule_parameters:
              for policy in rule_parameters["PoliciesToCheck"].split(","):
                policyARN = "arn:aws:iam::%s:policy/%s" %(account_id, policy)
                print(policyARN)
                try:
                  response = client.get_policy(PolicyArn=policyARN)
                except:
                  fails = fails + 1
            else:
              print("No IAM policy defined in parameter")
              fails = fails + 1
            if fails == 0:
              return "COMPLIANT"
            else:
              return "NON_COMPLIANT"


          def lambda_handler(event, context):
              account_id = event['accountId']
              invoking_event = json.loads(event["invokingEvent"])
              print(invoking_event)
              rule_parameters = json.loads(event["ruleParameters"])
              result_token = "No token found."
              if "resultToken" in event:
                  result_token = event["resultToken"]

              config = boto3.client("config")
              config.put_evaluations(
                  Evaluations=[
                      {
                          'ComplianceResourceType': 'AWS::::Account',
                          'ComplianceResourceId': account_id,
                          'ComplianceType': evaluate_compliance(rule_parameters, account_id),
                          'OrderingTimestamp': invoking_event['notificationCreationTime']
                      },
                  ],
                  ResultToken=event['resultToken']
              )
      Runtime: "python3.7"
      Timeout: 120

Outputs:
  IAMPolicyExistsLambdaArn:
    Description: Export Lambda ARN for use in conformance pack template
    Export:
      Name: IAMPolicyExistsLambdaArn
    Value:
      !GetAtt IAMPolicyExistsLambda.Arn

2 番目のテンプレート

ここでは2つのルールを含む適合パックを記述します。カスタムルールを定義し(使用する Lambda 関数 のARNをインポートしています)、マネージドルールを定義します。この適合パックのテンプレートは AWS Config でデプロイします。


---
Resources:
  IamPolicyInUse:
    Type: "AWS::Config::ConfigRule"
    Properties:
      ConfigRuleName: IamPolicyInUse
      Description: "Checks whether the IAM policy ARN is attached to an IAM user, or an IAM group with one or more IAM users, or an IAM role with one or more trusted entity."
      MaximumExecutionFrequency: TwentyFour_Hours
      InputParameters:
        policyARN: "arn:aws:iam::aws:policy/IAMFullAccess"
      Source:
        Owner: AWS
        SourceIdentifier: IAM_POLICY_IN_USE
  
  IamPolicyExists:
    Type: "AWS::Config::ConfigRule"
    Properties:
      ConfigRuleName: IamPolicyExists
      Description: "Checks that defined IAM policies have been defined in AWS IAM."
      MaximumExecutionFrequency: TwentyFour_Hours
      InputParameters:
        PoliciesToCheck: "arn:aws:iam::aws:policy/IAMFullAccess"
      Source:
        Owner: "CUSTOM_LAMBDA"
        SourceIdentifier:
          Fn::ImportValue: IAMPolicyExistsLambdaArn
        SourceDetails: 
        - EventSource: "aws.config"
          MessageType: "ScheduledNotification"

最初の例と同様に、コンソール、API、または AWS CLI を使用してパックの表示、更新、削除ができます。

パックへ修正アクションを追加する

コンプライアンスを考えるうえで最初のステップは、可視化と監視です。これにより、リソースのコンプライアンスの状態を確実に把握できます。次のステップは、検出した結果に基づいてアクションすることです。このために、”修復アクション”を使用します。

修復アクションは、AWS Config ルールとターゲットを紐づけるAWS::Config::RemediationConfigurationリソースタイプを使用して定義されます。ターゲットは、コンプライアンスに準拠していないソースを修復するロジックを持つ、 SSM ドキュメントです。修復アクションを使ってこのブログの最初でデプロイした適合パックを強化するには「修復を伴う Amazon DynamoDB 運用のベストプラクティス(Operational Best Practices For Amazon DynamoDB with Remediation)」を使用します。テンプレートをローカルに保存し、<Account ID>プレースホルダーをデプロイする AWS アカウント ID に置き換え、最初のパックに使用したデプロイ手順を繰り返します。この種のパックには、入力パラメータとして Amazon SNS トピック ARN が必要です。このトピックは、自動修復ステータスに関する通知に使用されます。

修復を自動的に適用するかどうかは設定可能です。これは、Automaticパラメータを使用して行われます。通知を行って(半)手動で修復操作を行うこともでできますが、Automaticパラメータを使えばコンプライアンスに準拠していないリソースを自動修復することができます。

デプロイすると、下のスクリーンショットのように、画面にはルールの修復アクションとステータスが表示されます。

整理すると、SSM ドキュメント (一度だけ作成する) と適合パックの 2 つのコンポーネントがあります。さまざまなパックや他の AWS リソースから参照できるこの方式により、SSM ドキュメントの再利用性が向上します。

組織全体への適合パック展開

多くのお客様は、複数のアカウントを持ち、AWS Organizations を活用しています。適合パックは、前述のように 1 つのアカウントに展開することに加え、組織全体に展開することもできます。

この機能は、現在 AWS CLI および API のみのサポートですが、単一アカウントのデプロイと非常によく似ています。

aws configservice put-organization-conformance-pack --organization-conformance-pack-name="OrgDynamoConformancePack" --template-body="file://<PATH TO YOUR TEMPLATE>/<TEMPLATE FILENAME>" --delivery-s3-bucket=<YOUR BUCKET>

プレースホルダは、対応する値に置き換えてください。

注:適合パックを組織にデプロイする場合、 Amazon S3 delivery バケットの名前は awsconfigconforms プレフィックスで始まる必要があります(例:awsconfigconforms-demo )。

シングルアカウントパックと同様に、次の操作を実行できます。

      • 適合パックに関する説明を記述する (describe-organization-conformance-packs)
      • ステータスを取得する(describe-organization-conformance-pack-statuses
      • 詳細ステータスの確認 (get-organization-conformance-pack-detailed-status)

AWS Organizationsのサポートについては、AWS Config ドキュメントにより詳しい情報があります。

まとめ

本記事では、AWS Config 適合パックを使用して複数のルールをパッケージ化し、展開し、アカウントのコンプライアンスを管理する方法についてご紹介しました。そしてさらに、修復アクションと、これらを組織全体に展開する方法についてご説明しました。

独自のカスタムルールを作成している場合は、AWS GitHub リポジトリを介して AWS および他の仲間と共有することを強くお勧めします。AWS は引き続きお客様からのフィードバックを収集し、機能と能力を追加していきますので、Whas’s newの内容をチェックしてください。

 


 

著者について

Raphael は、AWS Service Catalog と Control Towerの事業開発マネージャーです。
自動化とコーディングに夢中で、マネジメントツールコミュニティ活動を楽しんでいます。

 

 

 

 

Himanshu は AWS Config のソフトウェア開発マネージャーです。AWS およびハイブリッドクラウド環境において、設定管理、ガバナンス、コンプライアンス管理に関連する、あらゆることに興味を持っています。

 

 

 

原文はこちら。翻訳はSA柳が担当しました。