AWS Security Hubのセキュリティ基準のコントロール一覧を取得するときはus-east-1を利用しようねって話

us-east-1じゃないと取れない情報があるよって話
2022.07.23

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

こんにちは、臼田です。

みなさん、Security Hubでセキュリティチェックしてますか?(挨拶

今回はちょっとしたメモです。

概要

AWS Security Hubのセキュリティ基準はよく使いますよね?もちろん使うのはAWS基礎セキュリティベストプラクティスです。

運用するためのスクリプトを組むときなどで、このコントロール(IAM.6などのチェック項目)一覧が欲しくなります。

その時の注意事項についてメモします。

東京リージョンで一覧取得

大体作業するときは東京リージョンで行うことが多いので、東京リージョンでコントロール一覧を取得してみます。以下のようなスクリプトです。

import sys
import logging
import boto3


logger = logging.getLogger()
logger.setLevel(logging.INFO)

# params
standard_name = "aws-foundational-security-best-practices/v/1.0.0"
account_id = boto3.client('sts').get_caller_identity()['Account']
logger.addHandler(logging.StreamHandler(stream=sys.stdout))
securityhub = boto3.client('securityhub')
# get controls
region_name = securityhub._client_config.region_name
std_subsc_arn = "arn:aws:securityhub:{}:{}:subscription/{}".format(
    region_name, account_id, standard_name)
describe_standards_controls_paginator = securityhub.get_paginator(
    'describe_standards_controls')
describe_standards_controls_iterator = describe_standards_controls_paginator.paginate(
    StandardsSubscriptionArn=std_subsc_arn)
controls = []
for r in describe_standards_controls_iterator:
    controls.extend(r['Controls'])
logger.info("controls: " + str(len(controls)))

実行した結果は以下の通りです。

controls: 174

しかしマネジメントコンソールでは174個以上コントロールがあります。

内訳を出力してみましょう。

>>> [x['ControlId'] for x in controls]
['ACM.1', 'APIGateway.1', 'APIGateway.2', 'APIGateway.3', 'APIGateway.4', 'APIGateway.5', 'AutoScaling.1', 'AutoScaling.2', 'AutoScaling.3', 'AutoScaling.4', 'AutoScaling.6', 'Autoscaling.5', 'CloudFormation.1', 'CloudTrail.1', 'CloudTrail.2', 'CloudTrail.4', 'CloudTrail.5', 'CodeBuild.1', 'CodeBuild.2', 'CodeBuild.4', 'CodeBuild.5', 'Config.1', 'DMS.1', 'DynamoDB.1', 'DynamoDB.2', 'DynamoDB.3', 'EC2.1', 'EC2.10', 'EC2.15', 'EC2.16', 'EC2.17', 'EC2.18', 'EC2.19', 'EC2.2', 'EC2.20', 'EC2.21', 'EC2.22', 'EC2.23', 'EC2.24', 'EC2.3', 'EC2.4', 'EC2.6', 'EC2.7', 'EC2.8', 'EC2.9', 'ECR.1', 'ECR.2', 'ECR.3', 'ECS.1', 'ECS.10', 'ECS.12', 'ECS.2', 'ECS.3', 'ECS.4', 'ECS.5', 'ECS.8', 'EFS.1', 'EFS.2', 'EFS.3', 'EFS.4', 'EKS.2', 'ELB.10', 'ELB.12', 'ELB.13', 'ELB.14', 'ELB.2', 'ELB.3', 'ELB.4', 'ELB.5', 'ELB.6', 'ELB.7', 'ELB.8', 'ELB.9', 'ELBv2.1', 'EMR.1', 'ES.1', 'ES.2', 'ES.3', 'ES.4', 'ES.5', 'ES.6', 'ES.7', 'ES.8', 'ElasticBeanstalk.1', 'ElasticBeanstalk.2', 'GuardDuty.1', 'IAM.1', 'IAM.2', 'IAM.21', 'IAM.3', 'IAM.4', 'IAM.5', 'IAM.6', 'IAM.7', 'IAM.8', 'KMS.1', 'KMS.2', 'KMS.3', 'Kinesis.1', 'Lambda.1', 'Lambda.2', 'Lambda.5', 'NetworkFirewall.3', 'NetworkFirewall.4', 'NetworkFirewall.5', 'NetworkFirewall.6', 'Opensearch.1', 'Opensearch.2', 'Opensearch.3', 'Opensearch.4', 'Opensearch.5', 'Opensearch.6', 'Opensearch.7', 'Opensearch.8', 'RDS.1', 'RDS.10', 'RDS.11', 'RDS.12', 'RDS.13', 'RDS.14', 'RDS.15', 'RDS.16', 'RDS.17', 'RDS.18', 'RDS.19', 'RDS.2', 'RDS.20', 'RDS.21', 'RDS.22', 'RDS.23', 'RDS.24', 'RDS.25', 'RDS.3', 'RDS.4', 'RDS.5', 'RDS.6', 'RDS.7', 'RDS.8', 'RDS.9', 'Redshift.1', 'Redshift.2', 'Redshift.3', 'Redshift.4', 'Redshift.6', 'Redshift.7', 'Redshift.8', 'Redshift.9', 'S3.1', 'S3.10', 'S3.11', 'S3.12', 'S3.13', 'S3.2', 'S3.3', 'S3.4', 'S3.5', 'S3.6', 'S3.8', 'S3.9', 'SNS.1', 'SNS.2', 'SQS.1', 'SSM.1', 'SSM.2', 'SSM.3', 'SSM.4', 'SageMaker.1', 'SecretsManager.1', 'SecretsManager.2', 'SecretsManager.3', 'SecretsManager.4', 'WAF.2', 'WAF.3', 'WAF.4']

CloudFrontなどが見受けられないので、グローバルサービスのコントロールが取得されていないようです。というわけでus-east-1で取り直しましょう。

import sys
import logging
import boto3


logger = logging.getLogger()
logger.setLevel(logging.INFO)

# params
standard_name = "aws-foundational-security-best-practices/v/1.0.0"
account_id = boto3.client('sts').get_caller_identity()['Account']
logger.addHandler(logging.StreamHandler(stream=sys.stdout))
region_name = "us-east-1"
securityhub = boto3.client('securityhub', region_name=region_name)
# get controls
std_subsc_arn = "arn:aws:securityhub:{}:{}:subscription/{}".format(
    region_name, account_id, standard_name)
describe_standards_controls_paginator = securityhub.get_paginator(
    'describe_standards_controls')
describe_standards_controls_iterator = describe_standards_controls_paginator.paginate(
    StandardsSubscriptionArn=std_subsc_arn)
controls = []
for r in describe_standards_controls_iterator:
    controls.extend(r['Controls'])
logger.info("controls: " + str(len(controls)))

結果は以下のようになりました。

controls: 188

内訳を見てみましょう。

>>> [x['ControlId'] for x in controls]
['ACM.1', 'APIGateway.1', 'APIGateway.2', 'APIGateway.3', 'APIGateway.4', 'APIGateway.5', 'AutoScaling.1', 'AutoScaling.2', 'AutoScaling.3', 'AutoScaling.4', 'AutoScaling.6', 'Autoscaling.5', 'CloudFormation.1', 'CloudFront.1', 'CloudFront.10', 'CloudFront.2', 'CloudFront.3', 'CloudFront.4', 'CloudFront.5', 'CloudFront.6', 'CloudFront.7', 'CloudFront.8', 'CloudFront.9', 'CloudTrail.1', 'CloudTrail.2', 'CloudTrail.4', 'CloudTrail.5', 'CodeBuild.1', 'CodeBuild.2', 'CodeBuild.4', 'CodeBuild.5', 'Config.1', 'DMS.1', 'DynamoDB.1', 'DynamoDB.2', 'DynamoDB.3', 'EC2.1', 'EC2.10', 'EC2.15', 'EC2.16', 'EC2.17', 'EC2.18', 'EC2.19', 'EC2.2', 'EC2.20', 'EC2.21', 'EC2.22', 'EC2.23', 'EC2.24', 'EC2.3', 'EC2.4', 'EC2.6', 'EC2.7', 'EC2.8', 'EC2.9', 'ECR.1', 'ECR.2', 'ECR.3', 'ECS.1', 'ECS.10', 'ECS.12', 'ECS.2', 'ECS.3', 'ECS.4', 'ECS.5', 'ECS.8', 'EFS.1', 'EFS.2', 'EFS.3', 'EFS.4', 'EKS.2', 'ELB.10', 'ELB.12', 'ELB.13', 'ELB.14', 'ELB.2', 'ELB.3', 'ELB.4', 'ELB.5', 'ELB.6', 'ELB.7', 'ELB.8', 'ELB.9', 'ELBv2.1', 'EMR.1', 'ES.1', 'ES.2', 'ES.3', 'ES.4', 'ES.5', 'ES.6', 'ES.7', 'ES.8', 'ElasticBeanstalk.1', 'ElasticBeanstalk.2', 'GuardDuty.1', 'IAM.1', 'IAM.2', 'IAM.21', 'IAM.3', 'IAM.4', 'IAM.5', 'IAM.6', 'IAM.7', 'IAM.8', 'KMS.1', 'KMS.2', 'KMS.3', 'Kinesis.1', 'Lambda.1', 'Lambda.2', 'Lambda.5', 'NetworkFirewall.3', 'NetworkFirewall.4', 'NetworkFirewall.5', 'NetworkFirewall.6', 'Opensearch.1', 'Opensearch.2', 'Opensearch.3', 'Opensearch.4', 'Opensearch.5', 'Opensearch.6', 'Opensearch.7', 'Opensearch.8', 'RDS.1', 'RDS.10', 'RDS.11', 'RDS.12', 'RDS.13', 'RDS.14', 'RDS.15', 'RDS.16', 'RDS.17', 'RDS.18', 'RDS.19', 'RDS.2', 'RDS.20', 'RDS.21', 'RDS.22', 'RDS.23', 'RDS.24', 'RDS.25', 'RDS.3', 'RDS.4', 'RDS.5', 'RDS.6', 'RDS.7', 'RDS.8', 'RDS.9', 'Redshift.1', 'Redshift.2', 'Redshift.3', 'Redshift.4', 'Redshift.6', 'Redshift.7', 'Redshift.8', 'Redshift.9', 'S3.1', 'S3.10', 'S3.11', 'S3.12', 'S3.13', 'S3.2', 'S3.3', 'S3.4', 'S3.5', 'S3.6', 'S3.8', 'S3.9', 'SNS.1', 'SNS.2', 'SQS.1', 'SSM.1', 'SSM.2', 'SSM.3', 'SSM.4', 'SageMaker.1', 'SecretsManager.1', 'SecretsManager.2', 'SecretsManager.3', 'SecretsManager.4', 'WAF.1', 'WAF.2', 'WAF.3', 'WAF.4', 'WAF.6', 'WAF.7', 'WAF.8']

CloudFrontやWAFの項目が増えていますね。これでOKです。

まとめ

コントロール一覧を取得するときの注意点メモでした。

リージョンによる差分があることはAWSではよくあるので、意識したいですね。