We are trying to automate the deployment of AWS lambda and API gateway using Amazon CloudFormation and Swagger. Towards this, we have created a CloudFormation template to create the Lambda and other resources required for APIGateway (including the endpoints). We would like to import the API definitions from an external swagger file so that the same CloudFormation template can be used for multiple lambdas and APIGateways. Is there a way we can refer the ARN of the lambda which has been created by the CloudFormation template in the external swagger file (being referred to in the same CloudFormation template) which holds the API definition?
Swagger content:
"x-amazon-apigateway-integration": {
"uri": "arn:aws:apigateway:us-east-1:lambda:path/2015-03-31/functions/arn:aws:lambda:us-east-1:123456789012:function:TestSimpleProxy/invocations",
"passthroughBehavior": "when_no_match",
"httpMethod": "POST",
"type": "aws_proxy"
}
In the above integration method I need to replace the value of the uri dynamically from the cloud formation template.
My cloud formation script is as below:
"myApi":{
"Type" : "AWS::ApiGateway::RestApi",
"Properties" : {
"BodyS3Location" : S3Location of the swagger definition file,
..,
..
}
}
New solution:
It is now possible to use the new AWS::Include
Transform to reference the uploaded template directly from a CloudFormation template:
Api:
Type: AWS::ApiGateway::RestApi
Properties:
Body:
Fn::Transform:
Name: AWS::Include
Parameters:
Location: !Sub s3://${ArtifactsBucket}/swagger.yaml
where ArtifactsBucket
refers to the bucket where you upload Swagger spec before you create or update your stack. Then, in the Swagger template itself you can use the intrinsics, e.g.
x-amazon-apigateway-integration:
type: aws_proxy
httpMethod: POST
uri:
Fn::Sub: arn:aws:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/${LambdaFunction.Arn}/invocations
Here I'm using the long Fn::Sub
notation instead of just !Sub
, because Swagger doesn't natively support the latter, and also because the docs on AWS::Include
Transform say that shorthand forms are not supported yet.
You can also use AWS::Serverless::Api
and DefinitionBody
if you use SAM.
Old workaround:
Another (somewhat hacky, yet simple) solution is to list the Api as the last resource in the CloudFormation template, and specify an empty Body with : !Sub |-
at the end.
You can then concatenate this template with the actual Swagger file, and reference any parameters using the standard ${}
syntax in that file.
The only minor complication is that you have to properly indent the Swagger file when concatenating it when you're using YAML (this approach won't work for JSON templates though; you'll have to substitute Body with something like jq
if you use these).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With