サーバーレスで活用するCloudFormationのNested Applications
 
										弊社のサーバレス開発事例にて利用している
Nested Applications についてご紹介いたします。
CloudFormationのリソース数の制限
AWS CloudFormation には制限があることをご存知でしょうか。
制限のほとんどは、上限解放することができない制限となっております。
重要な制限として、リソース数の制限があります。
リソースは一つのテンプレートに最大で200までしか作成することができません。
「テンプレートに記載したリソース数 = リソース数」
ではない
例えば、シンプルなAWS Lambdaをテンプレートに定義した場合、
下記2つのリソースが作成されます。
- AWS::Lambda::Function
- AWS::IAM::Role
テンプレートに記載したリソース数は
最終的に出力されるリソース数とは合致しません。
リソース数はテンプレートへの記載を増やす毎に、膨らんでいきます。
特にサーバーレスの場合はAWS Lambdaに対してのイベントソースとして
複数のAPIエンドポイントを紐づけるケースがあり、
すぐにリソース数がいっぱいになってしまうこともあります。

では、どのようにすればよいのでしょうか。
解決策を記載します。
Nested Applicationsを利用してネストされたスタックを作成する
AWS Serverless Application Model(SAM)は拡張されたフォーマットのため、
AWS::CloudFormation::Stack 定義を利用することができません。
代替手段として、 Nested Applicationsの
AWS::Serverless::Application が利用可能です。
Nested Applicationsを利用することで 最大で40,000 の
リソースを作成することが可能になります。
また、ネストされるテンプレートは自動的にS3にアップロードされます。
Nested Applicationsは Serverless Application Repository の
アプリケーションをネストできることに注目されていますが、
ローカルにあるテンプレートをネストすることも可能です。
ローカルにあるテンプレートをネストする場合の記述例:
Transform: AWS::Serverless-2016-10-31
Resources:
  applicationaliasname:
    Type: AWS::Serverless::Application
    Properties:
      Location: ../my-other-app/template.yamlNested Applicationsを利用して、サーバーレスのスタックを作成
それでは、実際にやってみましょう。
サンプルは下図のフォルダ構成となります。

筆者本人のGitHubアカウントにてリポジトリも公開しておりますので、
よろしければご参照下さい。
テンプレートファイル(template.yml)
テンプレートファイルは AWS::Serverless::Application のリソースを定義し
ネストされたスタックを構築します。パラメータを受け渡すことも可能です。
下記の記述例では、 Parameters に定義された変数とS3のバケット名を受け渡しています。
AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Parameters:
  Stage:
    Type: String
    Default: test
Resources:
  app1:
    Type: AWS::Serverless::Application
    Properties:
      Location: ./template_app1.yml
  app2:
    Type: AWS::Serverless::Application
    Properties:
      Location: ./template_app2.yml
      Parameters:
        Stage: !Ref Stage
        BucketTest: !Ref S3Bucket
  S3Bucket:
      Type: AWS::S3::Bucket
      Properties:
        BucketName: aws-sam-nested-application-test-bucket-0-001ネストされたテンプレートファイル
サンプルでは、ネストされたテンプレートファイルのそれぞれに AWS::Serverless::Function のリソースを定義しました。
親のテンプレートファイルから受け渡されたパラメータも参照しています。
テンプレート1(template_app1.yml)
AWSTemplateFormatVersion: 2010-09-09
Transform: AWS::Serverless-2016-10-31
Resources:
  App1Function:
    Type: AWS::Serverless::Function
    Properties:
      FunctionName: app1
      CodeUri: handlers/app1
      Handler: app1
      Runtime: go1.x
  S3Bucket001:
      Type: AWS::S3::Bucket
      Properties:
        BucketName: aws-sam-nested-application-test-bucket-1-001テンプレート2(template_app2.yml)
AWSTemplateFormatVersion: 2010-09-09
Transform: AWS::Serverless-2016-10-31
Parameters:
  Stage:
    Type: String
    Default: dev
  BucketTest:
    Type: String
Globals:
  Function:
    Runtime: go1.x
    Timeout: 900
    Environment:
      Variables:
        STAGE: !Ref Stage
Resources:
  App2Function:
    Type: AWS::Serverless::Function
    Properties:
      FunctionName: app2
      CodeUri: handlers/app2
      Handler: app2
  S3Bucket2001:
      Type: AWS::S3::Bucket
      Properties:
        BucketName: aws-sam-nested-application-test-bucket-2-001デプロイ
デプロイは sam deploy の実行時にCAPABILITY_AUTO_EXPANDのオプションを付与する必要があります。
#!/bin/sh
# Create Package
sam package 
  --template-file ./template.yml 
  --output-template-file ./template-output.yml 
  --s3-bucket aws-sam-nested-application-packages 
  --profile temp_profile
# Deploy
sam deploy 
  --template-file ./template-output.yml 
  --stack-name aws-sam-nested-application 
  --capabilities CAPABILITY_IAM CAPABILITY_AUTO_EXPAND 
  --profile temp_profile実行結果

Nested Applicationsの作成に成功していることが確認できました!
テンプレートの分割は計画的に
サーバレス開発の場合、気づいたらリソース数が逼迫しているということも
珍しくないと思います。中・大規模のサーバレス開発なら尚更です。
リソースの整理に伴う再作成が余儀なくされる前に、計画的にテンプレートを分割することをオススメいたします。
弊社ではGoとAWS SAMを活用したサーバレスアプリケーション開発実績があります
少しでもご興味を持ちましたら、弊社にエントリーしていただければ幸いです。
一緒に楽しく成長しあえる仲間を募集しています。
・リモートワークでAWSなサーバーレスシステムに携わりたいエンジニア大募集
MMMのサーバーレスへの取り組みについては以下でご紹介しています。ぜひご覧ください。


 
																											 
																											 
																											