Hello Devs,
I am going to tell you one AWS SAM issue regarding resource AWS::Serverless::Api
and transform AWS::Serverless-2016-10-31
raised over StackOverflow and their solution to tackle temporary basis because this issue still exist. Let me explain what is a problem first.
Problem statement :
While creating AWS Serverless API gateway using SAM this configuration to deploy to the 'Prod' Stage along with serverless code sample, but while creating resources it create two stage under API gateway one which you provided as per below example and one is default Stage. So if you want to create own Stage can't create it throw you error is Stage already exists
:
AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: AWS SAM template with a simple API definition
Resources:
ApiGatewayApi:
Type: AWS::Serverless::Api
Properties:
StageName: prod
ApiFunction: # Adds a GET api endpoint at "/" to the ApiGatewayApi via an Api event
Type: AWS::Serverless::Function
Properties:
Events:
ApiEvent:
Type: Api
Properties:
Path: /
Method: get
RestApiId:
Ref: ApiGatewayApi
Runtime: python3.7
Handler: index.handler
InlineCode: |
def handler(event, context):
return {'body': 'Hello World!', 'statusCode': 200}
There is a bug in AWS SAM whenever you create StageName
it creates the default Stage along with the stage name which you provided like Prod. First you delete your current one then you can apply these changes.
To solve this issue there is two ways by adding OpenApiVersion: '2.0'
in your YAML file :
Solution 1: Under properties following StageName
can add this. This properties can be added for AWS::Serverless::Api
or other resources like AWS::Serverless::Lambda
.
AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: AWS SAM template with a simple API definition
Resources:
ApiGatewayApi:
Type: AWS::Serverless::Api
Properties:
StageName: 'V1'
OpenApiVersion: '2.0'
ApiFunction: # Adds a GET api endpoint at "/" to the ApiGatewayApi via an Api event
Type: AWS::Serverless::Function
Properties:
Events:
ApiEvent:
Type: Api
Properties:
Path: /
Method: get
RestApiId:
Ref: ApiGatewayApi
Runtime: python3.7
Handler: index.handler
InlineCode: |
def handler(event, context):
return {'body': 'Hello World!', 'statusCode': 200}
Solution 2: The following to your SAM template at the top level AND be sure you have defined a stage using "StageName" on your AWS::Serverless:Api resource. This will be global level if you have multiple resources like API or lambda etc.
Globals:
Api:
OpenApiVersion: 3.0.1
Cors: '*'
Resources:
ImplicitApiFunction:
Type: AWS::Serverless::Function
Properties:
CodeUri: s3://sam-demo-bucket/member_portal.zip
Handler: index.gethtml
Runtime: nodejs12.x
Events:
GetHtml:
Type: Api
Properties:
Path: /
Method: get
ExplicitApi:
Type: AWS::Serverless::Api
Properties:
StageName: Prod
Note: This solution works ONLY when one creates an API from scratch. If an API was created before, and the user adds OpenApiVersion: '2.0'
to it, it doesn't remove the "Stage" stage. It needs to be added from the beginning. Also this example for YAML same can be applied for JSON format.
If you like my blog please like the article, It will encourage me to write more such problem oriented blogs. Do share your valuable suggestions, I appreciate your honest feedback!. If you have any query regarding can reach out to me over my twitter handle @aviboy2006
Reference :
https://github.com/aws/serverless-application-model/blob/master/tests/translator/input/api_with_open_api_version.yaml#L3
https://github.com/aws/serverless-application-model/issues/191#issuecomment-551051431
Top comments (2)
good to know! I always wondered what the purpose of that stage was and if there was a way to eliminate it
That bug they found lately. Still bug is open.