简体   繁体   English

Node.js AWS SNS 订阅,确认

[英]Node.js AWS SNS subscription , confirmation

I'm trying to connect an SNS topic to my Meteor ( node ) JS application, but it seems like i'm not getting the right response when i try to subscribe and stuff.我正在尝试将 SNS 主题连接到我的 Meteor(节点)JS 应用程序,但是当我尝试订阅时似乎没有得到正确的响应。

I have few questions regarding this matter.关于这个问题,我有几个问题。 but first , this is my topic and code :但首先,这是我的主题和代码:

  • I created a topic in SNS, and got it's ARN.我在 SNS 中创建了一个主题,并得到了它的 ARN。
  • I Set my AMI Policy to be able to use SNS.我设置了我的 AMI 策略以能够使用 SNS。 Got my access key and secret key得到了我的访问密钥和秘密密钥
  • Wrote this on my LOCALHOST server :在我的 LOCALHOST 服务器上写了这个:

     AWS.config.update({ accessKeyId: 'something', secretAccessKey: 'someotherthing+a4f23', region: 'eu-west-1' }); let sns = new AWS.SNS(); var params = { Protocol: 'http', /* required */ TopicArn: 'arn:aws:sns:eu-west-1:888472248156:ps-tracking', /* required */ Endpoint: 'http://URL:4000' }; sns.subscribe(params, function(err, data) { if (err) console.log(err, err.stack); // an error occurred else console.log(data); // successful response });

I'm still running my node app on LOCALHOST at this point此时我仍在 LOCALHOST 上运行我的节点应用程序

then i switch to my AWS SNS panel and create a subscription, choose HTTP as protocol and type in the ENDPOINT URL.然后我切换到我的 AWS SNS 面板并创建订阅,选择 HTTP 作为协议并输入 ENDPOINT URL。

First Question Is there any possibility that i can get this to work on localhost without moving it to the live server, if so how ?第一个问题有没有可能我可以让它在本地主机上工作而不将它移动到实时服务器,如果是这样怎么办?

so when i run the appliction i get this message in the console :所以当我运行应用程序时,我在控制台中收到此消息:

{ ResponseMetadata: { RequestId: '64a88abb-7997-5f47-bfcc-d8cfc5281ca3' },
 SubscriptionArn: 'pending confirmation' }

i switch to my AWS panel i see我切换到我的 AWS 面板,我看到了在此处输入图片说明

even when i move all this to the live server, with the same data, i'm getting this pending message.即使当我使用相同的数据将所有这些移动到实时服务器时,我也会收到此待处理消息。 and i don't know what i should do !我不知道我应该做什么!

You need to confirm the subscription.您需要确认订阅。

After you subscribe your endpoint, Amazon SNS will send a subscription confirmation message to the endpoint.在您订阅终端节点后,Amazon SNS 将向终端节点发送订阅确认消息。 You should already have code that performs the actions described in Step 1 deployed to your endpoint.您应该已经将执行步骤 1 中描述的操作的代码部署到您的端点。 Specifically, the code at the endpoint must retrieve the SubscribeURL value from the subscription confirmation message and either visit the location specified by SubscribeURL itself or make it available to you so that you can manually visit the SubscribeURL, for example, using a web browser.具体而言,端点处的代码必须从订阅确认消息中检索 SubscribeURL 值,并访问 SubscribeURL 本身指定的位置或使其可供您使用,以便您可以手动访问 SubscribeURL,例如,使用 Web 浏览器。 Amazon SNS will not send messages to the endpoint until the subscription has been confirmed.在确认订阅之前,Amazon SNS 不会向终端节点发送消息。 When you visit the SubscribeURL, the response will contain an XML document containing an element SubscriptionArn that specifies the ARN for the subscription.当您访问 SubscribeURL 时,响应将包含一个 XML 文档,其中包含一个元素 SubscriptionArn,该元素指定订阅的 ARN。 You can also use the Amazon SNS console to verify that the subscription is confirmed: The Subscription ID will display the ARN for the subscription instead of the PendingConfirmation value that you saw when you first added the subscription.您还可以使用 Amazon SNS 控制台来验证订阅是否已确认:订阅 ID 将显示订阅的 ARN,而不是您第一次添加订阅时看到的 PendingConfirmation 值。

Sending Amazon SNS Messages to HTTP/HTTPS Endpoints 将 Amazon SNS 消息发送到 HTTP/HTTPS 终端节点

I made an function for typescript to confirm the subscription.我为 typescript 制作了一个函数来确认订阅。 Just pass in your header and body from the express route.只需从快速路线传递您的标题和正文。

Also the content type of the sns request is something like text/plain and the bodyParser used in most express apps won't process the body so the body.Token will be empty.此外,sns 请求的内容类型类似于text/plain并且大多数快递应用程序中使用的 bodyParser 不会处理正文,因此body.Token将为空。 To solve this use a middleware before you body parser to augment the request coming in.要解决此问题,请在正文解析器之前使用中间件来增加传入的请求。

Process subscription confirmation处理订阅确认

import AWS from "aws-sdk";
const snsInstance = new AWS.SNS();

function isConfirmSubscription(headers: {
    'x-amz-sns-message-type': string
}) {
    return headers['x-amz-sns-message-type'] === 'SubscriptionConfirmation'
}

function confirmSubscription(
    headers: {
        'x-amz-sns-topic-arn': string,
        'x-amz-sns-message-type': string
},
    body: {Token: string}
): Promise<string>{

    return new Promise(((resolve, reject) =>{
        if(!isConfirmSubscription(headers)){
            return resolve('No SubscriptionConfirmation in sns headers')
        }

        snsInstance.confirmSubscription({
            TopicArn: headers['x-amz-sns-topic-arn'],
            Token : body.Token
        }, (err, res)=>{
            console.log(err);
            if(err){
                return reject(err)
            }
            return resolve(res.SubscriptionArn);
        });
    }))

}

SubscriptionConfirmation content type modifier SubscriptionConfirmation 内容类型修饰符

app.use(function(req, res, next) {
    if (req.headers['x-amz-sns-message-type']) {
        req.headers['content-type'] = 'application/json;charset=UTF-8';
    }
    next();
});

If you need to confirm the subscription to an SNS Topic, you can use the AWS-NODE-SDK using the Request sent from SNS:如果您需要确认对 SNS 主题的订阅,您可以使用AWS-NODE-SDK使用 SNS 发送的请求:

{
  "Type" : "SubscriptionConfirmation",
  "MessageId" : "165545c9-2a5c-472c-8df2-7ff2be2b3b1b",
  "Token" : "2336412f37fb687f5d51e6e241d09c805a5a57b30d712f794cc5f6a988666d92768dd60a747ba6f3beb71854e285d6ad02428b09ceece29417f1f02d609c582afbacc99c583a916b9981dd2728f4ae6fdb82efd087cc3b7849e05798d2d2785c03b0879594eeac82c01f235d0e717736",
  "TopicArn" : "arn:aws:sns:us-west-2:123456789012:MyTopic",
  "Message" : "You have chosen to subscribe to the topic arn:aws:sns:us-west-2:123456789012:MyTopic.\nTo confirm the subscription, visit the SubscribeURL included in this message.",
  "SubscribeURL" : "https://sns.us-west-2.amazonaws.com/?Action=ConfirmSubscription&TopicArn=arn:aws:sns:us-west-2:123456789012:MyTopic&Token=2336412f37fb687f5d51e6e241d09c805a5a57b30d712f794cc5f6a988666d92768dd60a747ba6f3beb71854e285d6ad02428b09ceece29417f1f02d609c582afbacc99c583a916b9981dd2728f4ae6fdb82efd087cc3b7849e05798d2d2785c03b0879594eeac82c01f235d0e717736",
  "Timestamp" : "2012-04-26T20:45:04.751Z",
  "SignatureVersion" : "1",
  "Signature" : "EXAMPLEpH+DcEwjAPg8O9mY8dReBSwksfg2S7WKQcikcNKWLQjwu6A4VbeS0QHVCkhRS7fUQvi2egU3N858fiTDN6bkkOxYDVrY0Ad8L10Hs3zH81mtnPk5uvvolIC1CXGu43obcgFxeL3khZl8IKvO61GWB6jI9b5+gLPoBc1Q=",
  "SigningCertURL" : "https://sns.us-west-2.amazonaws.com/SimpleNotificationService-f3ecfb7224c7233fe7bb5f59f96de52f.pem"
}

To make the confirmation you will need the TopicArn from the header & Token found on the body:要进行确认,您将需要来自正文中的标题和令牌的 TopicArn:

AWS.config.update({
  accessKeyId    : 'ACCESS_KEY',
  secretAccessKey: 'ACCESS_SECRET_KEY',
  region : 'region'
});
// Create S3 Object from AWS SDK
const sns = new AWS.SNS();
// Request options
let options = {
  TopicArn: req.headers['x-amz-sns-topic-arn'],
  Token : req.body.Token
}
// Confirm Token Subscription
sns.confirmSubscription(options, callback);

Note: AWS will send the SubscriptionConfirmation & Notifications to the same endpoint, you can differentiate those by using the header 'x-amz-sns-message-type'注意:AWS 会将订阅确认和通知发送到同一终端节点,您可以使用标头“x-amz-sns-message-type”来区分它们

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM