[AWS]Aurora PostgreSQLをCloudFormationで構築する

CloudFormationを使って、一発でAurora PostgreSQLを構築するテンプレートです。コピペでご利用ください。
2019.02.25

コンニチハ、千葉です。

CloudFormationにて、Aurora PostgreSQL を構築する機会がありましたので、コピペできるようにCloudFormationテンプレートを置いておきます。 Aurora PostgreSQLを作成するスニペットがなかったので、CloudFormationのドキュメントを読みまくって作りました。実際書くと結構苦労することが多いと思いますので、コピペできるようにブログ化しておきます!

はじめに

作成したCloudFormationテンプレートを利用するにあたり、前提やポイントをまとめます。

前提

CloudFormationスタックを作成する前に、以下を確認しておきましょう。

  • VPCが作成済みであること
  • RDS用のセキュリティグループが作成済みであること

作成されるリソース

このテンプレートで作成されるリソースは以下です。

  • DBサブネットグループ
  • クラスターパラメータグループ
  • DBパラメータグループ
  • マスターインスタンス
  • リードレプリカインスタンス
  • 拡張モニタリング用のIAMロール

ポイント

こちらのテンプレートは以下のパラメータになります。

  • DBインスタンスの削除保護が有効
  • 拡張モニタリングが有効
  • PerformanceInsightsが有効
  • ディスクを暗号化
  • パブリックアクセスが無効

注意事項

マスターが配置されるAZを指定できないので、任意のAZにマスターを移動したい場合は、手動でフェイルオーバーを行なってください。

CloudFormationテンプレート

コピペで利用できます。Mappingsパラメータを適宜変更してご利用ください。

AWSTemplateFormatVersion: '2010-09-09'
Description: This CloudFormation template to create RDS db instances.

Mappings:
prd:
DBSubnet1a: { ID: subnet-xxx }
DBSubnet1c: { ID: subnet-xxx }
RdsSecurityGroup: { ID: sg-xxx }
DBInstance:
Engine: aurora-postgresql
EngineVersion: 10.6
RDS1AvailabilityZone: ap-northeast-1a
RDS2AvailabilityZone: ap-northeast-1c
BackupRetentionPeriod: 7
PreferredBackupWindow: 13:00-13:30
ClusterPreferredMaintenanceWindow: tue:13:30-tue:14:00
InstancePreferredMaintenanceWindow: wed:13:30-wed:14:00
DatabaseName: chiba_db
AutoMinorVersionUpgrade: true
DBInstanceClass: db.r5.large
DBParameterGroup:
DBEngineFamily: aurora-postgresql10

Parameters:
Environment:
Description: Type of this environment.
Type: String
Default: prd
AllowedValues:
- prd
- stg
SystemName:
Description: Name of this system.
Type: String
Default: chiba-rds
Username:
Description: Name of DB mater username.
Type: String
Default: admin
Password:
Description: Name of DB mater user password.
Type: String
NoEcho: true

Metadata:
AWS::CloudFormation::Interface:
ParameterGroups:
- Label:
default: Environment Configuration
Parameters:
- SystemName
- Environment
- Label:
default: RDS DB instace Configuration
Parameters:
- Username
- Password

Resources:
# IAM Role for enhanced monitoring
RDSMonitoringRole:
Type: AWS::IAM::Role
Properties:
RoleName: !Sub ${SystemName}-${Environment}-rds-monitoring-role
Path: /
AssumeRolePolicyDocument:
!Sub |
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Service": "monitoring.rds.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
ManagedPolicyArns:
- arn:aws:iam::aws:policy/service-role/AmazonRDSEnhancedMonitoringRole

RDSCluster:
Type: AWS::RDS::DBCluster
Properties:
MasterUsername: !Ref Username
MasterUserPassword: !Ref Password
Engine: !FindInMap [ !Ref Environment, DBInstance, Engine ]
DBSubnetGroupName: !Ref DBSubnetGroup
DBClusterParameterGroupName: !Ref RDSDBClusterParameterGroup
VpcSecurityGroupIds:
- !FindInMap [ !Ref Environment, RdsSecurityGroup, ID ]
BackupRetentionPeriod: !FindInMap [ !Ref Environment, DBInstance, BackupRetentionPeriod ]
PreferredBackupWindow: !FindInMap [ !Ref Environment, DBInstance, PreferredBackupWindow ]
DatabaseName: !FindInMap [ !Ref Environment, DBInstance, DatabaseName ]
DBClusterIdentifier: !Sub ${SystemName}-${Environment}-aurora-posgre
DeletionProtection: true
EngineMode: provisioned
EngineVersion: !FindInMap [ !Ref Environment, DBInstance, EngineVersion ]
PreferredMaintenanceWindow: !FindInMap [ !Ref Environment, DBInstance, ClusterPreferredMaintenanceWindow ]
StorageEncrypted: true
Tags:
- Key: Name
Value: !Sub ${SystemName}-${Environment}-aurora-posgre-cluster

