やりたいこと
HTTP RESTしかしゃべれないアプリからのデータでも、AWS IoTにPublishしたい!
概要
AWS IoTにPublishするのってMQTTだけじゃなくてHTTP RESTでも出来るんです
Clients can publish by sending a POST message to
<AWS IoT Endpoint>/topics/<url_encoded_topic_name>?qos=1
一方でAPI GatewayはAWS Service ProxyでAWS各種サービスへRESTリクエストをproxyできます
- Amazon API Gateway で AWS Service Proxy を使って DynamoDB にアクセスする | Developers.IO
- Amazon API Gateway の AWS Service Proxy の使い方
これ組み合わせれば、独自なRESTクライアントからのリクエストでもAWS IoTにデータ送れるようになります
論よりコード
- IAM ポリシー作成
- IAM ロール作成
- API GatewayでAPI endpoint作成
IAM ポリシー作成
ポリシー
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "Stmt1460435015000",
"Effect": "Allow",
"Action": [
"iot:Publish"
],
"Resource": [
"*"
]
}
]
}
iot:publish が入っていればOKです
IAM ロール作成 & ポリシーアタッチ
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Sid": "",
"Principal": {
"Service": "apigateway.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
上記のように信頼されたエンティティのIDに apigateway.amazonaws.com が指定されていればOKです
また、このロールに先ほど作成したポリシーをアタッチしてください
Endpoint 作成
Integration Requestを下記のように作るだけです
項目 | 設定内容 |
---|---|
Integration type | AWS Service Proxy |
AWS Region | |
AWS Service | Iot Data |
AWS Subdomain | <`aws iot describe-endpoint` で表示される XXXXX.iot.REGION.amazonaws.com の XXXXX の部分> |
HTTP method | POST |
Action Type | Path override にして topics/{tp_lv1}/{tp_lv2}
|
Execution role | <先に作成したロールのARN> |
Credentials cache | Do not add caller credentials to cache key |
画面上はこんな感じです
解説とポイント
ポイントは Action Type を Path override にするところにあります
これにより、API GatewayからAWS内のサービスにHTTP RESTリクエストが発信されるようになります
また、最終的に呼ばれるURIは <AWS Subdomain>.iot.<AWS Region>.amazonaws.com/<Path override>?<URL Query String Parameters>
となります
URL Path Parameters;
Path override 内の {param_name}
を Mapped from で置き換えます
また Path override の中の {...} は URL Path Parameters で置き換わります
下記の例だと最終的には A33XXXXXXXXXT.iot.ap-northeast1.amazonaws.com/topics/sensor/geo?qos=1 が呼ばれることになり、ロールに割り当てられたポリシー(iot:publish)の権限を使ってPublishできるようになるというわけです
あとがき
Content-Type: application/octet-stream なリクエストでも、API Gatewayの $util と、マッピングを駆使すればJSON化できるので、AWS IoTを経由して好きなサービスを呼び出すこともできますね
※Amazon API Gatewayにおいてバイナリデータの調査をしました
Lambdaをそのまま使えば?という声も聞こえてきそうですけど。