Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docs/globals.rst
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ Currently, the following resources and properties are being supported:
TracingEnabled:
OpenApiVersion:
Domain:
SecurityPolicy:

HttpApi:
# Properties of AWS::Serverless::HttpApi
Expand Down
10 changes: 10 additions & 0 deletions samtranslator/internal/schema_source/aws_serverless_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,11 @@ class Properties(BaseModel):
Tags: Optional[DictStrAny] = properties("Tags")
Policy: Optional[PassThroughProp] # TODO: add docs
PropagateTags: Optional[bool] # TODO: add docs
SecurityPolicy: Optional[PassThroughProp] = passthrough_prop(
PROPERTIES_STEM,
"SecurityPolicy",
["AWS::ApiGateway::RestApi", "Properties", "SecurityPolicy"],
)
TracingEnabled: Optional[TracingEnabled] = passthrough_prop(
PROPERTIES_STEM,
"TracingEnabled",
Expand Down Expand Up @@ -392,6 +397,11 @@ class Globals(BaseModel):
Domain: Optional[Domain] = properties("Domain")
AlwaysDeploy: Optional[AlwaysDeploy] = properties("AlwaysDeploy")
PropagateTags: Optional[bool] # TODO: add docs
SecurityPolicy: Optional[PassThroughProp] = passthrough_prop(
PROPERTIES_STEM,
"SecurityPolicy",
["AWS::ApiGateway::RestApi", "Properties", "SecurityPolicy"],
)


class Resource(ResourceAttributes):
Expand Down
3 changes: 2 additions & 1 deletion samtranslator/internal/schema_source/sam-docs.json
Original file line number Diff line number Diff line change
Expand Up @@ -705,6 +705,7 @@
"Name": "A name for the API Gateway RestApi resource \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`Name`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-restapi.html#cfn-apigateway-restapi-name) property of an `AWS::ApiGateway::RestApi` resource\\.",
"OpenApiVersion": "Version of OpenApi to use\\. This can either be `2.0` for the Swagger specification, or one of the OpenApi 3\\.0 versions, like `3.0.1`\\. For more information about OpenAPI, see the [OpenAPI Specification](https://swagger.io/specification/)\\. \n AWS SAM creates a stage called `Stage` by default\\. Setting this property to any valid value will prevent the creation of the stage `Stage`\\. \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is unique to AWS SAM and doesn't have an AWS CloudFormation equivalent\\.",
"PropagateTags": "Indicate whether or not to pass tags from the `Tags` property to your [AWS::Serverless::Api](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-specification-generated-resources-api.html) generated resources\\. Specify `True` to propagate tags in your generated resources\\. \n*Type*: Boolean \n*Required*: No \n*Default*: `False` \n*AWS CloudFormation compatibility*: This property is unique to AWS SAM and doesn't have an AWS CloudFormation equivalent\\.",
"SecurityPolicy": "The Transport Layer Security (TLS) version + cipher suite for this RestApi. \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`SecurityPolicy`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-restapi.html#cfn-apigateway-restapi-securitypolicy) property of an `AWS::ApiGateway::RestApi` resource\\.",
"StageName": "The name of the stage, which API Gateway uses as the first path segment in the invoke Uniform Resource Identifier \\(URI\\)\\. \nTo reference the stage resource, use `<api-logical-id>.Stage`\\. For more information about referencing resources generated when an [AWS::Serverless::Api](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/#sam-resource-api.html#sam-resource-api) resource is specified, see [AWS CloudFormation resources generated when AWS::Serverless::Api is specified](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-specification-generated-resources-api.html)\\. For general information about generated AWS CloudFormation resources, see [Generated AWS CloudFormation resources for AWS SAM](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-specification-generated-resources.html)\\. \n*Type*: String \n*Required*: Yes \n*AWS CloudFormation compatibility*: This property is similar to the [`StageName`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-stage.html#cfn-apigateway-stage-stagename) property of an `AWS::ApiGateway::Stage` resource\\. It is required in SAM, but not required in API Gateway \n*Additional notes*: The Implicit API has a stage name of \"Prod\"\\.",
"Tags": "A map \\(string to string\\) that specifies the tags to be added to this API Gateway stage\\. For details about valid keys and values for tags, see [Resource tag](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-properties-resource-tags.html) in the *AWS CloudFormation User Guide*\\. \n*Type*: Map \n*Required*: No \n*AWS CloudFormation compatibility*: This property is similar to the [`Tags`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-stage.html#cfn-apigateway-stage-tags) property of an `AWS::ApiGateway::Stage` resource\\. The Tags property in SAM consists of Key:Value pairs; in CloudFormation it consists of a list of Tag objects\\.",
"TracingEnabled": "Indicates whether active tracing with X\\-Ray is enabled for the stage\\. For more information about X\\-Ray, see [Tracing user requests to REST APIs using X\\-Ray](https://docs.aws.amazon.com/apigateway/latest/developerguide/apigateway-xray.html) in the *API Gateway Developer Guide*\\. \n*Type*: Boolean \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`TracingEnabled`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-stage.html#cfn-apigateway-stage-tracingenabled) property of an `AWS::ApiGateway::Stage` resource\\.",
Expand Down Expand Up @@ -841,4 +842,4 @@
"UseAliasAsEventTarget": "Indicate whether or not to pass the alias, created by using the `AutoPublishAlias` property, to the events source's target defined with [Events](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/#sam-statemachine-events.html#sam-statemachine-events)\\. \nSpecify `True` to use the alias as the events' target\\. \n*Type*: Boolean \n*Required*: No \n*Default*: `False` \n*AWS CloudFormation compatibility*: This property is unique to AWS SAM and doesn't have an AWS CloudFormation equivalent\\."
}
}
}
}
5 changes: 5 additions & 0 deletions samtranslator/model/api/api_generator.py
Original file line number Diff line number Diff line change
Expand Up @@ -221,6 +221,7 @@ def __init__( # noqa: PLR0913
always_deploy: Optional[bool] = False,
feature_toggle: Optional[FeatureToggle] = None,
policy: Optional[Union[Dict[str, Any], Intrinsicable[str]]] = None,
security_policy: Optional[Intrinsicable[str]] = None,
):
"""Constructs an API Generator class that generates API Gateway resources

Expand Down Expand Up @@ -279,6 +280,7 @@ def __init__( # noqa: PLR0913
self.always_deploy = always_deploy
self.feature_toggle = feature_toggle
self.policy = policy
self.security_policy = security_policy

def _construct_rest_api(self) -> ApiGatewayRestApi:
"""Constructs and returns the ApiGateway RestApi.
Expand Down Expand Up @@ -335,6 +337,9 @@ def _construct_rest_api(self) -> ApiGatewayRestApi:
if self.policy:
rest_api.Policy = self.policy