RDSDBInstance1:
Type: AWS::RDS::DBInstance
Properties:
DBSubnetGroupName: !Ref DBSubnetGroup
DBParameterGroupName: !Ref RDSDBParameterGroup
Engine: !FindInMap [ !Ref Environment, DBInstance, Engine ]
EngineVersion: !FindInMap [ !Ref Environment, DBInstance, EngineVersion ]
DBClusterIdentifier: !Ref RDSCluster
PubliclyAccessible: 'false'
AvailabilityZone: !FindInMap [ !Ref Environment, DBInstance, RDS1AvailabilityZone ]
DBInstanceClass: !FindInMap [ !Ref Environment, DBInstance, DBInstanceClass ]
AutoMinorVersionUpgrade: !FindInMap [ !Ref Environment, DBInstance, AutoMinorVersionUpgrade ]
CopyTagsToSnapshot: true
DBInstanceIdentifier: !Sub ${SystemName}-${Environment}-aurora-posgre-1
EnablePerformanceInsights: true
PreferredMaintenanceWindow: !FindInMap [ !Ref Environment, DBInstance, InstancePreferredMaintenanceWindow ]
DeletionProtection: true
MonitoringInterval: 60
MonitoringRoleArn: !GetAtt RDSMonitoringRole.Arn
PubliclyAccessible: false
PromotionTier: 1
Tags:
- Key: Name
Value: !Sub ${SystemName}-${Environment}-aurora-posgre-1

RDSDBInstance2:
Type: AWS::RDS::DBInstance
Properties:
DBSubnetGroupName: !Ref DBSubnetGroup
DBParameterGroupName: !Ref RDSDBParameterGroup
Engine: !FindInMap [ !Ref Environment, DBInstance, Engine ]
EngineVersion: !FindInMap [ !Ref Environment, DBInstance, EngineVersion ]
DBClusterIdentifier: !Ref RDSCluster
PubliclyAccessible: 'false'
AvailabilityZone: !FindInMap [ !Ref Environment, DBInstance, RDS2AvailabilityZone ]
DBInstanceClass: !FindInMap [ !Ref Environment, DBInstance, DBInstanceClass ]
AutoMinorVersionUpgrade: !FindInMap [ !Ref Environment, DBInstance, AutoMinorVersionUpgrade ]
CopyTagsToSnapshot: true
DBInstanceIdentifier: !Sub ${SystemName}-${Environment}-aurora-posgre-2
EnablePerformanceInsights: true
PreferredMaintenanceWindow: !FindInMap [ !Ref Environment, DBInstance, InstancePreferredMaintenanceWindow ]
DeletionProtection: true
MonitoringInterval: 60
MonitoringRoleArn: !GetAtt RDSMonitoringRole.Arn
PubliclyAccessible: false
PromotionTier: 2
Tags:
- Key: Name
Value: !Sub ${SystemName}-${Environment}-aurora-posgre-2

# DB subnet group
DBSubnetGroup:
Type: AWS::RDS::DBSubnetGroup
Properties:
DBSubnetGroupName: !Sub ${SystemName}-${Environment}-db-subnet-group
DBSubnetGroupDescription: !Sub ${SystemName}-${Environment}-db-subnet-group
SubnetIds:
- !FindInMap [ !Ref Environment, DBSubnet1a, ID ]
- !FindInMap [ !Ref Environment, DBSubnet1c, ID ]
Tags:
- Key: Name
Value: !Sub ${SystemName}-${Environment}-db-subnet-group

# DB Cluster Parameter Group
RDSDBClusterParameterGroup:
Type: AWS::RDS::DBClusterParameterGroup
Properties:
Description: !Sub ${SystemName}-${Environment}-db-cluster-param-group
Family: !FindInMap [ !Ref Environment, DBParameterGroup, DBEngineFamily ]
Parameters:
client_encoding: UTF8
Tags:
- Key: Name
Value: !Sub ${SystemName}-${Environment}-db-cluster-param-group

# DB parameter group
RDSDBParameterGroup:
Type: AWS::RDS::DBParameterGroup
Properties:
Description: !Sub ${SystemName}-${Environment}-db-param-group
Family: !FindInMap [ !Ref Environment, DBParameterGroup, DBEngineFamily ]
Tags:
- Key: Name
Value: !Sub ${SystemName}-${Environment}-db-param-group

最後に

RDSのCloudFormation化はやっていたのですが、Auroraは初でした。RDSだとDBInstanceにバックアップパラメータを指定しますが、AuroraだとDBClusterリソースがあり、こちらにバックアップなどのいくつかの定義をする必要があります。また、AuroraはマスターとリードレプリカそれぞれDBInstanceリソースを作る必要がありました。いざ作ってみると、はまることもあると思うので、参考にしてみてください!

参考

https://docs.aws.amazon.com/ja_jp/AWSCloudFormation/latest/UserGuide/aws-resource-rds-dbcluster.html