cloud9 + lambdaでslack bot作ってみる

Adways Advent Calendar 2017 15日目の記事です。

http://blog.engineer.adways.net/entry/advent_calendar_2017


こんにちは、swfzです。

先日のre:eventで発表されたAWS Cloud9

気になっていたのでこの機会に使ってみたいと思います

Cloud9とは

Cloud9はAmazonが去年買収した IDEです

下記AWSの一部引用です

AWS Cloud9 は、ブラウザのみでコードを記述、実行、デバッグできるクラウドベースの統合開発環境 (IDE) です。これには、コードエディタ、デバッガー、ターミナルが含まれています。

新しいプロジェクトを開始するためにファイルをインストールしたり、開発マシンを設定したりする必要はありません。

また、Cloud9 では、サーバーレスアプリケーションを開発するためのシームレスなエクスペリエンスが提供されており、リソースの定義、デバッグ、ローカルとリモートの間でのサーバーレスアプリケーションの実行の切り替えを簡単に行えます。

Cloud9 を使用すると、開発環境をすばやくチームと共有し、ペアプログラミングを行って互いの入力をリアルタイムで追跡できます。

面倒な環境構築が不要でlambdaの環境構築もサクサクできます、さらに共同編集機能でペアプロできます

といった感じでしょうか

試してみるために lambda + slack api で簡単なbotを作ってみたいと思います

cloud9の起動

f:id:AdwaysEngineerBlog:20171221152637p:plain

create environmentで環境を作ります

f:id:AdwaysEngineerBlog:20171221152652p:plain

名前を入れます

f:id:AdwaysEngineerBlog:20171221152705p:plain

動かす環境を選べます、既存のEC2や新規で立てるEC2などが選べるようです

今回は新規でEC2立ててやってみます

サクサク進んでいくと構築中の画面になります

f:id:AdwaysEngineerBlog:20171221152738p:plain

しばらく待つと

f:id:AdwaysEngineerBlog:20171221152753p:plain

環境ができたようです

ここからlambdaの設定を行っていきます

f:id:AdwaysEngineerBlog:20171221152810p:plain

アプリ名、function名を入力して

f:id:AdwaysEngineerBlog:20171221152821p:plain

blueprintsから選びます

サンプルなのでとりあえずhelloworldにしておきます

f:id:AdwaysEngineerBlog:20171221152836p:plain

lambdaのトリガーを指定します

今回はslackからのリクエストを受け付けるためのAPI GATEWAYをトリガーとします

さらにリソースのパスを指定します

f:id:AdwaysEngineerBlog:20171221152900p:plain

lambdaのスペックとロールを選択します

確認画面を通して少し待つと

lambdaの環境ができました

雰囲気はこんな感じです

f:id:AdwaysEngineerBlog:20171221152915p:plain

今回は新規でlambda関数を作りましたが既存環境のものをimportしたりgitからcloneしてごにょごにょすることもできるようです

slack側の設定

今回はEvents APIを使ってボットのいるチャンネルの発言に対して反応するだけの実装をします

ボットがリクエストを送れるようにするために下記手順でボットを登録します

  • Slack Appを作る

  • Event SubscriptionsでEvents APIを有効にします

    • Subscribe to Bot Eventsmessage.channelsを選択します
    • Request URLにイベント発生時のURLを入力します(API GatewayのURL)
  • 認証イベントを通す(後述)

    • イベント発生時のURLの認証
    • lambda側でpayloadのchallengeの値をそのまま返す処理を書いて認証を通します

f:id:AdwaysEngineerBlog:20171221152941p:plain

  • アクセストークンを取得、権限設定を行う
    • OAuth & Permissionsでボットが発言できる権限を与えます

lambdaの実装

npmモジュールもターミナルからnpm installするだけであとはよしなにデプロイしてくれます

今回はslackにポストするのでslack-api-clientをインストールしておきます

cd cloud9slackapp
npm init
npm install --save slack-api-client

f:id:AdwaysEngineerBlog:20171221153008p:plain

node_module以下にモジュールがインストールされました

あとは使うだけです

とりあえず動かせそうなサンプルを用意します

  • index.js
'use strict';

console.log('Loading function');

exports.handler = (event, contet, callback) => {

  const payload = JSON.parse(event.body);

  // 通知先認証用
  if(payload['type'] && payload.type == 'url_verification') {
     callback(null, {
      statusCode: 200,
      body: payload.challenge,
    });
  }
  // bot自身の発言に対しては何もしない
  else if(payload.event['subtype'] && payload.event['subtype'] == 'bot_message'){
    callback(null, {
      statusCode: 200,
      body: '',
    });
  }
  else {
    const slackToken = 'xxxx-xxxxxxxxxxxxx-xxxxxxxxxxxxxxxxxxxxxxx';
    const slackApiClient = require('slack-api-client');
    const slack = new slackApiClient(slackToken); 

    slack.api.chat.postMessage({
      channel: 'swfz_test',
      username: 'swfz_bot',
      text: `Hello! ${payload.event.text}`,
    },(err, res) => {
      if(err){
        console.log(err);
      }
      else {
        callback(null, {
          statusCode: 200,
          body: '',
        });
      }
    });
  }
};

通知先URLの認証通すときは受け取ったchallengeの中身をそのまま返すことで認証を通すことができるのでその処理を入れています

テスト

slackから送られるpayloadを準備してテストしてみます

API Gateway(local)を選択すると対応する入力欄が出てきます

今回はPOSTでデータが送られるので Methodを POST

Bodyに実際に送られるであろうパラメータを入れていきます

最後にRunボタンを押して実行します

f:id:AdwaysEngineerBlog:20171221153040p:plain

デプロイ

テストで問題なければデプロイします

デプロイもボタンポチーしてしばらく待てば完了しています

f:id:AdwaysEngineerBlog:20171221153153p:plain

slackで確認

botをチャンネルに招待して何か発言してみます

f:id:AdwaysEngineerBlog:20171221153210p:plain

うまくいきましたね。

共同編集

ボット作成には関係ないですが共同編集を使ってみます

あらかじめ別ユーザーを作成しておきます(今回はtestというユーザー名)

f:id:AdwaysEngineerBlog:20171221153245p:plain

共有設定にするにはIDE右上のshareボタンをクリックします

f:id:AdwaysEngineerBlog:20171221153255p:plain

共同編集に招待するユーザー名を入力してInviteします

f:id:AdwaysEngineerBlog:20171221153303p:plain

招待されたユーザーで見てみるとShared with youの方に環境があるのでそこから編集作業に入ります

f:id:AdwaysEngineerBlog:20171221153316g:plain

共同編集!

varconstに変えたり、テンプレートリテラルに変えたりしてみました

同時にカーソルが動いて編集されているのがわかるかと思います

google docs使ってるみたいな感覚になりますね

f:id:AdwaysEngineerBlog:20171221181552g:plain

作業開始からの履歴も追うことができます

ペアプロ、モブプロ、研修とかで使ってみたら効果ありそうだと思いました

環境もサクッと立てられるのでlambdaに限らず色々用途はありそうです

まとめ

実際にサービス開発に使うには認証など色々クリアする課題はありそうですが

環境作るのも手軽にできるのでモックだったりサクッと作ってフィードバックをもらいたい時とかにも使えるんじゃないでしょうか

個人的にはvimモードもあるしターミナルもあるし使いやすかったです

気になったのはターミナル上でのショートカット操作とブラウザのショートカットが被るとブラウザのショートカットが優先されるのでC+wでタブを閉じてしまったりといったところが「あー!!」となりました

最後にEC2インスタンス起動分の料金は掛かるのでそこだけ注意ですね