From 1ee34153cb52f1d3c92e4bebc537d23f6af82856 Mon Sep 17 00:00:00 2001 From: Kyle Roach Date: Mon, 24 May 2021 14:34:14 -0400 Subject: [PATCH 1/2] feat: http api - iam authorizer Last outstanding authorizer for http apis. resolves #10534 --- .../aws-apigatewayv2-authorizers/README.md | 23 ++ .../lib/http/iam.ts | 12 + .../test/http/iam.test.ts | 39 +++ .../test/http/integ.iam.expected.json | 258 ++++++++++++++++++ .../test/http/integ.iam.ts | 46 ++++ .../test/integ.iam.signature/.env.example | 4 + .../test/integ.iam.signature/.gitignore | 3 + .../test/integ.iam.signature/README.md | 21 ++ .../test/integ.iam.signature/index.js | 30 ++ .../test/integ.iam.signature/package.json | 10 + .../test/integ.iam.signature/yarn.lock | 20 ++ .../aws-apigatewayv2/lib/http/authorizer.ts | 1 + .../aws-apigatewayv2/lib/http/route.ts | 5 +- .../aws-apigatewayv2/test/http/route.test.ts | 2 +- 14 files changed, 472 insertions(+), 2 deletions(-) create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/lib/http/iam.ts create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.expected.json create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.ts create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.env.example create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.gitignore create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/README.md create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/index.js create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/package.json create mode 100644 packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/yarn.lock diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/README.md b/packages/@aws-cdk/aws-apigatewayv2-authorizers/README.md index 7dd9c2f5e61bd..8ea658d903a23 100644 --- a/packages/@aws-cdk/aws-apigatewayv2-authorizers/README.md +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/README.md @@ -25,6 +25,7 @@ - [JWT Authorizers](#jwt-authorizers) - [User Pool Authorizer](#user-pool-authorizer) - [Lambda Authorizers](#lambda-authorizers) +- [IAM Authorizers](#iam-authorizers) ## Introduction @@ -192,3 +193,25 @@ api.addRoutes({ authorizer, }); ``` + +## IAM Authorizers + +IAM Authorizers allow and restrict clients from accessing HTTP APIs by using IAM Policies. Unlike the other authorizers, the IAM Authorizer doesn't create a new resource in your stack, but configures the route(s) to use IAM authorization. + +Clients are actual users defined in the IAM console with generated AWS Credentials. When enabled for a route, clients must use [Signature Version 4](https://docs.aws.amazon.com/general/latest/gr/signature-version-4.html) to sign their requests with AWS credentials. + +Using this authorizer requires assigning the relevant policies for each client. Here are some [examples](https://docs.aws.amazon.com/apigateway/latest/developerguide/api-gateway-control-access-using-iam-policies-to-invoke-api.html). + +```ts +const authorizer = new HttpIamAuthorizer(); + +const api = new HttpApi(stack, 'HttpApi'); + +api.addRoutes({ + integration: new HttpProxyIntegration({ + url: 'https://get-books-proxy.myproxy.internal', + }), + path: '/books', + authorizer, +}); +``` diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/lib/http/iam.ts b/packages/@aws-cdk/aws-apigatewayv2-authorizers/lib/http/iam.ts new file mode 100644 index 0000000000000..f48b5642840d1 --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/lib/http/iam.ts @@ -0,0 +1,12 @@ +import { HttpRouteAuthorizerConfig, IHttpRouteAuthorizer } from '@aws-cdk/aws-apigatewayv2'; + +/** + * Authorize Http Api routes with IAM using sigv4 to sign request + */ +export class HttpIamAuthorizer implements IHttpRouteAuthorizer { + public bind(): HttpRouteAuthorizerConfig { + return { + authorizationType: 'AWS_IAM', + }; + } +} diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts new file mode 100644 index 0000000000000..4a50287fe1363 --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts @@ -0,0 +1,39 @@ +import '@aws-cdk/assert-internal/jest'; +import { ABSENT } from '@aws-cdk/assert-internal'; +import { HttpApi, IHttpRouteIntegration, HttpRouteIntegrationBindOptions, PayloadFormatVersion, HttpIntegrationType } from '@aws-cdk/aws-apigatewayv2'; +import { Stack } from '@aws-cdk/core'; +import { HttpIamAuthorizer } from '../../lib/http/iam'; + +describe('HttpIamAuthorizer', () => { + test('default', () => { + // GIVEN + const stack = new Stack(); + const api = new HttpApi(stack, 'HttpApi'); + + const authorizer = new HttpIamAuthorizer(); + + // WHEN + api.addRoutes({ + integration: new DummyRouteIntegration(), + path: '/books', + authorizer, + }); + + // THEN + expect(stack).toHaveResource('AWS::ApiGatewayV2::Route', { + AuthorizationType: 'AWS_IAM', + AuthorizerId: ABSENT, + }); + }); +}); + + +class DummyRouteIntegration implements IHttpRouteIntegration { + public bind(_: HttpRouteIntegrationBindOptions) { + return { + payloadFormatVersion: PayloadFormatVersion.VERSION_2_0, + type: HttpIntegrationType.HTTP_PROXY, + uri: 'some-uri', + }; + } +} diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.expected.json b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.expected.json new file mode 100644 index 0000000000000..96419f0234253 --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.expected.json @@ -0,0 +1,258 @@ +{ + "Resources": { + "MyHttpApi8AEAAC21": { + "Type": "AWS::ApiGatewayV2::Api", + "Properties": { + "Name": "MyHttpApi", + "ProtocolType": "HTTP" + } + }, + "MyHttpApiDefaultStageDCB9BC49": { + "Type": "AWS::ApiGatewayV2::Stage", + "Properties": { + "ApiId": { + "Ref": "MyHttpApi8AEAAC21" + }, + "StageName": "$default", + "AutoDeploy": true + } + }, + "MyHttpApiGETIAMAuthorizerIntegMyHttpApiGET271B2CE5PermissionE3A1E0E1": { + "Type": "AWS::Lambda::Permission", + "Properties": { + "Action": "lambda:InvokeFunction", + "FunctionName": { + "Fn::GetAtt": [ + "lambda8B5974B5", + "Arn" + ] + }, + "Principal": "apigateway.amazonaws.com", + "SourceArn": { + "Fn::Join": [ + "", + [ + "arn:", + { + "Ref": "AWS::Partition" + }, + ":execute-api:", + { + "Ref": "AWS::Region" + }, + ":", + { + "Ref": "AWS::AccountId" + }, + ":", + { + "Ref": "MyHttpApi8AEAAC21" + }, + "/*/*/" + ] + ] + } + } + }, + "MyHttpApiGETHttpIntegration6f095b8469365f72e33fa33d9711b140516EBE31": { + "Type": "AWS::ApiGatewayV2::Integration", + "Properties": { + "ApiId": { + "Ref": "MyHttpApi8AEAAC21" + }, + "IntegrationType": "AWS_PROXY", + "IntegrationUri": { + "Fn::GetAtt": [ + "lambda8B5974B5", + "Arn" + ] + }, + "PayloadFormatVersion": "2.0" + } + }, + "MyHttpApiGETE0EFC6F8": { + "Type": "AWS::ApiGatewayV2::Route", + "Properties": { + "ApiId": { + "Ref": "MyHttpApi8AEAAC21" + }, + "RouteKey": "GET /", + "AuthorizationType": "AWS_IAM", + "Target": { + "Fn::Join": [ + "", + [ + "integrations/", + { + "Ref": "MyHttpApiGETHttpIntegration6f095b8469365f72e33fa33d9711b140516EBE31" + } + ] + ] + } + } + }, + "lambdaServiceRole494E4CA6": { + "Type": "AWS::IAM::Role", + "Properties": { + "AssumeRolePolicyDocument": { + "Statement": [ + { + "Action": "sts:AssumeRole", + "Effect": "Allow", + "Principal": { + "Service": "lambda.amazonaws.com" + } + } + ], + "Version": "2012-10-17" + }, + "ManagedPolicyArns": [ + { + "Fn::Join": [ + "", + [ + "arn:", + { + "Ref": "AWS::Partition" + }, + ":iam::aws:policy/service-role/AWSLambdaBasicExecutionRole" + ] + ] + } + ] + } + }, + "lambda8B5974B5": { + "Type": "AWS::Lambda::Function", + "Properties": { + "Code": { + "S3Bucket": { + "Ref": "AssetParameters1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cdaS3Bucket2E6D85D3" + }, + "S3Key": { + "Fn::Join": [ + "", + [ + { + "Fn::Select": [ + 0, + { + "Fn::Split": [ + "||", + { + "Ref": "AssetParameters1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cdaS3VersionKey22B8E7C6" + } + ] + } + ] + }, + { + "Fn::Select": [ + 1, + { + "Fn::Split": [ + "||", + { + "Ref": "AssetParameters1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cdaS3VersionKey22B8E7C6" + } + ] + } + ] + } + ] + ] + } + }, + "Role": { + "Fn::GetAtt": [ + "lambdaServiceRole494E4CA6", + "Arn" + ] + }, + "Handler": "index.handler", + "Runtime": "nodejs12.x" + }, + "DependsOn": [ + "lambdaServiceRole494E4CA6" + ] + }, + "testuser14267055": { + "Type": "AWS::IAM::User", + "Properties": { + "ManagedPolicyArns": [ + { + "Fn::Join": [ + "", + [ + "arn:", + { + "Ref": "AWS::Partition" + }, + ":iam::aws:policy/AmazonAPIGatewayInvokeFullAccess" + ] + ] + } + ] + } + }, + "accesskey": { + "Type": "AWS::IAM::AccessKey", + "Properties": { + "UserName": { + "Ref": "testuser14267055" + } + } + } + }, + "Parameters": { + "AssetParameters1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cdaS3Bucket2E6D85D3": { + "Type": "String", + "Description": "S3 bucket for asset \"1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cda\"" + }, + "AssetParameters1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cdaS3VersionKey22B8E7C6": { + "Type": "String", + "Description": "S3 key for asset version \"1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cda\"" + }, + "AssetParameters1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cdaArtifactHash82A279EA": { + "Type": "String", + "Description": "Artifact hash for asset \"1fd1c15cb7d5e2e36a11745fd10b4b7c3ca8eb30642b41954630413d2b913cda\"" + } + }, + "Outputs": { + "apiurl": { + "Value": { + "Fn::Join": [ + "", + [ + "https://", + { + "Ref": "MyHttpApi8AEAAC21" + }, + ".execute-api.", + { + "Ref": "AWS::Region" + }, + ".", + { + "Ref": "AWS::URLSuffix" + }, + "/" + ] + ] + } + }, + "accesskey": { + "Value": { + "Ref": "accesskey" + } + }, + "secretaccesskey": { + "Value": { + "Fn::GetAtt": [ + "accesskey", + "SecretAccessKey" + ] + } + } + } +} \ No newline at end of file diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.ts b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.ts new file mode 100644 index 0000000000000..2634284408f17 --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/integ.iam.ts @@ -0,0 +1,46 @@ +import * as path from 'path'; +import { HttpApi, HttpMethod } from '@aws-cdk/aws-apigatewayv2'; +import { LambdaProxyIntegration } from '@aws-cdk/aws-apigatewayv2-integrations'; +import { User, CfnAccessKey, ManagedPolicy } from '@aws-cdk/aws-iam'; +import * as lambda from '@aws-cdk/aws-lambda'; +import { App, Stack, CfnOutput } from '@aws-cdk/core'; +import { HttpIamAuthorizer } from '../../lib/http/iam'; + +/* + * Stack verification steps: + * * `curl ` should return 403 + * * `curl -H 'Authorization: ' -H 'x-amz-date: ' -H 'Accept: application/json' ` should return 200 + * @see [../integ.iam.signature/README.md] to generate header values using this stack's outputs +*/ + +const app = new App(); +const stack = new Stack(app, 'IAMAuthorizerInteg'); + +const httpApi = new HttpApi(stack, 'MyHttpApi'); + +const authorizer = new HttpIamAuthorizer(); + +const handler = new lambda.Function(stack, 'lambda', { + runtime: lambda.Runtime.NODEJS_12_X, + handler: 'index.handler', + code: lambda.AssetCode.fromAsset(path.join(__dirname, '../integ.lambda.handler')), +}); + +httpApi.addRoutes({ + path: '/', + methods: [HttpMethod.GET], + integration: new LambdaProxyIntegration({ handler }), + authorizer, +}); + +const user = new User(stack, 'test-user'); + +user.addManagedPolicy(ManagedPolicy.fromAwsManagedPolicyName('AmazonAPIGatewayInvokeFullAccess')); + +const accessKey = new CfnAccessKey(stack, 'access-key', { + userName: user.userName, +}); + +new CfnOutput(stack, 'api_url', { value: httpApi.url! }); +new CfnOutput(stack, 'access_key', { value: accessKey.ref }); +new CfnOutput(stack, 'secret_access_key', { value: accessKey.attrSecretAccessKey }); \ No newline at end of file diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.env.example b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.env.example new file mode 100644 index 0000000000000..5a4cbcffad3ed --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.env.example @@ -0,0 +1,4 @@ +AWS_ACCESS_KEY_ID= +AWS_SECRET_KEY= +AWS_REGION= +AWS_API_GATEWAY_ENDPOINT= \ No newline at end of file diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.gitignore b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.gitignore new file mode 100644 index 0000000000000..48a21d2417085 --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/.gitignore @@ -0,0 +1,3 @@ +.env +headers.yaml +!index.js \ No newline at end of file diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/README.md b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/README.md new file mode 100644 index 0000000000000..fbcc13dcfc856 --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/README.md @@ -0,0 +1,21 @@ +# SigV4 API Gateway generator + +This is quick node script to generate the SigV4 headers needed to perform an HTTP request for an API Gateway that uses IAM route authorization. + +## Setup + +```bash +# Install dependencies +yarn + +# Setup env +cp .env.example .env +``` + +After filling in the variables, start the script. + +```bash +node index.js +``` + +The headers needed to make the http request are generated to `./headers.yaml`. diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/index.js b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/index.js new file mode 100644 index 0000000000000..1fdcbf6b78e8a --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/index.js @@ -0,0 +1,30 @@ +require('dotenv').config(); + +const fs = require('fs'); +const path = require('path'); +const awsV4 = require('aws-v4'); + +const { headers } = awsV4 + .newClient({ + accessKey: process.env.AWS_ACCESS_KEY_ID, + secretKey: process.env.AWS_SECRET_KEY, + region: process.env.AWS_REGION, + endpoint: process.env.AWS_API_GATEWAY_ENDPOINT, + }) + .signRequest({ + method: 'get', + path: '/', + headers: { + 'Content-Type': 'application/json', + }, + queryParams: {}, + body: {}, + }); +fs.writeFileSync( + path.join(__dirname, './headers.yaml'), + `Accept: ${headers.Accept} +x-amz-date: ${headers['x-amz-date']} +Authorization: ${headers.Authorization} +Content-Type: ${headers['Content-Type']} +` +); diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/package.json b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/package.json new file mode 100644 index 0000000000000..317323992ca7e --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/package.json @@ -0,0 +1,10 @@ +{ + "name": "sig-v4-generator", + "version": "1.0.0", + "main": "index.js", + "license": "MIT", + "dependencies": { + "aws-v4": "^1.0.0", + "dotenv": "^10.0.0" + } +} diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/yarn.lock b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/yarn.lock new file mode 100644 index 0000000000000..7de7d7083f08e --- /dev/null +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/integ.iam.signature/yarn.lock @@ -0,0 +1,20 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +aws-v4@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/aws-v4/-/aws-v4-1.0.0.tgz#611e07c1019cb33a3138a7d5a396d30ad7818689" + integrity sha512-BBa72vu6EUTSKf6f1ecYWcnsHc9TCGjFxAxrcCDxIwflPf5gWyJCHc0y7XzpDrXd30Q4hiswRKZQOK60Z02EnQ== + dependencies: + crypto-js "^3.1.9-1" + +crypto-js@^3.1.9-1: + version "3.3.0" + resolved "https://registry.yarnpkg.com/crypto-js/-/crypto-js-3.3.0.tgz#846dd1cce2f68aacfa156c8578f926a609b7976b" + integrity sha512-DIT51nX0dCfKltpRiXV+/TVZq+Qq2NgF4644+K7Ttnla7zEzqc+kjJyiB96BHNyUTBxyjzRcZYpUdZa+QAqi6Q== + +dotenv@^10.0.0: + version "10.0.0" + resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-10.0.0.tgz#3d4227b8fb95f81096cdd2b66653fb2c7085ba81" + integrity sha512-rlBi9d8jpv9Sf1klPjNfFAuWDjKLwTIJJ/VxtoTwIR6hnZxcEOQCZg2oIL3MWBYw5GpUDKOEnND7LXTbIpQ03Q== diff --git a/packages/@aws-cdk/aws-apigatewayv2/lib/http/authorizer.ts b/packages/@aws-cdk/aws-apigatewayv2/lib/http/authorizer.ts index 08936ecf36d8f..572b6d9332142 100644 --- a/packages/@aws-cdk/aws-apigatewayv2/lib/http/authorizer.ts +++ b/packages/@aws-cdk/aws-apigatewayv2/lib/http/authorizer.ts @@ -223,6 +223,7 @@ export interface HttpRouteAuthorizerConfig { * Possible values are: * - JWT - JSON Web Token Authorizer * - CUSTOM - Lambda Authorizer + * - AWS_IAM - IAM Polices * - NONE - No Authorization */ readonly authorizationType: string; diff --git a/packages/@aws-cdk/aws-apigatewayv2/lib/http/route.ts b/packages/@aws-cdk/aws-apigatewayv2/lib/http/route.ts index a88aaae0b3416..4f9dca49110f0 100644 --- a/packages/@aws-cdk/aws-apigatewayv2/lib/http/route.ts +++ b/packages/@aws-cdk/aws-apigatewayv2/lib/http/route.ts @@ -130,6 +130,9 @@ enum HttpRouteAuthorizationType { /** Lambda Authorizer */ CUSTOM = 'CUSTOM', + /** IAM Authorization */ + AWS_IAM = 'AWS_IAM', + /** No authorizer */ NONE = 'NONE' } @@ -162,7 +165,7 @@ export class HttpRoute extends Resource implements IHttpRoute { }) : undefined; if (authBindResult && !(authBindResult.authorizationType in HttpRouteAuthorizationType)) { - throw new Error('authorizationType should either be JWT, CUSTOM, or NONE'); + throw new Error('authorizationType should either be JWT, CUSTOM, AWS_IAM, or NONE'); } let authorizationScopes = authBindResult?.authorizationScopes; diff --git a/packages/@aws-cdk/aws-apigatewayv2/test/http/route.test.ts b/packages/@aws-cdk/aws-apigatewayv2/test/http/route.test.ts index f30bdaba9205e..c032f47e1af21 100644 --- a/packages/@aws-cdk/aws-apigatewayv2/test/http/route.test.ts +++ b/packages/@aws-cdk/aws-apigatewayv2/test/http/route.test.ts @@ -254,7 +254,7 @@ describe('HttpRoute', () => { integration: new DummyIntegration(), routeKey: HttpRouteKey.with('/books', HttpMethod.GET), authorizer, - })).toThrowError('authorizationType should either be JWT, CUSTOM, or NONE'); + })).toThrowError('authorizationType should either be JWT, CUSTOM, AWS_IAM, or NONE'); }); }); From 604cc1d35360f1f7e77cfacf41e146a9f2afed0f Mon Sep 17 00:00:00 2001 From: Kyle Roach Date: Wed, 9 Jun 2021 13:23:23 -0400 Subject: [PATCH 2/2] test: add unit test for default integration --- .../test/http/iam.test.ts | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts index 4a50287fe1363..665732f7486e9 100644 --- a/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts +++ b/packages/@aws-cdk/aws-apigatewayv2-authorizers/test/http/iam.test.ts @@ -25,6 +25,24 @@ describe('HttpIamAuthorizer', () => { AuthorizerId: ABSENT, }); }); + + test('default integration', () => { + // GIVEN + const stack = new Stack(); + const authorizer = new HttpIamAuthorizer(); + + // WHEN + new HttpApi(stack, 'HttpApi', { + defaultAuthorizer: authorizer, + defaultIntegration: new DummyRouteIntegration(), + }); + + // THEN + expect(stack).toHaveResource('AWS::ApiGatewayV2::Route', { + AuthorizationType: 'AWS_IAM', + AuthorizerId: ABSENT, + }); + }); });