-
-
Notifications
You must be signed in to change notification settings - Fork 4.2k
fix delete method of AWS::SNS::TopicPolicy CFn resource #12831
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -14,6 +14,7 @@ | |
ResourceProvider, | ||
ResourceRequest, | ||
) | ||
from localstack.services.sns.models import create_default_sns_topic_policy | ||
|
||
|
||
class SNSTopicPolicyProperties(TypedDict): | ||
|
@@ -96,14 +97,17 @@ def delete( | |
for topic_arn in model["Topics"]: | ||
try: | ||
sns.set_topic_attributes( | ||
TopicArn=topic_arn, AttributeName="Policy", AttributeValue="" | ||
TopicArn=topic_arn, | ||
AttributeName="Policy", | ||
AttributeValue=json.dumps(create_default_sns_topic_policy(topic_arn)), | ||
) | ||
|
||
except ClientError as err: | ||
if "NotFound" not in err.response["Error"]["Code"]: | ||
raise | ||
|
||
return ProgressEvent( | ||
status=OperationStatus.IN_PROGRESS, | ||
status=OperationStatus.SUCCESS, | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. question: I suppose this is the main fix, right? the Delete operation would never finish as it never returned There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. this + the default policy, because sending an empty attribute value to moto raises and error here: https://github.com/getmoto/moto/blob/338cb256a4ab938f24b5b29ec079ed26a9d0c093/moto/sns/models.py#L137-L139 |
||
resource_model=model, | ||
custom_context=request.custom_context, | ||
) | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -5,6 +5,7 @@ | |
|
||
from localstack.testing.aws.util import is_aws_cloud | ||
from localstack.testing.pytest import markers | ||
from localstack.utils.aws.arns import parse_arn | ||
from localstack.utils.common import short_uid | ||
|
||
|
||
|
@@ -152,6 +153,61 @@ def test_sns_topic_with_attributes(infrastructure_setup, aws_client, snapshot): | |
snapshot.match("topic-archive-policy", response["Attributes"]["ArchivePolicy"]) | ||
|
||
|
||
@markers.aws.validated | ||
@markers.snapshot.skip_snapshot_verify( | ||
paths=[ | ||
"$..Statement..Action", # TODO: see https://github.com/getmoto/moto/pull/9041 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. thanks a lot for fixing this 😄 this is gonna remove a few snapshot skips! |
||
] | ||
) | ||
def test_sns_topic_policy_resets_to_default( | ||
sns_topic, infrastructure_setup, aws_client, snapshot, account_id | ||
): | ||
"""Tests the delete statement of a ``AWS::SNS::TopicPolicy`` resource, which should reset the topic's policy to the | ||
default policy.""" | ||
# simulate a pre-existing topic | ||
existing_topic_arn = sns_topic["Attributes"]["TopicArn"] | ||
existing_topic_name = parse_arn(existing_topic_arn)["resource"] | ||
snapshot.add_transformer(snapshot.transform.regex(existing_topic_name, "<topic-name>")) | ||
|
||
# create the stack | ||
stack_name = "SnsTopicPolicyStack" | ||
infra = infrastructure_setup(namespace="SnsTests") | ||
# persisting the stack means persisting the existing_topic_arn reference, but that changes every test run | ||
infra.persist_output = False | ||
stack = cdk.Stack(infra.cdk_app, stack_name=stack_name) | ||
|
||
# get the existing topic | ||
topic = cdk.aws_sns.Topic.from_topic_arn(stack, "Topic", existing_topic_arn) | ||
|
||
# add the topic policy resource | ||
topic_policy = cdk.aws_sns.TopicPolicy(stack, "CustomTopicPolicy", topics=[topic]) | ||
topic_policy.document.add_statements( | ||
cdk.aws_iam.PolicyStatement( | ||
effect=cdk.aws_iam.Effect.ALLOW, | ||
principals=[cdk.aws_iam.AnyPrincipal()], | ||
actions=["sns:Publish"], | ||
resources=[topic.topic_arn], | ||
conditions={"StringEquals": {"aws:SourceAccount": account_id}}, | ||
) | ||
) | ||
|
||
# snapshot its policy | ||
default = aws_client.sns.get_topic_attributes(TopicArn=existing_topic_arn) | ||
snapshot.match("default-topic-attributes", default["Attributes"]["Policy"]) | ||
|
||
# deploy the stack | ||
cdk.CfnOutput(stack, "TopicArn", value=topic.topic_arn) | ||
with infra.provisioner() as prov: | ||
assert prov.get_stack_outputs(stack_name=stack_name)["TopicArn"] == existing_topic_arn | ||
|
||
modified = aws_client.sns.get_topic_attributes(TopicArn=existing_topic_arn) | ||
snapshot.match("modified-topic-attributes", modified["Attributes"]["Policy"]) | ||
|
||
# now that it's destroyed, get the topic attributes again | ||
reverted = aws_client.sns.get_topic_attributes(TopicArn=existing_topic_arn) | ||
snapshot.match("reverted-topic-attributes", reverted["Attributes"]["Policy"]) | ||
|
||
|
||
@markers.aws.validated | ||
def test_sns_subscription_region( | ||
snapshot, | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nice addition! I'm always torn with this kind of utils in
models.py
, but it makes sense. It's going to nicely be used when we start creating topics in LocalStack directly 👀Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
happy to put it elsewhere. what would be a good place? should we create a utils module, or should it just go into the provider? i could also move it to the resource provider directly
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it is good for now! If we internalize, we’ll create a util folder and move things around! Sorry for the delay 😄