Вопрос

Пытаясь начать с Amazon Sns. API очень простой отдых. Кажется, я повесился на подписи часть звонка. Пример API:

http://sns.us-east-1.amazonaws.com/
?Subject=My%20first%20message
&TopicArn=arn%3Aaws%3Asns%3Aus-east-1%3A698519295917%3AMy-Topic
&Message=Hello%20world%21
&Action=Publish
&SignatureVersion=2
&SignatureMethod=HmacSHA256
&Timestamp=2010-03-31T12%3A00%3A00.000Z
&AWSAccessKeyId=AKIAJHS4T6XPF7XIURNA
&Signature=9GZysQ4Jpnz%2BHklqM7VFTvEcjR2LIUtn6jW47054xxE%3D

Я следил за Документы API для подписей, Так что я пытаюсь:

from time import strftime,gmtime,time
import urllib2
import hmac
import hashlib
import base64
import string

def publichSNSMsg(Subject,TopicArn,Message,AWSAccessKeyId,privatekey):
  #http://docs.amazonwebservices.com/AWSSimpleQueueService/2008-01-01/SQSDeveloperGuide/
  amzsnshost = 'sns.us-east-1.amazonaws.com'
  values = {'Subject' : Subject,
            'TopicArn' : TopicArn,
            'Message' :Message,
            'Timestamp' : strftime("%Y-%m-%dT%H:%M:%S.000Z", gmtime(time())),
            'AWSAccessKeyId' : AWSAccessKeyId,
            'Action' : 'Publish',
            'SignatureVersion' : '2',
            'SignatureMethod' : 'HmacSHA256',
            }

  amazquote=lambda v: urllib2.quote(v).replace('%7E','~')
  cannqs=string.join(["%s=%s"%(amazquote(key),amazquote(values[key])) for key in sorted(values.keys(),key=str.lower)],'&')
  string_to_sign=string.join(["GET",amzsnshost,"/",cannqs],'\n')

  sig=base64.encodestring(hmac.new(privatekey,string_to_sign,hashlib.sha1).digest())
  querystring = "%s&Signature=%s"%(cannqs,amazquote(sig))
  url="http://%s/?%s"%(amzsnshost,querystring)

  try:
    return urllib2.urlopen(url).read()
  except urllib2.HTTPError, exception:
    return "Error %s (%s):\n%s"%(exception.code,exception.msg,exception.read())

И вернуться:

<ErrorResponse xmlns="http://sns.amazonaws.com/doc/2010-03-31/"> 
  <Error> 
    <Type>Sender</Type> 
    <Code>SignatureDoesNotMatch</Code> 
    <Message>The request signature we calculated does not match the signature you provided. Check your AWS Secret Access Key and signing method. Consult the service documentation for details.</Message> 
  </Error> 
  <RequestId>8d6e5a41-dafb-11df-ac33-f981dc4e6c50</RequestId> 
</ErrorResponse> 

Есть идеи?

Это было полезно?

Решение

Ой, это было просто!

Ключи в строке запроса должны были быть Байт-заказ Сортирован, а не без особых случаев отсортирован (это было для версии 1 подписи).

Слегка обновленная (и теперь исправьте) код доступен на суть.

Другие советы

Я нашел этот пример так полезно, что я переписал его в C #. Поскольку AWS не имеет библиотеки WP7 для SNS, возможно, это поможет кому-то: https://gist.github.com/2705156.

Я бы предложил вам использовать BOTO3 для SNS. Документация можно найти в http://boto3.readtheDoc.io/en/latest/reference/services/sns.html.. Отказ Следующий фрагмент кода может быть использован для получения подписи как JSON.

import boto3
from django.views.decorators.csrf import csrf_exempt
topic_arn = <your topic>
client = boto3.client('sns',region_name="us-west-2")

#Call this to publish
def sns_publish(arg1,arg2):
    response = client.publish(
                        TopicArn=topic_arn,
                        Message=arg2,
                        Subject=arg2
                    )

#Function to subscribe to topic
@csrf_exempt
def sns_parse(request):
    print request.body.decode('utf-8')
    if request.method == "POST":
        response = json.loads(request.body.decode('utf-8'))
        type = response.get('Type')
        if type == 'Subscription':
            print(type)
            return("Subscription URL: "+<Url obtained>)
        elif type == 'Notification':
            return HttpResponse(type.get('Signature'))
    else:
        return HttpResponse('Not a POST object')

Это просто код шаблона, но да, BOTO3 действительно полезен.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top