Repository: smithy-lang/smithy
Pull request #2091 (2024-01-05 17:32:58)

Support iamAction for CFN handler permissions
By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.



Patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index d3ac4a6d8..a3985fff9 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -18,6 +18,7 @@
 
 ### Bug Fixes
 
+* Fixed an issue where `@iamAction` wasn't reflected in CFN resource schema creation. ([#2091](https://github.com/smithy-lang/smithy/pull/2091)) 
 * Fixed tree node start and end locations. ([#2084](https://github.com/smithy-lang/smithy/pull/2084))
 * Fixed several minor build warnings. ([2089](https://github.com/smithy-lang/smithy/pull/2089))
 * Fixed protocol test service signing name for `awsJson1_1` protocol. ([#2089](https://github.com/smithy-lang/smithy/pull/2089))
diff --git a/smithy-aws-cloudformation/src/main/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapper.java b/smithy-aws-cloudformation/src/main/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapper.java
index 971067258..4a671f949 100644
--- a/smithy-aws-cloudformation/src/main/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapper.java
+++ b/smithy-aws-cloudformation/src/main/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapper.java
@@ -22,6 +22,7 @@ import software.amazon.smithy.aws.cloudformation.schema.fromsmithy.CfnMapper;
 import software.amazon.smithy.aws.cloudformation.schema.fromsmithy.Context;
 import software.amazon.smithy.aws.cloudformation.schema.model.Handler;
 import software.amazon.smithy.aws.cloudformation.schema.model.ResourceSchema;
+import software.amazon.smithy.aws.iam.traits.IamActionTrait;
 import software.amazon.smithy.aws.iam.traits.RequiredActionsTrait;
 import software.amazon.smithy.aws.traits.ServiceTrait;
 import software.amazon.smithy.model.Model;
@@ -30,6 +31,7 @@ import software.amazon.smithy.model.shapes.ResourceShape;
 import software.amazon.smithy.model.shapes.ServiceShape;
 import software.amazon.smithy.model.shapes.ShapeId;
 import software.amazon.smithy.model.traits.NoReplaceTrait;
+import software.amazon.smithy.utils.ListUtils;
 import software.amazon.smithy.utils.SetUtils;
 import software.amazon.smithy.utils.SmithyInternalApi;
 
@@ -112,9 +114,11 @@ public final class HandlerPermissionMapper implements CfnMapper {
         permissionsEntries.add(operationActionName);
 
         // Add all the other required actions for the operation.
-        operation.getTrait(RequiredActionsTrait.class)
-                .map(RequiredActionsTrait::getValues)
-                .map(permissionsEntries::addAll);
+        permissionsEntries.addAll(operation.getTrait(IamActionTrait.class)
+                .map(IamActionTrait::getRequiredActions)
+                .orElseGet(() -> operation.getTrait(RequiredActionsTrait.class)
+                        .map(RequiredActionsTrait::getValues)
+                        .orElse(ListUtils.of())));
         return permissionsEntries;
     }
 }


Test patch:
diff --git a/smithy-aws-cloudformation/src/test/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapperTest.java b/smithy-aws-cloudformation/src/test/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapperTest.java
index 410b00ec2..1bbe03ca9 100644
--- a/smithy-aws-cloudformation/src/test/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapperTest.java
+++ b/smithy-aws-cloudformation/src/test/java/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/HandlerPermissionMapperTest.java
@@ -58,7 +58,7 @@ public final class HandlerPermissionMapperTest {
                 containsInAnyOrder("testservice:CreateFooOperation", "otherservice:DescribeDependencyComponent"));
         assertThat(handlersDefined.get("read").expectObjectNode()
                            .expectArrayMember("permissions").getElementsAs(StringNode::getValue),
-                contains("testservice:GetFooOperation"));
+                containsInAnyOrder("testservice:GetFooOperation", "otherservice:DescribeThing"));
         assertThat(handlersDefined.get("update").expectObjectNode()
                            .expectArrayMember("permissions").getElementsAs(StringNode::getValue),
                 contains("testservice:UpdateFooOperation"));
diff --git a/smithy-aws-cloudformation/src/test/resources/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/simple.smithy b/smithy-aws-cloudformation/src/test/resources/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/simple.smithy
index 115fd0c2e..edcf04fec 100644
--- a/smithy-aws-cloudformation/src/test/resources/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/simple.smithy
+++ b/smithy-aws-cloudformation/src/test/resources/software/amazon/smithy/aws/cloudformation/schema/fromsmithy/mappers/simple.smithy
@@ -3,6 +3,7 @@ $version: "2.0"
 namespace smithy.example
 
 use aws.cloudformation#cfnResource
+use aws.iam#iamAction
 
 service TestService {
     version: "2020-07-02",
@@ -56,6 +57,7 @@ structure CreateFooResponse {
 }
 
 @readonly
+@iamAction(requiredActions: ["otherservice:DescribeThing"])
 operation GetFooOperation {
     input: GetFooRequest,
     output: GetFooResponse,