AWSの運用・導入、システム開発・アプリケーション開発のことならクロスパワーのクラウド

電話番号 電話番号 お問い合わせ

受付時間 平日10:00~18:00

TOP

お問い合わせはこちら

AWS IoT エンタープライズボタンでRaspberry Piで写真を撮ろう

社内に例のボタンが先日届いたので使ってみました。

 

よく見る使い方ですが、ポチっと押すとラズパイに繋げたWebカメラが写真を撮り、

S3にアップロードしたりSlackに投稿したりを試してみましょう。

 

目次

 

撮影テスト
AWS IoTの設定
実行スクリプトの編集
Lambda関数の変更
IoT 1-Clickの設定
slackへの投稿

 

撮影テスト

 

今回はfswebcamを使って写真を撮ります。

 

ラズパイへsshし、apt-get install fswebcamでfswebcamをインストールし、

fswebcam test.jpgでテスト撮影してみましょう。

 

 

無事写真が撮れたようです。

 

AWS IoTの設定

 

今回は以前のブログで作成したモノやスクリプトそのまま使い回しちゃいます。

ので、モノの状態を管理してくれるAWS IoTのThing Shadowを使います。

状態のRunningが1の場合、写真撮って0に戻します。

 

モノの設定等は以下の記事に記載してあります。

 

AWS IoT – インスタンスの起動状態をRaspberry Piに繋げたLEDで監視しよう

 

写真撮ってアップロードするだけなのでShadow stateを使用したこの方法はあまりスマートではないのですが……

ボタンでstateの切り替えを応用したら色々と面白い事が出来そうですね。

 

上記環境より変更するのは実行スクリプトとLambdaになります。

 

実行スクリプトの編集

 

まずは画像アップロード用のバケットをs3に作成しましょう。

 

今回はboto3を使うので、amユーザーを用意、boto3とawscliをインストールし、

aws configure行います。

 

 

runningが1の時写真撮ってs3上げる様にちょこっと編集加えます。

 

from AWSIoTPythonSDK.MQTTLib import AWSIoTMQTTShadowClient

import json
import time
import datetime
import logging
import subprocess
import boto3
s3 = boto3.resource('s3')
bucketName = "xp-rpi-pic"

def updateState():
    report_json = '{"state":{"desired": {"running": 0}}}'
    deviceShadowHandler.shadowUpdate(report_json, None, 5)

def take_pic(payload, response, token):

    payloadDict = json.loads(payload)

    if int(payloadDict["state"]["running"]) == 1 :
        today = datetime.datetime.today()
        filedate = today.strftime("%Y%m%d_%H%M%S")
        filename = "%srpipic.jpg" % filedate
        cmd = "fswebcam %s" % filename
        subprocess.call(cmd,shell=True)
        s3.Bucket(bucketName).upload_file(filename,filename)

    updateState()

host = "xxxxxxxxxxxxx.iot.ap-northeast-1.amazonaws.com"
port = 8883
clientId = "xxxxxxxx"
thingName = "xxxxxxx"
rootCAPath = "xxxxxxx"
certificatePath = "xxxxxxx"
privateKeyPath = "xxxxxxx"

#logger = logging.getLogger("core") # Python 3
logger = logging.getLogger("AWSIoTPythonSDK.core") # Python 2
logger.setLevel(logging.DEBUG)
streamHandler = logging.StreamHandler()
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
streamHandler.setFormatter(formatter)
logger.addHandler(streamHandler)

# Init AWSIoTMQTTShadowClient
myAWSIoTMQTTShadowClient = None
myAWSIoTMQTTShadowClient = AWSIoTMQTTShadowClient(clientId)
myAWSIoTMQTTShadowClient.configureEndpoint(host, 8883)
myAWSIoTMQTTShadowClient.configureCredentials(rootCAPath, privateKeyPath, certificatePath)

# AWSIoTMQTTShadowClient configuration
myAWSIoTMQTTShadowClient.configureAutoReconnectBackoffTime(1, 32, 20)
myAWSIoTMQTTShadowClient.configureConnectDisconnectTimeout(10) # 10 sec
myAWSIoTMQTTShadowClient.configureMQTTOperationTimeout(5) # 5 sec

# Connect to AWS IoT
myAWSIoTMQTTShadowClient.connect()

deviceShadowHandler= myAWSIoTMQTTShadowClient.createShadowHandlerWithName(thingName, True)

deviceShadowHandler.shadowRegisterDeltaCallback(take_pic)

while True:
    pass

 

Lambda関数の変更

 

前回はインスタンスの状態を反映させてましたが、今回はボタン押したらrunningを1にしたいだけです。

 

import boto3
import json

def lambda_handler(event, context):
    
    state = "1"
        
    client = boto3.client('iot-data')
    response = client.update_thing_shadow(
        thingName='xxxxxxx',
        payload=json.dumps({"state":{"desired": {"running": state}}})
    )


IoT 1-Clickの設定

 

後はボタンにLambda関数を紐づけます

 

デバイスの登録等は以下の記事にあります。

 

AWS IoT Enterprise Buttonを使ってみよう

 

AWSコンソールのIoT 1-Clickに移動し

プロジェクトを作成し……

 

 

 

Lambda関数を紐づけ……

 

 

プレイスメントを作成し、デバイスに紐づければ設定完了です。

 

 

Slackへの投稿

 

折角なのでSlackへの投稿も試してみました。

 

Slack Appsよりbotを作成し、tokenをメモし、指定のチャンネルにbotを招待します。
channelsはチャンネルのurlを見ればすぐ分かります。

 

import requestsし、s3にアップロードする箇所を変更しましょう。

 

files = {'file': open(filename, 'rb')}
param = {
    'token': "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
    'channels': "xxxxxx"
}
requests.post(url="https://slack.com/api/files.upload",params=param, files=files)

これでボタンをポチポチしますとSlackに写真が投稿されるはずです。

 

Copyright 2016 Cross Power Corporation. All Rights Reserved.