Single AZなVPCに作成したRedshiftクラスターのクラスター再配置をあとから有効にすることはできますか?

Single AZなVPCに作成したRedshiftクラスターのクラスター再配置をあとから有効にすることはできます。(要 Subnetの追加・Redshiftクラスタの再起動)
2023.03.09

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

はじめに

好物はインフラとフロントエンドのかじわらゆたかです。

結論として前提としてVPCに別AZなSubnetを作る必要はありますが、答えとしては、できますが答えとなります。 その際にRedshiftクラスタの作り直しは必要なく、Redshiftクラスタの再起動が行われます。

以下では実際にSingle AZなVPCを構築し、別AZのSubnetをVPCに追加とその後クラスタの再配置を有効にしてみました。

クラスター再配置って何?

Redshiftの可用性を上げる機能の一つです。 クラスタの再配置については以下が特徴となります。

  • データの損失やアプリケーションへの変更なしに、クラスターを別のアベイラビリティーゾーン (AZ) に移動させることができます。
  • 追加料金はかかりません
  • Amazon Redshift クラスターが新しいアベイラビリティーゾーンに再配置されると、新しいクラスターは元のクラスターと同じエンドポイントを持ちます。
  • Amazon Redshift クラスターの再配置は、ra3.16xlarge、ra3.4xlarge、ra3.xlplus などの RA3 インスタンスタイプでのみサポートされています。

Amazon Redshift でのクラスター再配置の管理 - Amazon Redshift

このような特徴がある機能のため、上記のドキュメントをを参考に制約条件に引っかからないのであれば有効にしておくべき機能と言えます。

実際にSingle AZなRedshiftをMulti-AZなSubnetに配置して、クラスター再配置を有効にしてみた。

手順としては、以下の手順で行いました。

  1. Single AZなVPCでRedshiftを構築する
  2. VPCに異なるAvailabilityZoneのSubnetを追加し、RedshiftのSubnetGroupに追加する
  3. Redshiftのクラスタ再配置を有効にする

Single AZで構築したRedshiftを作ってみる。

以下のようなCloudformationのテンプレートを用いて、まずはSingle AZなVPC上にRedshiftを構築します。 (行数が多いので、全体はトグルを開いて確認してください)

Signel AZなVPCとRedsfhitクラスタを構築するCloudformationテンプレート

vpc_redshift-solo.yaml

AWSTemplateFormatVersion: 2010-09-09
Description: Redshift Env
Parameters:
  Prefix:
    Description: Prefix
    Type: String
    Default: cm-kajiwara-sample
  MasterUsername:
    Type: "String"
    Default: "admin"
  CidrBlock:
    Description: Please type the CidrBlock.
    Type: String
    Default: 192.168.0.0/22
  MasterUserPasswordSSMParam:
    Type: String
    Description: colons-separated parameter name and version for master user's password for DB instance. e.x. parameter-name:1

Resources:
  #-----------------------------------------------------------------------------
  # VPC
  #-----------------------------------------------------------------------------
  VPC:
    Type: AWS::EC2::VPC
    Properties:
      CidrBlock: !Sub ${CidrBlock}
      EnableDnsSupport: true
      EnableDnsHostnames: true
      Tags:
        - Key: Name
          Value: !Sub "${Prefix}-vpc"
  PrivateRouteTable:
    Type: AWS::EC2::RouteTable
    Properties:
      VpcId: !Ref VPC
      Tags:
        - Key: Name
          Value: !Sub "${Prefix}-private-rtb"
  PrivateSubnet1:
    Type: AWS::EC2::Subnet
    Properties:
      AvailabilityZone: !Select [ 0, !GetAZs ]
      VpcId: !Ref VPC
      CidrBlock: !Select [ 0, !Cidr [ !GetAtt VPC.CidrBlock, 4, 8 ]]
      Tags:
        - Key: Name
          Value: !Sub "${Prefix}-private-subnet"
  InternetGateway:
    Type: AWS::EC2::InternetGateway
    Properties:
      Tags:
      - Key: Application
        Value:
          Ref: AWS::StackId
      - Key: Network
        Value: Public
  AttachGateway:
    Type: AWS::EC2::VPCGatewayAttachment
    Properties:
      VpcId:
        Ref: VPC
      InternetGatewayId:
        Ref: InternetGateway
  #-----------------------------------------------------------------------------
  # Securty Group
  #-----------------------------------------------------------------------------
  RedshiftSecurityGroup:
    Type: "AWS::EC2::SecurityGroup"
    Properties:
      GroupDescription: !Sub "${Prefix}-redshift-sg"
      GroupName: !Sub "${Prefix}-redshift-sg"
      Tags:
        - Key: "Name"
          Value: !Sub "${Prefix}-redshift-sg"
      VpcId: !Ref VPC
      SecurityGroupEgress:
        - CidrIp: "0.0.0.0/0"
          IpProtocol: "-1"
  #-----------------------------------------------------------------------------
  # IAM
  #-----------------------------------------------------------------------------
  RedshiftRole:
    Type: "AWS::IAM::Role"
    Properties:
      Path: "/"
      RoleName: !Sub "${Prefix}-redshift-role"
      AssumeRolePolicyDocument:
        Version: "2012-10-17"
        Statement:
          - Effect: Allow
            Principal:
              Service:
                - redshift.amazonaws.com
            Action: sts:AssumeRole
      MaxSessionDuration: 3600
      ManagedPolicyArns:
        - "arn:aws:iam::aws:policy/AmazonS3FullAccess"
      Description: "Allows Redshift clusters to call AWS services on your behalf."
      Tags:
        - Key: "Name"
          Value: !Sub "${Prefix}-redshift-role"

  #-----------------------------------------------------------------------------
  # Redshift
  #-----------------------------------------------------------------------------
  RedshiftClusterSubnetGroup:
    Type: "AWS::Redshift::ClusterSubnetGroup"
    Properties:
      Description: !Sub "${Prefix}-redshift-subnet-group"
      SubnetIds:
        - !Ref PrivateSubnet1

  RedshiftClusterParameterGroup:
    Type: "AWS::Redshift::ClusterParameterGroup"
    Properties:
      Description: !Sub "${Prefix}-redshift-parameter-group"
      ParameterGroupFamily: "redshift-1.0"
      Parameters:
        - ParameterName: "require_ssl"
          ParameterValue: "true"
  RedshiftCluster:
    Type: "AWS::Redshift::Cluster"
    Properties:
      ClusterIdentifier: !Sub "${Prefix}-redshift"
      ClusterType: multi-node
      NumberOfNodes: 2
      NodeType: ra3.xlplus
      MasterUsername: !Ref MasterUsername
      MasterUserPassword: !Sub "{{resolve:ssm-secure:${MasterUserPasswordSSMParam}}}"
      DBName: !Sub "${Prefix}-db"
      AutomatedSnapshotRetentionPeriod: 35
      VpcSecurityGroupIds:
        - !Ref RedshiftSecurityGroup
      EnhancedVpcRouting: true
      ClusterParameterGroupName: !Ref RedshiftClusterParameterGroup
      ClusterSubnetGroupName: !Ref RedshiftClusterSubnetGroup
      AvailabilityZone: !Select [ 0, !GetAZs ]
      PreferredMaintenanceWindow: sat:18:00-sat:18:30
      ClusterVersion: "1.0"
      AllowVersionUpgrade: true
      PubliclyAccessible: false
      IamRoles:
        - !GetAtt RedshiftRole.Arn

