Skip to content

Commit

Permalink
fix: move the normalized open api version to feature flag normalized_…
Browse files Browse the repository at this point in the history
…open_api_version (#3555)
  • Loading branch information
xazhao committed Apr 22, 2024
1 parent 7593908 commit 7d2752b
Show file tree
Hide file tree
Showing 10 changed files with 1,866 additions and 7 deletions.
17 changes: 13 additions & 4 deletions samtranslator/model/api/api_generator.py
Expand Up @@ -3,6 +3,7 @@
from dataclasses import dataclass
from typing import Any, Dict, List, Optional, Set, Tuple, Union, cast

from samtranslator.feature_toggle.feature_toggle import FeatureToggle
from samtranslator.metrics.method_decorator import cw_timer
from samtranslator.model import Resource
from samtranslator.model.apigateway import (
Expand Down Expand Up @@ -40,6 +41,8 @@

LOG = logging.getLogger(__name__)

FEATURE_FLAG_NORMALIZED_OPENAPI_VERSION = "normalized_open_api_version"

_CORS_WILDCARD = "'*'"
CorsProperties = namedtuple(
"CorsProperties", ["AllowMethods", "AllowHeaders", "AllowOrigin", "MaxAge", "AllowCredentials"]
Expand Down Expand Up @@ -205,6 +208,7 @@ def __init__( # noqa: PLR0913
mode: Optional[Intrinsicable[str]] = None,
api_key_source_type: Optional[Intrinsicable[str]] = None,
always_deploy: Optional[bool] = False,
feature_toggle: Optional[FeatureToggle] = None,
):
"""Constructs an API Generator class that generates API Gateway resources
Expand Down Expand Up @@ -261,6 +265,7 @@ def __init__( # noqa: PLR0913
self.mode = mode
self.api_key_source_type = api_key_source_type
self.always_deploy = always_deploy
self.feature_toggle = feature_toggle

def _construct_rest_api(self) -> ApiGatewayRestApi:
"""Constructs and returns the ApiGateway RestApi.
Expand Down Expand Up @@ -1125,11 +1130,15 @@ def _openapi_postprocess(self, definition_body: Dict[str, Any]) -> Dict[str, Any
if definition_body.get("swagger") is not None:
return definition_body

if definition_body.get("openapi") is not None and self.open_api_version is None:
self.open_api_version = definition_body.get("openapi")
if self.feature_toggle and self.feature_toggle.is_enabled(FEATURE_FLAG_NORMALIZED_OPENAPI_VERSION):
normalized_open_api_version = definition_body.get("openapi", self.open_api_version)
elif definition_body.get("openapi") is not None and self.open_api_version is None:
normalized_open_api_version = definition_body.get("openapi")
else:
normalized_open_api_version = self.open_api_version

if self.open_api_version and SwaggerEditor.safe_compare_regex_with_string(
SwaggerEditor._OPENAPI_VERSION_3_REGEX, self.open_api_version
if normalized_open_api_version and SwaggerEditor.safe_compare_regex_with_string(
SwaggerEditor._OPENAPI_VERSION_3_REGEX, normalized_open_api_version
):
if definition_body.get("securityDefinitions"):
components = definition_body.get("components", Py27Dict())
Expand Down
2 changes: 2 additions & 0 deletions samtranslator/model/sam_resources.py
Expand Up @@ -1294,6 +1294,7 @@ def to_cloudformation(self, **kwargs) -> List[Resource]: # type: ignore[no-unty
shared_api_usage_plan = kwargs.get("shared_api_usage_plan")
template_conditions = kwargs.get("conditions")
route53_record_set_groups = kwargs.get("route53_record_set_groups", {})
feature_toggle = kwargs.get("feature_toggle")

api_generator = ApiGenerator(
self.logical_id,
Expand Down Expand Up @@ -1330,6 +1331,7 @@ def to_cloudformation(self, **kwargs) -> List[Resource]: # type: ignore[no-unty
mode=self.Mode,
api_key_source_type=self.ApiKeySourceType,
always_deploy=self.AlwaysDeploy,
feature_toggle=feature_toggle,
)

generated_resources = api_generator.to_cloudformation(redeploy_restapi_parameters, route53_record_set_groups)
Expand Down
@@ -0,0 +1,166 @@
Transform:
- AWS::Serverless-2016-10-31
Resources:
ApiGatewayCognitoExecutionRole4F7CB5C8:
Type: AWS::IAM::Role
Properties:
AssumeRolePolicyDocument:
Statement:
- Action: sts:AssumeRole
Effect: Allow
Principal:
Service: apigateway.amazonaws.com
Version: '2012-10-17'
Policies:
- PolicyDocument:
Statement:
- Action: lambda:Invoke*
Effect: Allow
Resource:
Fn::GetAtt:
- LambdaFunction7804BD21
- Arn
Version: '2012-10-17'
PolicyName: apigInvokeLambda
LambdaFunctionServiceRoleD6E423C9:
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
LambdaFunctionServiceRoleDefaultPolicyF01A7EDC:
Type: AWS::IAM::Policy
Properties:
PolicyDocument:
Statement:
- Action: sns:Publish
Effect: Allow
Resource: '*'
Version: '2012-10-17'
PolicyName: LambdaFunctionServiceRoleDefaultPolicyF01A7EDC
Roles:
- Ref: LambdaFunctionServiceRoleD6E423C9
LambdaFunction7804BD21:
Type: AWS::Lambda::Function
Properties:
Code:
ZipFile: |
exports.handler = async (event, context, callback) => {
const auth = event.queryStringParameters.authorization
const policyDocument = {
Version: '2012-10-17',
Statement: [{
Action: 'execute-api:Invoke',
Effect: auth && auth.toLowerCase() === 'allow' ? 'Allow' : 'Deny',
Resource: event.methodArn
}]
}
return {
principalId: 'user',
context: {},
policyDocument
}
}
Role:
Fn::GetAtt:
- LambdaFunctionServiceRoleD6E423C9
- Arn
Handler: index.handler
Runtime: nodejs16.x
MyCognitoUserPool:
Type: AWS::Cognito::UserPool
Properties:
UserPoolName: MyCognitoUserPool
ApiGatewayCognitoService15108F0B:
Type: AWS::Serverless::Api
Properties:
StageName: prod
Auth:
AddDefaultAuthorizerToCorsPreflight: false
Authorizers:
CognitoAuthorizer:
UserPoolArn:
Fn::GetAtt: MyCognitoUserPool.Arn
DefaultAuthorizer: CognitoAuthorizer
DefinitionBody:
openapi: 3.0.2
info:
title: RxtHofApprovalServiceLambdaCognito
version: '2018-05-10'
paths:
/reviews:
post:
operationId: CreateReview
requestBody:
content:
application/json:
schema:
$ref: '#/components/schemas/CreateReviewRequestContent'
required: true
responses:
'200':
description: CreateReview 200 response
headers:
Access-Control-Allow-Origin:
schema:
type: string
Access-Control-Expose-Headers:
schema:
type: string
content:
application/json:
schema:
$ref: '#/components/schemas/CreateReviewResponseContent'
x-amazon-apigateway-integration:
type: aws_proxy
httpMethod: POST
uri:
Fn::Sub: arn:${AWS::Partition}:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/${LambdaFunction7804BD21.Arn}/invocations
credentials:
Fn::Sub: ${ApiGatewayCognitoExecutionRole4F7CB5C8.Arn}
responses:
default:
statusCode: '200'
responseParameters:
method.response.header.Access-Control-Allow-Origin: "'*'"
method.response.header.Access-Control-Expose-Headers: "'Content-Length,Content-Type,X-Amzn-Errortype,X-Amzn-Requestid'"
components:
schemas:
CreateReviewRequestContent:
type: object
properties:
reviewId:
type: string
CreateReviewResponseContent:
type: object
properties:
reviewId:
type: string
securitySchemes:
aws.auth.sigv4:
type: apiKey
description: AWS Signature Version 4 authentication
name: Authorization
in: header
x-amazon-apigateway-authtype: awsSigv4
security:
- aws.auth.sigv4: []
x-amazon-apigateway-gateway-responses:
DEFAULT_5XX:
responseTemplates:
application/json: '{"message":$context.error.messageString}'
responseParameters:
gatewayresponse.header.Access-Control-Allow-Origin: "'*'"
OpenApiVersion: '2.0'
TracingEnabled: true

0 comments on commit 7d2752b

Please sign in to comment.