LoginSignup
3
2

More than 3 years have passed since last update.

【AWS-CDK】認証付きWebAPIをSolutions Constructsを使って手軽に構築

Last updated at Posted at 2020-07-07

Solutions ConstructsでAWSインフラ構築

先日、AWS Solutions Constructsが発表されました。これはAWS-CDKにおいて、抽象化されたリソースを表すConstructsのよく使う組み合わせをWell-Architected準拠の設定込みで一発で構築できるライブラリです。例えばLambda + DynamoDBCloudFront + S3などの組み合わせのパターンが25個(2020/7月現在)提供されています。

これをつかってパパっとAWS上にWebAPIを構築したいと思います。

注意

2020/7/6現在、Solutions ConstructsのstabilityはすべてExperimentalとなっています。
本番環境などでの使用はよく検討した上で行ってください。

環境

  • AWS-CDK CLI v1.47.0
    • ※ Solutions ConstrucsはCDK v1.46.0以上に対応しています。
  • TypeScript v3.9.2
  • npm v6.14.5
  • node.js v12.18.0

使用するConstructs

今回は以下のSolutions Constructsを使用します。

構成図は以下のとおりです。

aws-web-api-infra.png

CDKによって、API Gateway, Lambda, Cognito, DynamoDBテーブルを作成します。
さらに、各リソースのオプションはデフォルトで下記のWell-Architected準拠の設定が施されています。

  • Cognito
    • ユーザープールに対するパスワードポリシーの設定
    • ユーザープールに対するアドバンスドセキュリティの有効化
  • API Gateway
    • エンドポイントのエッジ最適化設定
    • アクセスログの有効化
    • 最小限のIAMロールの設定
    • すべてのメソッドに対するIAM認証設定
  • Lambda
    • 最小限のIAMロールの設定
    • ログ出力の有効化
    • keep-alive時のコネクション再利用設定(Node.jsファンクション)
  • DynamoDB
    • オンデマンドモードの設定
    • AWSマネージドCMKによる暗号化設定

作成手順

AWS-CDK CLIをグローバルインストールします。

npm install -g aws-cdk

インストール後にプロジェクトを作成します。

cdk init app --language=typescript

今回使用するライブラリをインストールします。(SolutionsConstructsの最新verが1.47.0なので統一)

npm install -s @aws-cdk/aws-lambda@1.47.0 @aws-cdk/aws-apigateway@1.47.0 @aws-cdk/aws-dynamodb@1.47.0 @aws-cdk/aws-cognito@1.47.0 @aws-solutions-constructs/aws-cognito-apigateway-lambda@1.47.0 @aws-solutions-constructs/aws-lambda-dynamodb@1.47.0

Constructsを使ってCDKを記述します。

import * as cdk from "@aws-cdk/core";
import * as lambda from "@aws-cdk/aws-lambda";
import { CognitoToApiGatewayToLambda } from "@aws-solutions-constructs/aws-cognito-apigateway-lambda";
import { LambdaToDynamoDB } from "@aws-solutions-constructs/aws-lambda-dynamodb";
import {
  AttributeType,
  BillingMode,
  TableEncryption,
} from "@aws-cdk/aws-dynamodb";

export class CdkWebappStack extends cdk.Stack {
  constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
    super(scope, id, props);

    // The code that defines your stack goes here
    const apigwToLambda = new CognitoToApiGatewayToLambda(
      this,
      "CognitoToApiGatewayToLambdaPattern",
      {
        deployLambda: true,
        lambdaFunctionProps: {
          runtime: lambda.Runtime.NODEJS_12_X,
          handler: "index.handler",
          code: lambda.Code.asset(`${__dirname}/lambda`),
        },
      }
    );

    new LambdaToDynamoDB(this, "LambdaToDynamoPattern", {
      deployLambda: false,
      existingLambdaObj: apigwToLambda.lambdaFunction, // 生成済みのLambdaを使用
      dynamoTableProps: {
        partitionKey: { name: "id", type: AttributeType.STRING },
        // デフォルトの設定は以下の通り
        //   キャパシティーモード: オンデマンド
        //   暗号化タイプ: KMS - AWSマネージドCMK
        // 無料枠で使用するために設定を変更している。
        billingMode: BillingMode.PROVISIONED,
        readCapacity: 5,
        writeCapacity: 5,
        encryption: TableEncryption.DEFAULT,
      },
    });
  }
}

lib/lambdaディレクトリにはlambdaのソースを配置します。

index.js
const { DynamoDB } = require("aws-sdk");

exports.handler = async function (event) {
  console.log("request:", JSON.stringify(event, undefined, 2));

  // create AWS SDK clients
  const dynamo = new DynamoDB();

  // APIのパスをパーティションキーとして、アクセス回数を記録する
  await dynamo
    .updateItem({
      TableName: process.env.DDB_TABLE_NAME,
      Key: { id: { S: event.path } },
      UpdateExpression: "ADD hits :incr",
      ExpressionAttributeValues: { ":incr": { N: "1" } },
    })
    .promise();

  return {
    statusCode: 200,
    headers: { "Content-Type": "text/plain" },
    body: `Hello, AWS Solutions Constructs! You've hit ${event.path}\n`,
  };
};

以下のコマンドでインフラをデプロイできます

npm run build && cdk deploy

cdk deploy実行時にリソースのデプロイ確認があるので、yを入力してデプロイを開始しましょう。

API Gatewayのコンソールから/fooメソッドのテストをおこなうと正常にレスポンスが返されることが確認できます。

スクリーンショット 2020-07-08 00.40.13.png

また、DynamoDBに、アクセスしたパスの文字列とアクセス回数が記録されていることが確認できます。

スクリーンショット 2020-07-08 00.41.51.png

まとめ

このように、Solution ConstructsではAWSでよく使われるリソースの組み合わせをConstructsをして提供してくれています。それを利用することで、爆速で今までよりもすばやく、かつ、Well-Architectedに準拠したインフラを構築することが可能になりました。

参考

3
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
2