if self.security_policy:
rest_api.SecurityPolicy = self.security_policy

return rest_api

def _validate_properties(self) -> None:
Expand Down
2 changes: 2 additions & 0 deletions samtranslator/model/apigateway.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ class ApiGatewayRestApi(Resource):
"ApiKeySourceType": GeneratedProperty(),
"Tags": GeneratedProperty(),
"Policy": GeneratedProperty(),
"SecurityPolicy": GeneratedProperty(),
}

Body: Optional[Dict[str, Any]]
Expand All @@ -46,6 +47,7 @@ class ApiGatewayRestApi(Resource):
ApiKeySourceType: Optional[PassThrough]
Tags: Optional[PassThrough]
Policy: Optional[PassThrough]
SecurityPolicy: Optional[PassThrough]

runtime_attrs = {"rest_api_id": lambda self: ref(self.logical_id)}

Expand Down
3 changes: 3 additions & 0 deletions samtranslator/model/sam_resources.py
Original file line number Diff line number Diff line change
Expand Up @@ -1645,6 +1645,7 @@ class SamApi(SamResourceMacro):
"ApiKeySourceType": PropertyType(False, IS_STR),
"AlwaysDeploy": Property(False, IS_BOOL),
"Policy": PropertyType(False, one_of(IS_STR, IS_DICT)),
"SecurityPolicy": PropertyType(False, IS_STR),
}

Name: Optional[Intrinsicable[str]]
Expand Down Expand Up @@ -1677,6 +1678,7 @@ class SamApi(SamResourceMacro):
ApiKeySourceType: Optional[Intrinsicable[str]]
AlwaysDeploy: Optional[bool]
Policy: Optional[Union[Dict[str, Any], Intrinsicable[str]]]
SecurityPolicy: Optional[Intrinsicable[str]]

referable_properties = {
"Stage": ApiGatewayStage.resource_type,
Expand Down Expand Up @@ -1745,6 +1747,7 @@ def to_cloudformation(self, **kwargs) -> List[Resource]: # type: ignore[no-unty
always_deploy=self.AlwaysDeploy,
feature_toggle=feature_toggle,
policy=self.Policy,
security_policy=self.SecurityPolicy,
)

