web-dev-qa-db-fra.com

Comment puis-je confirmer la demande d'abonnement HTTP d'Amazon SNS

J'ai cherché partout sur le Web et rien ne donne une réponse claire pour confirmer la demande d'abonnement d'Amazon SNS. J'envoie déjà l'abonnement depuis la console Amazon à mon site Web, mais quelle est la prochaine étape? J'utilise Amazon EC2 comme serveur avec PHP.

22

Avant même de configurer l'abonnement au point de terminaison HTTP/HTTPS via la console de gestion AWS, vous devez vous assurer que le point de terminaison HTTP ou HTTPS de votre site Web PHP a la capacité de gérer le HTTP POST requêtes générées par Amazon SNS. Il existe plusieurs types de messages SNS: SubscriptionConfirmation , Notification et UnsubscribeConfirmation. Your PHP doit obtenir l'en-tête x-amz-sns-message-type à partir de la demande et le traiter en fonction du type de message. Pour le message SubscriptionConfirmation, votre application PHP doit traiter le corps de message POST, qui est un document JSON. Pour souscrire le sujet, votre PHP doit visiter le "SubscriberURL" spécifié dans le corps JSON. Facultativement, vous devez vérifier la signature pour vous assurer de l'authenticité du message avant de vous abonner au sujet.

Vous pouvez trouver plus de détails sur la documentation AWS: http://docs.aws.Amazon.com/sns/latest/dg/SendMessageToHttp.html

18
Lan

Voici une application express (Node.js) qui confirme l'abonnement SNS:

const express = require('express')
const request = require('request')
// parse urlencoded request bodies into req.body
const bodyParser = require('body-parser')
const app = express()
const port = 8080

app.use(bodyParser.urlencoded({ extended: false }))
app.use(bodyParser.json())

app.post('/', (req, res) => {
  let body = ''

  req.on('data', (chunk) => {
    body += chunk.toString()
  })

  req.on('end', () => {
    let payload = JSON.parse(body)

    if (payload.Type === 'SubscriptionConfirmation') {
      const promise = new Promise((resolve, reject) => {
        const url = payload.SubscribeURL

        request(url, (error, response) => {
          if (!error && response.statusCode == 200) {
            console.log('Yess! We have accepted the confirmation from AWS')
            return resolve()
          } else {
            return reject()
          }
        })
      })

      promise.then(() => {
        res.end("ok")
      })
    }
  })
})

app.listen(port, () => console.log('Example app listening on port ' + port + '!'))

Pour l'utiliser, il faut installer les packages requis:

yarn add express request body-parser

Une fois que vous avez confirmé l'abonnement, AWS enverra une demande POST au serveur avec le contenu suivant:

{
  "Type": "SubscriptionConfirmation",
  "MessageId": "XXXXXXXX-1ee3-4de3-9c69-XXXXXXXXXXXX",
  "Token": "SECRET_TOKEN",
  "TopicArn": "arn:aws:sns:us-west-2:XXXXXXXXXXXX:ses-test",
  "Message": "You have chosen to subscribe to the topic arn:aws:sns:us-west-2:XXXXXXXXXXXX:ses-test. To 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:XXXXXXXXXXXX:ses-test&Token=SECRET_TOKEN",
  "Timestamp": "2018-11-21T19:48:08.170Z",
  "SignatureVersion": "1",
  "Signature": "SECRET",
  "SigningCertURL": "https://sns.us-west-2.amazonaws.com/SimpleNotificationService-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX.pem"
}

La charge utile contient SubscribeURL qui est demandée par le serveur.

8
czerasz

Abonnement SNS Spring Cloud avec annotation

spring Cloud AWS prend en charge la confirmation automatique de l'abonné, il vous suffit de mettre cette annotation "@NotificationSubscriptionMapping"

@Controller
@RequestMapping("/topicName")
public class NotificationTestController {

    @NotificationSubscriptionMapping
    public void handleSubscriptionMessage(NotificationStatus status) throws IOException {
        //We subscribe to start receive the message
        status.confirmSubscription();
    }

    @NotificationMessageMapping
    public void handleNotificationMessage(@NotificationSubject String subject, @NotificationMessage String message) {
        // ...
    }

    @NotificationUnsubscribeConfirmationMapping
    public void handleUnsubscribeMessage(NotificationStatus status) {
        //e.g. the client has been unsubscribed and we want to "re-subscribe"
        status.confirmSubscription();
    }
}

http://cloud.spring.io/spring-cloud-aws/spring-cloud-aws.html#_sns_support

2
Rams

Le point de terminaison que vous avez spécifié obtiendra les données du service de vérification des points de terminaison AWS SNS. Le même point de terminaison sera utilisé pour vérifier le point de terminaison et recevoir des notifications de aws,

Vider simplement l'entrée envoyée par AWS SNS dans un fichier texte comme,

$json_write_to_text = json_decode(file_get_contents("php://input"));

Vous trouverez toutes les données envoyées par AWS SNS, mais il vous suffit de trouver SubscriptionUrl (qui sera spécifique au point de terminaison ayant un jeton valide). Ouvrez-le dans le navigateur, vous aurez le statut SubscriptionConfirmation. C'est tout

Prendre plaisir.

2
Chintan7027

J'ai résolu cela en utilisant le backend NodeJS. Disons que vous avez une API comme celle-ci dans HapiJS (Eh bien, peu importe que vous puissiez avoir une autre technologie)

{
    method: 'POST',
    path: '/hello',
    handler: ( request, reply ) => {

        reply( Hello.print(request.payload) );
    },
    config: {
        tags: ['api']
    }
}

Passez simplement la charge utile que vous recevez à votre logique métier.

Dans le processus de logique métier, il ressemble à ceci

    'use strict';
    const request = require('request');

    exports.print = (payload) => {

    payload = JSON.parse(payload);
    if(payload.Type === 'SubscriptionConfirmation'){

        return new Promise((resolve, reject) => {
            const url = payload.SubscribeURL;
            request(url, (error, response) => {

                if (!error && response.statusCode == 200) {
                    console.log('Yess! We have accepted the confirmation from AWS');
                    return resolve();
                }
                else 
                    return reject();
            });
        });
    }

J'utilise le module de demande de NPM pour accepter automatiquement ces demandes.

Une autre façon serait d'imprimer le contenu de payload puis de cliquer sur l'URL indiquée dans payload.SubscribeURL.

Une fois qu'AWS l'accepte, vous vérifiez la confirmation sur la page Abonnements où Subscription ARN serait changé de Pending Confirmation à un nom complexe-SHA ayant le nom de votre sujet.

1
rahuljain1311