上記のテンプレートを以下のようなシェルで構築します。

set -eu
export AWS_PAGER=""
MasterUserPasswordSSMParam="/cm-kajiwara/redshift/master-password:3"
aws cloudformation deploy --stack-name cm-kajiwara-redshift-sample --template-file vpc_redshift-solo.yaml --no-execute-changeset \
  --capabilities CAPABILITY_NAMED_IAM \
  --parameter-overrides \
  MasterUserPasswordSSMParam=$MasterUserPasswordSSMParam

当然Single AZなVPCに構築しているため、クラスタ再配置は有効になっておりません。

VPCに異なるAvailabilityZoneのSubnetを追加し、RedshiftのSubnetGroupに追加する

上記のYamlに以下のように記載して、Subnetを追加と追加したSubnetをRedshiftのSubnet Groupに追加します。

  PrivateSubnet1:
    Type: AWS::EC2::Subnet
    Properties:
      AvailabilityZone: !Select [ 0, !GetAZs ]
      VpcId: !Ref VPC
      CidrBlock: !Select [ 0, !Cidr [ !GetAtt VPC.CidrBlock, 4, 8 ]]
      Tags:
        - Key: Name
          Value: !Sub "${Prefix}-private-subnet"
  PrivateSubnet2:
    Type: AWS::EC2::Subnet
    Properties:
      AvailabilityZone: !Select [ 1, !GetAZs ]
      VpcId: !Ref VPC
      CidrBlock: !Select [ 1, !Cidr [ !GetAtt VPC.CidrBlock, 4, 8 ]]
      Tags:
        - Key: Name
          Value: !Sub "${Prefix}-private-subnet"
  RedshiftClusterSubnetGroup:
    Type: "AWS::Redshift::ClusterSubnetGroup"
    Properties:
      Description: !Sub "${Prefix}-redshift-subnet-group"
      SubnetIds:
        - !Ref PrivateSubnet1
        - !Ref PrivateSubnet2

これを実行するだけではクラスタの再配置は有効にならず、またRedshiftの再起動も実施されません。

Redshiftのクラスタ再配置を有効にする

以下のように追記すると、Redshiftのクラスタ再配置が有効になります。

  RedshiftCluster:
    Type: "AWS::Redshift::Cluster"
    Properties:
      ClusterIdentifier: !Sub "${Prefix}-redshift"
      ClusterType: multi-node
      NumberOfNodes: 2
      NodeType: ra3.xlplus
      MasterUsername: !Ref MasterUsername
      MasterUserPassword: !Sub "{{resolve:ssm-secure:${MasterUserPasswordSSMParam}}}"
      DBName: !Sub "${Prefix}-db"
      AutomatedSnapshotRetentionPeriod: 35
      VpcSecurityGroupIds:
        - !Ref RedshiftSecurityGroup
      EnhancedVpcRouting: true
      ClusterParameterGroupName: !Ref RedshiftClusterParameterGroup
      ClusterSubnetGroupName: !Ref RedshiftClusterSubnetGroup
      AvailabilityZone: !Select [ 0, !GetAZs ]
      AvailabilityZoneRelocation: true
      PreferredMaintenanceWindow: sat:18:00-sat:18:30
      ClusterVersion: "1.0"
      AllowVersionUpgrade: true
      PubliclyAccessible: false
      IamRoles:
        - !GetAtt RedshiftRole.Arn

このタイミングでRedshiftのクラスタの再起動が実施されることとなり、Redshiftのクラスタ再配置が有効になります。

まとめ

Signal AZな構成で組んだVPC RedshiftであってもVPCに別AZのSubnetが追加可能であれば、あとからクラスタの再配置を有効にすることはできます。 その際にRedshiftクラスタの再起動は必要となりますが、この機能を有効にするにあたって追加の費用はかからずRedshiftの可用性を上げる方法の一つとなりますので、 有効になっていない場合は有効を検討していただければと思います。