Amazon API Gateway Deployment with CloudFormation: Difference between revisions
(7 intermediate revisions by the same user not shown) | |||
Line 3: | Line 3: | ||
* https://currentlyunnamed-theclassic.blogspot.com/2018/12/mastering-cloudformation-for-api.html | * https://currentlyunnamed-theclassic.blogspot.com/2018/12/mastering-cloudformation-for-api.html | ||
* https://stackoverflow.com/questions/41423439/cloudformation-doesnt-deploy-to-api-gateway-stages-on-update | * https://stackoverflow.com/questions/41423439/cloudformation-doesnt-deploy-to-api-gateway-stages-on-update | ||
* [https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/cfn-reference-apigateway.html Amazon API Gateway Resource Types Reference] | |||
=Internal= | =Internal= | ||
Line 27: | Line 28: | ||
Bucket: 'ovidiu-experiments' | Bucket: 'ovidiu-experiments' | ||
Key: 'openapi-aws.json' | Key: 'openapi-aws.json' | ||
The "Name" property, if specified, overrides OpenAPI document [[OpenAPI_Specification#title|title]]. | |||
==AWS::ApiGateway::Deployment== | ==AWS::ApiGateway::Deployment== | ||
Line 106: | Line 109: | ||
==AWS::ApiGateway::VpcLink== | ==AWS::ApiGateway::VpcLink== | ||
{{External|[https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-vpclink.html AWS::ApiGateway::VpcLink]}} | {{External|[https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-vpclink.html AWS::ApiGateway::VpcLink]}} | ||
Parameters: | |||
NetworkLoadBalancerArn: | |||
Type: String | |||
Default: arn:aws:elasticloadbalancing:us-west-2:777777777777:loadbalancer/net/some-nlb/1a49bf234253e5a0 | |||
Resources: | |||
VpcLink: | |||
Type: AWS::ApiGateway::VpcLink | |||
Properties: | |||
Name: 'blue' | |||
Description: 'Some description' | |||
[[Amazon_API_Gateway_Concepts#Target_Load_Balancer|TargetArns]]: | |||
- !Ref NetworkLoadBalancerArn | |||
Note that if the load balancer is created as part of the same stack, !Ref NetworkLoadBalancer returns the ARN. | |||
If an ALB ARN is used, the VpcLink creation will fail with a complain about the inconsistent load balancer ARN. | |||
=Idiosyncrasy= | =Idiosyncrasy= |
Latest revision as of 17:53, 16 April 2019
External
- https://currentlyunnamed-theclassic.blogspot.com/2018/12/mastering-cloudformation-for-api.html
- https://stackoverflow.com/questions/41423439/cloudformation-doesnt-deploy-to-api-gateway-stages-on-update
- Amazon API Gateway Resource Types Reference
Internal
Overview
Resource Types
AWS::ApiGateway::RestApi
Resources: Api: Type: AWS::ApiGateway::RestApi Properties: Name: 'experimental-api' Description: 'An experimental API, deployed programmatically' FailOnWarnings: true BodyS3Location: Bucket: 'ovidiu-experiments' Key: 'openapi-aws.json'
The "Name" property, if specified, overrides OpenAPI document title.
AWS::ApiGateway::Deployment
Resources: ApiDeployment: Type: AWS::ApiGateway::Deployment DependsOn: Api Properties: RestApiId: !Ref Api Description: 'something'
If StageName: is specified and the stage does not exist, it will be created.
AWS::ApiGateway::Stage
Resources: Stage: Type: AWS::ApiGateway::Stage DependsOn: - Api - ApiDeployment Properties: StageName: 'dev' RestApiId: !Ref Api DeploymentId: !Ref ApiDeployment
Execution Logging Configuration
Resources:
Stage:
Type: AWS::ApiGateway::Stage
...
Properties:
...
MethodSettings:
- ResourcePath: '/*'
HttpMethod: '*'
LoggingLevel: 'INFO'
The above configuration turns on execution logging for all resource paths and all http methods. Individual configuration can be specified, for details see Stage Reference - methodSettings.
For more details on API Gateway execution logging see:
Access Logging Configuration
Resources:
AccessLogGroup:
Type: AWS::Logs::LogGroup
Properties:
LogGroupName: ...
...
Stage:
Type: AWS::ApiGateway::Stage
...
Properties:
...
AccessLogSetting:
DestinationArn: !GetAtt AccessLogGroup.Arn
Format: >-
{"requestId":"$context.requestId", "ip": "$context.identity.sourceIp",
"caller":"$context.identity.caller",
"user":"$context.identity.user","requestTime":"$context.requestTime",
"eventType":"$context.eventType","routeKey":"$context.routeKey",
"status":"$context.status","connectionId":"$context.connectionId"}
For more details about access logging, see:
AWS::ApiGateway::VpcLink
Parameters: NetworkLoadBalancerArn: Type: String Default: arn:aws:elasticloadbalancing:us-west-2:777777777777:loadbalancer/net/some-nlb/1a49bf234253e5a0 Resources: VpcLink: Type: AWS::ApiGateway::VpcLink Properties: Name: 'blue' Description: 'Some description' TargetArns: - !Ref NetworkLoadBalancerArn
Note that if the load balancer is created as part of the same stack, !Ref NetworkLoadBalancer returns the ARN.
If an ALB ARN is used, the VpcLink creation will fail with a complain about the inconsistent load balancer ARN.
Idiosyncrasy
As per March 2019, an attempt to re-deploy a new version of an API, as expressed in a version of an Open API file, with CloudFormation, does not work as expected. CloudFormation AWS::ApiGateway::RestApi resource update, as described above, works fine: the new API content is deployed and visible in the console. One would expect that the AWS::ApiGateway::Deployment resource, declared above, would detect that the API changed and re-snapshot it. However, that does not happens. No new deployment is created. As consequence, the stage points to a stale deployment. Changing the description of a Deployment does not work either, the description will be updated on the current deployment, but the content of the API snapshot won't change.
On the same subject:
- https://medium.com/@ngchiwang/aws-apigateway-deployment-not-update-3e04fcffe85b. This one did not work, the template modified as described triggered a validation error: "An error occurred (ValidationError) when calling the CreateStack operation: Template format error: Resource name ApiDeployment$timestamp is non alphanumeric."
- https://stackoverflow.com/questions/41423439/cloudformation-doesnt-deploy-to-api-gateway-stages-on-update
Possible solutions:
Add Deployments and Stages to the Template
Add a new AWS::ApiGateway::Deployment, with a different logical name, irrespective of whether we keep the old one or now:
Resources:
Api:
...
ApiDeployment:
Type: AWS::ApiGateway::Deployment
DependsOn: Api
Properties:
RestApiId: !Ref Api
Stage:
Type: AWS::ApiGateway::Stage
DependsOn:
- Api
- ApiDeployment
Properties:
StageName: !Sub 'v0'
RestApiId: !Ref Api
DeploymentId: !Ref ApiDeployment
ApiDeployment2:
Type: AWS::ApiGateway::Deployment
DependsOn: Api
Properties:
RestApiId: !Ref Api
Stage2:
Type: AWS::ApiGateway::Stage
DependsOn:
- Api
- ApiDeployment2
Properties:
StageName: 'v2'
RestApiId: !Ref Api
DeploymentId: !Ref ApiDeployment2
Dynamically Change The Stack Template and Modify the API Deployment and Stage Logical IDs
Use timestamp or a counter.
Deploy API via CLI
Do not deploy the API and create the Stage with CloudFormation, but programmatically via CLI, from a follow up action.
Nested Stacks
Nested stacks, that describe new Deployment and stage.
Lambda-Backed Custom Resource
http://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/template-custom-resources.html