boto3を使ってAmazon SNSへpublishしてみた

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

サーモン大好き横山です。

今回はboto3を使って、Amazon SNSへpublishしてみました。

準備(AWS側)

まず、AWS側でSNSを設定していきます。 ManageConsoleの左上の「サービス」→「すべてのAWSサービス」→「SNS」を選びSNSのダッシュボードを開きます。

boto3_sns_01

次に「Create Topic」をクリックします。

boto3_sns_02

「Create new topic」画面が開きましたら、「Topic name」「Display name」を入力し、「Create topic」をクリックします。

boto3_sns_03

「Topic Details」画面が開きましたら、次に通知先の登録を行っていきます。 「Create Subscription」をクリックします

boto3_sns_04

「Create Subscription」画面が開きましたら「Protocol」「Endpoint」を設定していきます。 今回はSNSにpublishされた内容をメールに送信してたいので、「Protocol」は「Email」を、「Endpoint」には送信してもらいたいメールアドレスを記入し、「Create Subscription」ボタンをクリックします。

boto3_sns_05

下記画像の様な確認メールが「Endpoint」で設定したメールアドレスに届きますので、「Confirm subscription」をクリックし、Webページを開きます。

boto3_sns_06

Webページが開きましたら、確認完了ということでそのままWebページを閉じます。

boto3_sns_07

再び、マネーにコンソールからSNSの「Topic Details」画面が開きましたら、作成したサブスクリプションの「Subscription ID」が「PendingConfirmation」になっていないことを確認します。
(なっていた場合は確認メールでの確認がうまくいっていません)

boto3_sns_08

「Subscription ID」が「PendingConfirmation」になっていないこと確認できましたら、試しに左上の「Create Publish」をクリックします。

boto3_sns_09

「Publish a message」画面を開きましたら、「Subject」と「Message」を記入し、「Publish message」をクリックします。

boto3_sns_10

以下の画像ようなメールが届けば、AWS側の設定は完了です。

boto3_sns_11

準備(Python側)

次に、PowerUser権限をもったEC2上でPythonの準備をします。
PowerUser権限をもったEC2を準備するに当たっては下記の記事が参考になります。 AMIは「Amazon Linux AMI release 2015.09」利用しています。

次に /tmp/ に移動して、virtualenvで環境作っていきます。

$ cd /tmp/
$ virtualenv venv
New python executable in venv/bin/python2.7
Not overwriting existing python script venv/bin/python (you must use venv/bin/python2.7)
Installing setuptools, pip...done.
$ . venv/bin/activate
(venv)$

環境作ったら、pipのアップデートを行い、boto3を入れます。

(venv)$ pip install -U pip
You are using pip version 6.0.8, however version 8.0.2 is available.
You should consider upgrading via the 'pip install --upgrade pip' command.
Collecting pip from https://pypi.python.org/packages/py2.py3/p/pip/pip-8.0.2-py2.py3-none-any.whl#md5=2056f553d5b593d3a970296f229c1b79
  Using cached pip-8.0.2-py2.py3-none-any.whl
Installing collected packages: pip
  Found existing installation: pip 6.0.8
    Uninstalling pip-6.0.8:
      Successfully uninstalled pip-6.0.8

Successfully installed pip-8.0.2

(venv)$ pip install boto3
Collecting boto3
  Using cached boto3-1.2.3-py2.py3-none-any.whl
Collecting jmespath<1.0.0,>=0.7.1 (from boto3)
  Using cached jmespath-0.9.0-py2.py3-none-any.whl
Collecting futures<4.0.0,>=2.2.0 (from boto3)
  Using cached futures-3.0.4-py2-none-any.whl
Collecting botocore<1.4.0,>=1.3.0 (from boto3)
  Using cached botocore-1.3.22-py2.py3-none-any.whl
Collecting python-dateutil<3.0.0,>=2.1 (from botocore<1.4.0,>=1.3.0->boto3)
  Using cached python_dateutil-2.4.2-py2.py3-none-any.whl
Collecting docutils>=0.10 (from botocore<1.4.0,>=1.3.0->boto3)
  Using cached docutils-0.12.tar.gz
Collecting six>=1.5 (from python-dateutil<3.0.0,>=2.1->botocore<1.4.0,>=1.3.0->boto3)
  Using cached six-1.10.0-py2.py3-none-any.whl
Installing collected packages: jmespath, futures, six, python-dateutil, docutils, botocore, boto3
  Running setup.py install for docutils ... done
Successfully installed boto3-1.2.3 botocore-1.3.22 docutils-0.12 futures-3.0.4 jmespath-0.9.0 python-dateutil-2.4.2 six-1.10.0

準備が整ったのでコード書いていきます。 先ほどSNS Topicを作成した際に、「Topic Arn」を使用します。

ソース

  • main.py
#!/usr/bin/env python
# -*- encoding: utf-8 -*-

import boto3
import urllib2
import pprint

TOPIC_ARN = u'arn:aws:sns:ap-northeast-1:012345678912:sendmail'

msg = urllib2.urlopen('https://classmethod.jp/recruit/').read()
subject = u'クラスメソッド 採用情報'
client = boto3.client('sns')

request = {
    'TopicArn': TOPIC_ARN,
    'Message': msg,
    'Subject': subject
}

response = client.publish(**request)

pprint.pprint(response)

実行結果

実行したら以下のようなメールが届きます。
(内容は弊社採用情報のHTMLです)

 (venv)$ python main.py
{u'MessageId': '5d66c8d8-4041-58be-8085-87f9004c79a4',
 'ResponseMetadata': {'HTTPStatusCode': 200,
                      'RequestId': '9c3b7ac4-59db-54d5-9887-35e519d695cf'}}

boto3_sns_12

まとめ

送信先固定で通知だけを行うのであればboto3+SNSがお手軽かなと思います。
pipでインストールが必要なのが、boto3だけですので通知内容次第ではコードをそのままAWS Lambdaにもっていき動作させることも可能だと思います。