AWSのSNSを使ってrubyからAndroidにプッシュ通知を送る

More than 3 years have passed since last update.


Google API Consoleでの準備



  1. Google Cloud Messaging for AndroidのステータスをONにする。

  2. サーバーアプリケーションのキーを作成する。


    1. 新しいキーを作成をクリック。


    2. サーバーキーをクリック。

    3. 許可対象IPアドレスに0.0.0.0/0と入力する。



  3. 作成したAPIキーを書き留めておく。

  4. プロジェクトの概要を開いてプロジェクト番号を書き留めておく。


AWSのコンソールでの準備

SNSのAppを作成します。


  1. SNSの管理画面でAdd a New Appをクリック。


  2. Application Nameには好きな名前を、Push PlatformにはGoogle Cloud Messagingを、API Keyには先ほど作成したAPIキーを設定。

  3. 作成したAppのPlatformApplicationArnを書き留めておく。


Androidアプリの準備

省略。適当に受信できるアプリを作って下さい。


aws-sdk gemの追加

Gemfile

gem 'aws-sdk', '~> 2'


送信用rubyプログラム

sns = Aws::SNS::Client.new(region: 'ap-northeast-1') # regionは環境に合わせて変更

token = "<アプリが送ってきたregistration_id>"

# endpointの作成
app_arn = "SNSのapp_arn"
resp = sns.create_platform_endpoint(
platform_application_arn: app_arn,
token: token
)
# endpointのARNの取得
endpoint_arn = resp.endpoint_arn

# endpointの属性は以下のように取得する
resp = sns.get_endpoint_attributes(endpoint_arn: endpoint_arn)
# => #<struct attributes={"Enabled"=>"true", "Token"=>"APA91...XKmHKeA"}>
# Enabled属性は文字列で"true"であることが分かる。

# 同じtokenと同じ属性を持つendpointの作成を再度行うと、同じARNが返ってくる。
resp = sns.create_platform_endpoint(
platform_application_arn: app_arn,
token: token,
attributes: {"Enabled" => "true"}
)
resp.endpoint_arn == endpoint_arn
# => true

# tokenが同じで異なる属性を持つendpointの作成を行おうとするとエラーが発生する
resp = sns.create_platform_endpoint(
platform_application_arn: app_arn,
token: token,
attributes: {"Enabled" => "false"}
)
# => Aws::SNS::Errors::InvalidParameter: Invalid parameter: Token Reason: Endpoint arn:aws:sns:ap-northeast-1...xxxxx already exists with the same Token, but different attributes.

# endpointの属性は以下のように設定する
resp = sns.set_endpoint_attributes(
endpoint_arn: endpoint_arn,
attributes: { "Enabled" => "true" }
)

# プッシュ通知の送信
data = {data: {
text: "hogehoge",
post: {
id: 1,
title: "fuga"
}
}}.to_json.gsub('"', "\\\"")
message = <<-EOD
{"GCM": "
#{data}"}
EOD
resp = sns.publish(
target_arn: endpoint_arn,
message: message,
message_structure: "json"
)