CFn에 SNS 액세스 정책을 자동으로 추가하는 [Lambad-backed 사용자 정의 에셋]
13287 단어 CFnSNSAWSlambdaCloudFormation
예를 들어, EventBridge에서 기존 AWS SNS 주제를 그룹화하는 규칙을 작성할 때
1. AWS 콘솔에서 EventBridge를 수동으로 작성할 경우
→ 이전 SNS의 액세스 정책에 이벤트 브릿지의 라이센스 규칙도 자동으로 추가됩니다.
2. CLI와 CFn을 통해 EventBridge를 생성할 경우
→ SNS에 액세스 라이센스가 자동으로 추가되지 않습니다.이러다가는 이벤트브릿지에서 온 저글링이 SNS 쪽에서 거절당할 수도 있다.
따라서 이벤트브릿지의 인허가 정책도 CFn을 통해 자동으로 추가될 수 없다.
(파치를 수동으로 추가할 수도 있지만, 현장에서 AWS 계정을 많이 관리하기 때문에 간단하게 추가할 수 있기를 바랍니다. 어쨌든 편하게 하세요.)
솔루션 1 및 관심 분야
클라메소의 보도 팁은 CFn에 Lambda-Backed 사용자 정의 리소스를 기술하고 액세스 정책을 자동으로 업데이트합니다.
AWS SDK(python)
set_topic_attributes
를 통해 업데이트할 수 있습니다.주목점
하지만 이것
set_topic_attributes
은 SNS 액세스 정책의'추가'가 아닌'덮어쓰기'다.따라서 기존 SNS 주제에 다른 액세스 정책이 미리 추가된 상태에서 이 사용자 정의 에셋이 적용된 경우 미리 설정된 정책이 삭제됩니다.
이런 분쟁의 원인이 되는 맞춤형 자원을 만들고 싶지 않아 개선책을 모색했다.
해결 방법2
답은 간단하다.SDK
get_topic_attribets
에서만 SNS의 화제 정책을 획득하고 이벤트브릿지의 접근 허가set_topic_attributes
를 추기합니다.사용자 정의 리소스에 사용되는 Lambda 함수는 다음과 같습니다.
TopicArn
, AwsAccountId
는 사용자 정의 자원에서 전송되는 매개 변수이다.lambda-addSnsAccessPolicy.py
import json
import boto3
import logging
import cfnresponse
logger = logging.getLogger()
logger.setLevel(logging.INFO)
sns = boto3.client('sns')
def lambda_handler(event, context):
logger.info("event == {}".format(event))
response = None
topicArn = event['ResourceProperties']['TopicArn']
awsAccountId = event['ResourceProperties']['AwsAccountId']
addPolicy = {
"Sid": "AWSEvent_Allow",
"Effect": "Allow",
"Principal": {
"Service": "events.amazonaws.com"
},
"Action": "sns:Publish",
"Resource": topicArn,
"Condition": {
"StringEquals": {
"AWS:SourceAccount": awsAccountId
}
}
}
if event['RequestType'] == 'Create':
# 既存のトピックポリシーを取得
attributes = sns.get_topic_attributes(TopicArn = topicArn)
policy = eval(attributes["Attributes"]["Policy"])
logger.info("policy = {}".format(policy))
# EventBridgeからのパブリッシュ許可を追記
policy["Statement"].append(addPolicy)
logger.info("updatepolicy = {}".format(policy))
# トピックポリシーを上書き
responce=sns.set_topic_attributes(
TopicArn=topicArn,
AttributeName='Policy',
AttributeValue=json.dumps(policy)
)
if event['RequestType'] == 'Update':
cfnresponse.send(event, context, cfnresponse.SUCCESS, {})
if event['RequestType'] == 'Update':
cfnresponse.send(event, context, cfnresponse.SUCCESS, {})
logger.info("response == {}".format(responce))
cfnresponse.send(event, context, cfnresponse.SUCCESS, responce)
이 Lambda 함수, 사용자 정의 자원 등 CloudFormation 템플릿은 GiitHub 웨어하우스에 있습니다.자세히 보고 싶은 사람은 보세요.
실제로 해 보다
먼저 기존 SNS의 액세스 정책을 확인합니다.기본 정책 및 S3 라이센스가 설정되어 있습니다.
$ aws sns get-topic-attributes --topic-arn arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic
(ポリシーの部分だけ抜粋)
"Policy":
"{\"Version\":\"2008-10-17\",
\"Id\":\"__default_policy_ID\",
\"Statement\":[
↓デフォルトのポリシー
{\"Sid\":\"__default_statement_ID\",\"Effect\":\"Allow\",\"Principal\":{\"AWS\":\"*\"},\"Action\":[\"SNS:GetTopicAttributes\",\"SNS:SetTopicAttributes\",\"SNS:AddPermission\",\"SNS:RemovePermission\",\"SNS:DeleteTopic\",\"SNS:Subscribe\",\"SNS:ListSubscriptionsByTopic\",\"SNS:Publish\"],\"Resource\":\"arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic\",\"Condition\":{\"StringEquals\":{\"AWS:SourceOwner\":\"{AWSアカウントID}\"}}},
↓S3からのパブリッシュ許可ポリシー
{\"Sid\":\"S3_Allow\",\"Effect\":\"Allow\",\"Principal\":{\"Service\":\"s3.amazonaws.com\"},\"Action\":\"sns:Publish\",\"Resource\":\"arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic\",\"Condition\":{\"StringEquals\":{\"AWS:SourceAccount\":\"{AWSアカウントID}\"}}}
]}"
사용자 지정 리소스가 포함된 CFn을 추출합니다.액세스 정책을 다시 확인합니다.EventBridge의 추가 라이센스 정책이 확인되었습니다!!원래 설정한 정책도 사라지지 않고 그대로 남아있다.
$ aws sns get-topic-attributes --topic-arn arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic
(ポリシーの部分だけ抜粋)
"Policy":
"{\"Version\":\"2008-10-17\",
\"Id\":\"__default_policy_ID\",
\"Statement\":[
↓ もともとあったポリシー
{\"Sid\":\"__default_statement_ID\",\"Effect\":\"Allow\",\"Principal\":{\"AWS\":\"*\"},\"Action\":[\"SNS:GetTopicAttributes\",\"SNS:SetTopicAttributes\",\"SNS:AddPermission\",\"SNS:RemovePermission\",\"SNS:DeleteTopic\",\"SNS:Subscribe\",\"SNS:ListSubscriptionsByTopic\",\"SNS:Publish\"],\"Resource\":\"arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic\",\"Condition\":{\"StringEquals\":{\"AWS:SourceOwner\":\"{AWSアカウントID}\"}}},
{\"Sid\":\"S3_Allow\",\"Effect\":\"Allow\",\"Principal\":{\"Service\":\"s3.amazonaws.com\"},\"Action\":\"sns:Publish\",\"Resource\":\"arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic\",\"Condition\":{\"StringEquals\":{\"AWS:SourceAccount\":\"{AWSアカウントID}\"}}},
↓ 今回追加されたEventBridgeからの許可ポリシー
{\"Sid\":\"AWSEvent_Allow\",\"Effect\":\"Allow\",\"Principal\":{\"Service\":\"events.amazonaws.com\"},\"Action\":\"sns:Publish\",\"Resource\":\"arn:aws:sns:ap-northeast-1:{AWSアカウントID}:TestTopic\",\"Condition\":{\"StringEquals\":{\"AWS:SourceAccount\":\"{AWSアカウントID}\"}}}
]}"
최후조사해도 의외로 이 자동 추가 방법이 없다는 기사를 스스로 시도해 봤다.번거로운 SNS 액세스 정책을 손쉽게 관리할 수 있어서 다행입니다.
(해결 방법은 간단하지만, AWS 지지자 w에게 별 볼일 없이 좌우로 흔들며 묻기도 한다)
사용자 정의 자원을 별로 사용하지 않았지만 자유도가 높아 편리하다.공부를 잘하다.
참고 자료
・[클래식 뉴스] 이벤트브릿지가 SNS에 알리지 못해 푹 빠진 이야기
・[문서] Amazon EventBridge 리소스 기반 정책 사용 - Amazon SNS 액세스 허용
・[GiitHub 창고] CFn Lambda-backed 사용자 정의 자원을 사용하여 SNS 화제 전략 자동 증가
Reference
이 문제에 관하여(CFn에 SNS 액세스 정책을 자동으로 추가하는 [Lambad-backed 사용자 정의 에셋]), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/MAKOTO1995/items/275d32635bf238147d24텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)