generated_resources = api_generator.to_cloudformation(redeploy_restapi_parameters, route53_record_set_groups)
Expand Down
1 change: 1 addition & 0 deletions samtranslator/plugins/globals/globals.py
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,7 @@ class Globals:
"Domain",
"AlwaysDeploy",
"PropagateTags",
"SecurityPolicy",
],
SamResourceType.HttpApi.value: [
"Auth",
Expand Down
10 changes: 10 additions & 0 deletions samtranslator/schema/schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -355541,6 +355541,11 @@
"title": "Propagatetags",
"type": "boolean"
},
"SecurityPolicy": {
"markdownDescription": "The Transport Layer Security (TLS) version + cipher suite for this RestApi. \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`SecurityPolicy`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-restapi.html#cfn-apigateway-restapi-securitypolicy) property of an `AWS::ApiGateway::RestApi` resource\\.",
"title": "SecurityPolicy",
"type": "string"
},
"TracingEnabled": {
"markdownDescription": "Indicates whether active tracing with X\\-Ray is enabled for the stage\\. For more information about X\\-Ray, see [Tracing user requests to REST APIs using X\\-Ray](https://docs.aws.amazon.com/apigateway/latest/developerguide/apigateway-xray.html) in the *API Gateway Developer Guide*\\. \n*Type*: Boolean \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`TracingEnabled`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-stage.html#cfn-apigateway-stage-tracingenabled) property of an `AWS::ApiGateway::Stage` resource\\.",
"title": "TracingEnabled",
Expand Down Expand Up @@ -355741,6 +355746,11 @@
"title": "Propagatetags",
"type": "boolean"
},
"SecurityPolicy": {
"markdownDescription": "The Transport Layer Security (TLS) version + cipher suite for this RestApi. \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`SecurityPolicy`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-restapi.html#cfn-apigateway-restapi-securitypolicy) property of an `AWS::ApiGateway::RestApi` resource\\.",
"title": "SecurityPolicy",
"type": "string"
},
"StageName": {
"anyOf": [
{
Expand Down
38 changes: 38 additions & 0 deletions schema_source/sam.schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -4267,6 +4267,25 @@
"title": "Propagatetags",
"type": "boolean"
},
"SecurityPolicy": {
"__samPassThrough": {
"markdownDescriptionOverride": "The Transport Layer Security (TLS) version + cipher suite for this RestApi. \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`SecurityPolicy`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-restapi.html#cfn-apigateway-restapi-securitypolicy) property of an `AWS::ApiGateway::RestApi` resource\\.",
"schemaPath": [
"definitions",
"AWS::ApiGateway::RestApi",
"properties",
"Properties",
"properties",
"SecurityPolicy"
]
},
"allOf": [
{
"$ref": "#/definitions/PassThroughProp"
}
],
"title": "SecurityPolicy"
},
"TracingEnabled": {
"__samPassThrough": {
"markdownDescriptionOverride": "Indicates whether active tracing with X\\-Ray is enabled for the stage\\. For more information about X\\-Ray, see [Tracing user requests to REST APIs using X\\-Ray](https://docs.aws.amazon.com/apigateway/latest/developerguide/apigateway-xray.html) in the *API Gateway Developer Guide*\\. \n*Type*: Boolean \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`TracingEnabled`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-stage.html#cfn-apigateway-stage-tracingenabled) property of an `AWS::ApiGateway::Stage` resource\\.",
Expand Down Expand Up @@ -4640,6 +4659,25 @@
"title": "Propagatetags",
"type": "boolean"
},
"SecurityPolicy": {
"__samPassThrough": {
"markdownDescriptionOverride": "The Transport Layer Security (TLS) version + cipher suite for this RestApi. \n*Type*: String \n*Required*: No \n*AWS CloudFormation compatibility*: This property is passed directly to the [`SecurityPolicy`](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-apigateway-restapi.html#cfn-apigateway-restapi-securitypolicy) property of an `AWS::ApiGateway::RestApi` resource\\.",
"schemaPath": [
"definitions",
"AWS::ApiGateway::RestApi",
"properties",
"Properties",
"properties",
"SecurityPolicy"
]
},
"allOf": [
{
"$ref": "#/definitions/PassThroughProp"
}
],
"title": "SecurityPolicy"
},
"StageName": {
"anyOf": [
{
Expand Down
43 changes: 43 additions & 0 deletions tests/model/api/test_api_generator_security_policy.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
from unittest import TestCase
from unittest.mock import Mock

from samtranslator.model.api.api_generator import ApiGenerator


class TestApiGeneratorSecurityPolicy(TestCase):
def setUp(self):
self.logical_id = "MyApi"
self.default_args = {
"logical_id": self.logical_id,
"cache_cluster_enabled": None,
"cache_cluster_size": None,
"variables": None,
"depends_on": None,
"definition_body": {"swagger": "2.0"},
"definition_uri": None,
"name": None,
"stage_name": "Prod",
"shared_api_usage_plan": Mock(),
"template_conditions": Mock(),
"method_settings": None,
"endpoint_configuration": {"Type": "REGIONAL"},
"access_log_setting": None,
"canary_setting": None,
"tracing_enabled": None,
"open_api_version": None,
"always_deploy": None,
}

def test_security_policy_tls_1_3(self):
api_generator = ApiGenerator(**self.default_args, security_policy="SecurityPolicy_TLS13_1_3_2025_09")

rest_api = api_generator._construct_rest_api()

self.assertEqual(rest_api.SecurityPolicy, "SecurityPolicy_TLS13_1_3_2025_09")

def test_no_security_policy(self):
api_generator = ApiGenerator(**self.default_args, security_policy=None)

rest_api = api_generator._construct_rest_api()

self.assertIsNone(rest_api.SecurityPolicy)
17 changes: 17 additions & 0 deletions tests/translator/input/api_with_security_policy.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
Globals:
Api:
SecurityPolicy: SecurityPolicy_TLS13_1_3_2025_09

Resources:
# Inherits Globals (TLS 1.3)
ApiInheritGlobals:
Type: AWS::Serverless::Api
Properties:
StageName: Prod

# Top-level overrides Globals
ApiTopLevelOverride:
Type: AWS::Serverless::Api
Properties:
StageName: Prod
SecurityPolicy: SecurityPolicy_TLS13_1_3_2025_09
80 changes: 80 additions & 0 deletions tests/translator/output/api_with_security_policy.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
{
"Resources": {
"ApiInheritGlobals": {
"Properties": {
"Body": {
"info": {
"title": {
"Ref": "AWS::StackName"
},
"version": "1.0"
},
"paths": {},
"swagger": "2.0"
},
"SecurityPolicy": "SecurityPolicy_TLS13_1_3_2025_09"
},
"Type": "AWS::ApiGateway::RestApi"
},
"ApiInheritGlobalsDeployment5332c373d4": {
"Properties": {
"Description": "RestApi deployment id: 5332c373d45c69e6c0f562b4a419aa8eb311adc7",
"RestApiId": {
"Ref": "ApiInheritGlobals"
},
"StageName": "Stage"
},
"Type": "AWS::ApiGateway::Deployment"
},
"ApiInheritGlobalsProdStage": {
"Properties": {
"DeploymentId": {
"Ref": "ApiInheritGlobalsDeployment5332c373d4"
},
"RestApiId": {
"Ref": "ApiInheritGlobals"
},
"StageName": "Prod"
},
"Type": "AWS::ApiGateway::Stage"
},
"ApiTopLevelOverride": {
"Properties": {
"Body": {
"info": {
"title": {
"Ref": "AWS::StackName"
},
"version": "1.0"
},
"paths": {},
"swagger": "2.0"
},
"SecurityPolicy": "SecurityPolicy_TLS13_1_3_2025_09"
},
"Type": "AWS::ApiGateway::RestApi"
},
"ApiTopLevelOverrideDeployment5332c373d4": {
"Properties": {
"Description": "RestApi deployment id: 5332c373d45c69e6c0f562b4a419aa8eb311adc7",
"RestApiId": {
"Ref": "ApiTopLevelOverride"
},
"StageName": "Stage"
},
"Type": "AWS::ApiGateway::Deployment"
},
"ApiTopLevelOverrideProdStage": {
"Properties": {
"DeploymentId": {
"Ref": "ApiTopLevelOverrideDeployment5332c373d4"
},
"RestApiId": {
"Ref": "ApiTopLevelOverride"
},
"StageName": "Prod"
},
"Type": "AWS::ApiGateway::Stage"
}
}
}
Loading
Loading