この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。
はじめに
今回はインターネットゲートウェイを構築します。
前回の記事はこちら。
AWS 構成図
インターネットゲートウェイを作成し、VPC にアタッチします。
設計
インターネットゲートウェイのプロパティはこちら。
リソース名 | アタッチ先 VPC |
---|---|
devio-stg-igw | devio-stg-vpc |
インターネットゲートウェイは比較的シンプルなリソースなので、設定項目はリソース名(tags
)くらいです。
ルールのおさらい
前回の最後で宣言した、今後の実装に関する(自分)ルールです。
- 作成するリソースごとにファイル(クラス)を分割する
- 例)
internetGateway.ts
(InternetGateway
クラス)
- 例)
- すべてのリソースクラスは抽象クラス
Resource
を継承する - 「あるリソースの生成に必要となるリソース」はコンストラクタに渡す
- 渡すオブジェクトは
CfnXXX
クラスのインスタンス
- 渡すオブジェクトは
- リソースクラス内で複数のリソースを生成する場合はループで回す
new CfnXXX()
を何度も実行しないResourceInfo
インタフェースを用意してプロパティの変動部分のみを書き出す
- 生成したリソースはリソースクラス内の public メンバ変数に格納し、外部クラスから参照可能とする
これらに従って実装していきます。
実装
インターネットゲートウェイに関するクラスを作成しました。
lib/resource/internetGateway.ts
import * as cdk from '@aws-cdk/core';
import { CfnInternetGateway, CfnVPCGatewayAttachment, CfnVPC } from '@aws-cdk/aws-ec2';
import { Resource } from './abstract/resource';
export class InternetGateway extends Resource {
public igw: CfnInternetGateway;
private readonly vpc: CfnVPC;
constructor(vpc: CfnVPC) {
super();
this.vpc = vpc;
}
createResources(scope: cdk.Construct) {
this.igw = new CfnInternetGateway(scope, 'InternetGateway', {
tags: [{ key: 'Name', value: this.createResourceName(scope, 'igw') }]
});
new CfnVPCGatewayAttachment(scope, 'VpcGatewayAttachment', {
vpcId: this.vpc.ref,
internetGatewayId: this.igw.ref
});
}
}
インターネットゲートウェイの生成と VPC へのアタッチを行っています。
アタッチ時は VPC とインターネットゲートウェイの ID をそれぞれ指定します。VPCGatewayAttachment
のインスタンスは他のクラスで利用する予定がないのでメンバ変数には保持しません。この場でアタッチしておしまいです。
new CfnXXX
を 2 回実行していますが、対象が異なるリソースなのでこの場合はセーフです。(ルール違反ではない)
メインのプログラムはこちら。
ハイライト部分を追記しました。
lib/devio-stack.ts
import * as cdk from '@aws-cdk/core';
import { Vpc } from './resource/vpc';
import { Subnet } from './resource/subnet';
import { InternetGateway } from './resource/internetGateway';
export class DevioStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
// VPC
const vpc = new Vpc();
vpc.createResources(this);
// Subnet
const subnet = new Subnet(vpc.vpc);
subnet.createResources(this);
// Internet Gateway
const internetGateway = new InternetGateway(vpc.vpc);
internetGateway.createResources(this);
}
}
テスト
テストコードはこちら。
test/resource/internetGateway.test.ts
import { expect, countResources, haveResource } from '@aws-cdk/assert';
import * as cdk from '@aws-cdk/core';
import * as Devio from '../../lib/devio-stack';
test('InternetGateway', () => {
const app = new cdk.App();
const stack = new Devio.DevioStack(app, 'DevioStack');
expect(stack).to(countResources('AWS::EC2::InternetGateway', 1));
expect(stack).to(haveResource('AWS::EC2::InternetGateway', {
Tags: [{ 'Key': 'Name', 'Value': 'undefined-undefined-igw' }]
}));
expect(stack).to(countResources('AWS::EC2::VPCGatewayAttachment', 1));
});
以下を確認しています。
- インターネットゲートウェイリソースが 1 つあること
- リソース名が正しいこと
- VPCGatewayAttachment リソースが 1 つあること
確認
マネジメントコンソール上でリソースを確認してみましょう。
作成されていますね。アタッチ先の VPC も意図通りになっています。
CloudFormation 版
今回のコードを CFn で書くと以下のようになります。
InternetGateway:
Type: AWS::EC2::InternetGateway
Properties:
Tags:
- Key: Name
Value: devio-stg-igw
VpcGatewayAttachment:
Type: AWS::EC2::VPCGatewayAttachment
Properties:
VpcId:
Ref: Vpc
InternetGatewayId:
Ref: InternetGateway
短めです。
GitHub
今回のソースコードは コチラ です。
おわりに
長い時間をかけてベースを固めたおかげでスムーズに実装できました。設計って楽しいですね。
次回は NAT ゲートウェイに割り当てるための Elastic IP
を作成しようと思います。