8

使用以下代码,我可以使用我的 AWS 帐号添加权限,但队列不会收到来自 SNS 的任何消息。

AddPermissionRequest addPermissionRequest = new AddPermissionRequest();
addPermissionRequest.ActionName.Add("SendMessage");
addPermissionRequest.ActionName.Add("ReceiveMessage");
addPermissionRequest.QueueUrl = queueUrl;
addPermissionRequest.Label = General.IpAddressAWSFriendly;
addPermissionRequest.AWSAccountId.Add(AWS_ACCOUNT_ID);
sqs.AddPermission(addPermissionRequest);

但是,当我尝试通过通配符 (*) 为每个人设置权限时:

addPermissionRequest.AWSAccountId.Add("*");

它给了我一个错误。如果我在 AWS SQS 控制台中手动添加权限并指定

SendMessage
ReceiveMessage

对于允许的操作和原则,我将其设置为“每个人”,队列确实从我的 SNS 主题接收消息。所以,很明显,我做错了什么,但我再也看不到了。

任何帮助都会很棒!我希望亚马逊有示例,SDK 附带的示例没有显示任何有关设置策略或权限的内容。在线文档中也没有显示任何内容。令人沮丧。

4

4 回答 4

11

幸运的是,我自己想通了,因为我在这里没有收到任何回复。我真的希望 Amazon 能够为 .Net 框架上的 C# 开发人员提供更好的文档,而不仅仅是脚本小子。

无论如何,我最终创建了一个完整的 Policy 对象并将其传递给 SQS。我使用的是 AWS SDK v1.5 版本,而不是较新的 2.0(目前处于测试阶段),只是因为它现在可以工作,而且我懒得将其更改为较新的 2.0 版本。

以下是您需要以编程方式在 C# 中为 SQS 队列创建策略的代码,条件是仅将该队列与 SNS 主题一起使用:

        // 4. Set the queue policy to allow SNS to publish messages
        ActionIdentifier[] actions = new ActionIdentifier[2];
        actions[0] = SQSActionIdentifiers.SendMessage;
        actions[1] = SQSActionIdentifiers.ReceiveMessage;
        Policy sqsPolicy = new Policy()
            .WithStatements(new Statement(Statement.StatementEffect.Allow)
                                .WithPrincipals(Principal.AllUsers)
                                .WithResources(new Resource(queueArn))
                                .WithConditions(ConditionFactory.NewSourceArnCondition(_AWSSNSArn))
                                .WithActionIdentifiers(actions));
        SetQueueAttributesRequest setQueueAttributesRequest = new SetQueueAttributesRequest();
        List<Amazon.SQS.Model.Attribute> attributes = new List<Amazon.SQS.Model.Attribute>();
        Amazon.SQS.Model.Attribute attribute = new Amazon.SQS.Model.Attribute();
        attribute.Name = "Policy";
        attribute.Value = sqsPolicy.ToJson();
        attributes.Add(attribute);
        setQueueAttributesRequest.QueueUrl = queueUrl;
        setQueueAttributesRequest.Attribute = attributes;
        sqs.SetQueueAttributes(setQueueAttributesRequest);

我希望这可以帮助别人。

于 2013-10-17T01:36:44.447 回答
3

以前创建的权限没有按预期工作的资源。这是获得arn的更正:

    public static String TestQueueCreate(String name) {

        AmazonSQSClient sqs = new AmazonSQSClient(region: Amazon.RegionEndpoint.USEast1);
        CreateQueueResponse create = sqs.CreateQueue(name);

        String arn = sqs.GetQueueAttributes(create.QueueUrl, new List<String>() { "QueueArn" }).Attributes["QueueArn"];

        Policy policy = new Policy() {
            Statements = new List<Statement>() {
                new Statement(StatementEffect.Allow) {
                    Principals = new List<Principal>() { new Principal("*") },
                    Actions = new List<ActionIdentifier>() {
                        new ActionIdentifier("SQS:ReceiveMessage"),
                        new ActionIdentifier("SQS:SendMessage")
                    },
                    Resources = new List<Resource>() { new Resource(arn) }
                }
            },

        };

        Dictionary<String,String> queueAttributes = new Dictionary<String, String>();
        queueAttributes.Add(QueueAttributeName.Policy.ToString(), policy.ToJson());
        sqs.SetQueueAttributes(new SetQueueAttributesRequest(create.QueueUrl, queueAttributes));

        return create.QueueUrl;
    }
于 2016-10-14T18:56:57.947 回答
1

以下是在 Clojure 中使用amazonica的方法:

(require '[amazonica.aws.sqs :as sqs]
         '[amazonica.core :as aws)
(import '(com.amazonaws.auth.policy Statement Statement$Effect
                                    Principal
                                    Policy
                                    Resource
                                    Condition
                                    Action)
        '(com.amazonaws.auth.policy.actions SQSActions)
        '(com.amazonaws.auth.policy.conditions ConditionFactory))

(aws/defcredential "access-key" "secret-key" "us-east-1")

(def topic-arn "arn:aws:sns:us-east-1:123:foo")
(def queue-url "https://sqs.us-east-1.amazonaws.com/123/bar")
(def queue-arn (-> queue-url sqs/get-queue-attributes :QueueArn))

(def policy (Policy.
                   (str queue-arn "/SQSDefaultPolicy")
                   [(doto (Statement. Statement$Effect/Allow)
                       (.setPrincipals [Principal/AllUsers])
                       (.setResources [(Resource. queue-arn)])
                       (.setConditions [(ConditionFactory/newSourceArnCondition topic-arn)])
                       (.setActions [SQSActions/SendMessage]))]))

(sqs/set-queue-attributes queue-url {"Policy" (.toJson policy)})
于 2014-03-06T10:26:12.737 回答
1

以下是我如何使用匿名读取访问动态创建队列。只需根据需要添加额外的 ActionIdentifiers:

    public static String TestQueueCreate(String name) {

        AmazonSQSClient sqs = new AmazonSQSClient(region: Amazon.RegionEndpoint.USEast1);
        CreateQueueResponse create = sqs.CreateQueue(name);

        Policy policy = new Policy() {
            Statements = new List<Statement>() {
                new Statement(StatementEffect.Allow) {
                    Principals = new List<Principal>() { Principal.AllUsers },
                    Actions = new List<ActionIdentifier>() { SQSActionIdentifiers.ReceiveMessage }
                }
            }
        };

        Dictionary<String,String> queueAttributes = new Dictionary<String, String>();
        queueAttributes.Add(QueueAttributeName.Policy.ToString(), policy.ToJson());
        sqs.SetQueueAttributes(new SetQueueAttributesRequest(create.QueueUrl, queueAttributes));

        return create.QueueUrl;
    }
于 2016-10-14T17:33:31.900 回答