まだプログラマーですが何か?

プログラマーネタとアスリートネタ中心。たまに作成したウェブサービス関連の話も http://twitter.com/dotnsf

タグ:api

このブログエントリの続きです:
Slack の OAuth API を使ってみる

↑ここで紹介した方法を使って実際にアプリケーション・サービスを作ってみました。作った内容はこれ↓の Slack 版です:
お絵かき LIFF アプリを作ってみた

2019052501


(実はもともとは Twitter 向けに作ったのですが)LINE のフロントエンドフレームワーク: LIFF を使って、その場で指でお絵描きした画像を LINE のトークルームに送信する、という連携アプリケーションを以前に作りました。その Slack への移植です。

なお、このアプリケーションは Barloon というエンジニア向けバーで企画されたハッカソン向けに作成しました。興味ある方は "Barloon" でググって調べてみてください。


【作った物】
こちらで MIT ライセンスで公開しています。よかったら使ってください:
https://github.com/dotnsf/slack-doodle

2019052502



以下でも紹介していますが、注意点として「ワークスペースごとにアプリケーション・サーバーが1台必要」です。その理由ですが、このアプリは Slack API を利用して作っているのですが、Slack API に登録アプリを申請する際にワークスペース(https://○○○○.slack.com/ の ○○○○部分)を指定して申請する必要があるからです。ここで申請したワークスペース向けにアプリケーションを作って動かす形になるため、複数のワークスペースで動くアプリケーションを1つの URL で動かすことができないのでした(このあたりが上記の LINE 向けアプリと異なります)。


【サーバーの動かし方】
このアプリケーションは Node.js 上で動くウェブアプリケーションです。一応レスポンシブ対応しているつもりなので、PC ブラウザからも、スマホのブラウザからも使えます(PC ブラウザの場合はマウスで、スマホブラウザの場合は指でお絵描きすることになります)。したがって Node.js が導入済みのアプリケーション・サーバーが必要です。

利用にあたっては、まず Slack API のアプリケーション登録が必要です。こちらの詳しい手順はこのリンク先を参照してください:
http://dotnsf.blog.jp/archives/1074688701.html

ただし1点だけ注意が必要です。上記ページではアプリケーションの scope に channels:read のみを指定していますが、このお絵描きアプリケーションでは更に加えて:
 chat:write:user
 files:write:user
の2つ(計3つ)の scope を指定する必要があります(描いた画像を API でアップロードするために必要な scope です)。この3つを scope に指定する必要がある、という点に注意してください。

2019052503

※必要に応じてアプリケーションのアイコンなども好きなものに変えておいてください。


その上で上記 github の URLからソースコード一式を Node.js アプリケーションサーバー上に git clone するか download & unzip して、ソースコードを展開します。

展開後、settings.js というファイルが存在しているので、このファイルをテキストエディタで開き、exports.slack_client_id の値と、exports.slack_client_secret の値をそれぞれ Slack API 登録アプリの client_id および client_secret の値に書き換えて保存します(このあたりの具体的な情報はこちらを参照してください)。

そしてアプリケーションサーバーを起動、これで準備完了です:
$ npm install
$ node app

【遊び方】
アプリケーション・サーバー(例えば https://slack-doodle.xxx.com/ )が動いている状態で、そのアプリケーションサーバーの URL に PC かスマホのブラウザにアクセスするだけなのですが、その前にやっておくことがあります。

上記でも触れたのですが、このアプリケーションサーバーは特定のワークスペース向けに作られています(そのワークスペースでしか使えません)。一方、ブラウザで Slack にアクセスすると、いろんなワークスペースに切り替えて使うことができます。ということはブラウザが目的のワークスペース以外のセッションなどを保持している可能性があり、その状態で使っても期待通りの挙動にならない可能性があるのです。

この状態をクリアするために『念の為』以下の手順を最初に行っておくことを推奨します。まず PC かスマホのブラウザを起動し、目的のワークスペース(例えば目的のワークスペースが "abc" であれば https://abc.slack.com/ )にアクセスして、認証してログインします。これでブラウザが目的のワークスペースのセッションを保持した状態が作れました。

その上で、そのままアプリケーションサーバー( https://slack-doodle.xxx.com/ )にアクセスします。以下はスマホでの画面例ですが、PCブラウザだともう少し横に大きな画面になると思います(一応、この未ログインの時点でお絵描きを試すことはできるのですが、送信することはできません)。ではログインするため左上の "Login" をタップします:
2019052504


Slack アプリケーションのページに転送され、目的のワークスペースに向けた OAuth の認証が行われます:
2019052505


内容を確認して、「許可する」を選択します:
2019052506


するとログインが完了し、元のアプリの画面に戻ります。この時、画面上部にワークスペース上で自分が利用することのできるチャネルが選択できるようになり、POST をクリックすると、ここで選択したチャネルに描いた画像がアップロードされます:
2019052507


実際に POST するとこんな感じで目的のワークスペースの目的のチャネルに画像をアップロードすることができます:
2019052508


この系統のアプリ、Twitter ではじめて、LINE に移植して、今回は Slack にも移植して・・・ 次は何にしよう?? ちなみに facebook は publish の API が昨年廃止になってしまったので技術的に作れないことがわかってます。



某アプリを Slack 対応する経緯で Slack API の中の、特に認証/認可を司る OAuth API を使う機会があったので自己まとめです。

もともとやりたかったのはウェブアプリに Slack アカウントでログインして、そのログインした人の権限でチャネル一覧を取得し(※)、ウェブアプリから指定したチャネルにメッセージを書き込む、ということでした。この中の※部分までを Node.js + Express + EJS で実現したコードを Github に公開しています(後述)。


実際に試してみるにはまず Slack に対象アプリケーションを登録する必要があります。 https://api.slack.com/apps を開いてログインし、"Create New App" ボタンをクリックしてウェブアプリを登録します:
2019052401


登録するアプリの名前と、対象ワークスペースを指定します(つまり同じアプリを複数のワークスペースで使いたい場合は、アプリを複数登録する必要があります)。以下では名前は "Slack OAuth Sample"、ワークスペースは "dotnsf" を指定しています(ワークスペースはログインしたユーザーが利用可能なワークスペース一覧から選択します)。最後に "Create App" ボタンをクリックして作成します:
2019052402


すると指定したアプリケーションの API 設定画面に切り替わります。画面左上に入力したアプリ名がデフォルトアイコンと一緒に表示されていて、"Basic Information" メニューが選択されていることを確認します:
2019052403


この画面を下スクロールすると App Credentials という項目があります。この中の Client IDClient Secret の値を後で使うので、どこかにコピーしておくか、いつでもこの画面を開ける状態にしておきましょう。なお Client ID の値は画面内に表示されていますが、Client Secret の値は初期状態では非表示になっています。"Show" ボタンをクリックして内容を表示し、その表示された値をあとで使うことに注意してください。またこれらの値は他の人には教えないように、自分で管理する必要があります:
2019052404


次に画面左のメニューから "OAuth & Permissions" を選び、少し下にスクロールすると Redirect URLs という項目があります。ここにウェブアプリケーションを動かす際のコールバック URL を登録しておく必要があります。"Add New Redirect URL" ボタンをクリックします:
2019052405


すると Redirect URL を追加する画面になるので、http(s)://サーバー名/slack/callback と入力します。この値は開発時には開発時用のサーバー名とポート番号、本番環境では本番環境用のサーバー名を指定する必要があります。下図では開発時向けに localhost の 6010 番ポートで動かす想定で http://localhost:6010/slack/callback と指定しています。ここの値は実際の環境に合わせて適宜変更してください。入力し終わったら "Add" ボタンをクリックして、その後 "Save URLs" ボタンをクリックします:
2019052406


画面上部に "Success!" というメッセージが表示されればリダイレクト URL の設定は完了です。正しい Redirect URLs が登録されたことを確認します:
2019052407


続けて、このアプリで利用する Slack 機能のスコープを指定します。実は OAuth 認証だけであればここの設定は不要なのですが、今回のデモアプリでは OAuth 認証後にログインユーザーが参照できるチャネルの一覧を取得して表示する、という機能が含まれています。また実際のアプリケーションではそのアプリケーションで実装する機能によって、ここでスコープを追加する必要があります:
2019052408


今回はログインユーザーが利用できるチャネル一覧を取得するため、"channels:read" スコープを追加します。また他に必要なスコープがあればここで追加します。最後に "Save Changes" ボタンをクリックして変更を反映します:
2019052409


これで Slack API 側の設定は完了しました。

では改めて Github からアプリケーションを取得します。Node.js がインストール済みの実行サーバー上で以下の URL を指定して git clone するか、ソースコードをダウンロード&展開してください:
 https://github.com/dotnsf/slack-oauth

2019052410


ソースコード内の settings.js をテキストエディタで開き、exports.slack_client_id の値と exports.slack_client_secret の値を上記で確認した client_id と client_secret の値に(コピー&ペーストなどで)変更して、保存してください。

なお、このサンプルアプリケーションでは以下のリクエスト API(?)が用意されていて、これらを明示的&内部的に使って動きます:
リクエスト API用途
GET /ユーザーがアクセスする唯一のページ。アクセス時に認証情報がセッションに含まれているとチャネル一覧が表示される。認証情報がセッションに含まれていない場合は認証前とみなして「ログイン」ボタンを表示する
GET /slack/loginユーザーページで「ログイン」ボタンをクリックした時に実行される。Slack の OAuth 認証ページにリダイレクトされる
GET /slack/callbackSlack の OAuth 認証ページで Authorize された時のリダイレクトページ。この URL が Slack OAuth 設定時に指定されている必要がある。アクセストークンを暗号化してセッションに保存し、GET / へリダイレクトされる
POST /slack/logoutログアウト(セッション情報を削除)する
GET /channelsチャネル一覧を取得する。認証後にユーザーページが表示されると内部的にこの REST API が AJAX 実行されて、画面にチャネル一覧が表示される。


では実際に起動してみます。起動サーバーにログインし、ソースコードのあるフォルダに移動した状態で、以下を実行します:
$ npm install
$ node app

そしてウェブブラウザで起動中のアプリケーションにアクセスします。以下の例では localhost:6010 でアプリケーションが起動されている想定になっているので、http://localhost:6010/ にアクセスします。上記の GET / が実行され、ログイン前のシンプルなページが表示されます。ここで "Login" を選択します:
2019052411


GET /slack/login が実行され、ブラウザは Slack API の OAuth 認証ページにリダイレクトされます。アプリケーションが利用する scope が表示され、このまま認証処理を許可するかどうかを聞かれます。許可する場合は "Authorize" を選択します:
2019052412


Authorize を選択すると認証と認可が完了し、そのアクセストークンが GET /slack/callback へ渡されます。そこでアクセストークンを暗号化してセッションに含めます。この状態であらためてトップページ(GET /)が表示され、ログイン処理が住んでいるのでログイン後の画面が表示されます。AJAX で GET /channels が実行され、ログインユーザーが参照することのできるチャネルの一覧が表示されれば成功です:
2019052413


以上、Slack API の OAuth を使ってウェブアプリケーションから Slack の認証を行い、認証ユーザーの権限で Slack API を外部から実行する、というアプリケーションのサンプルを作って実行するまでの手順紹介でした。


 

Swagger APIはインタラクティブに動く REST API のドキュメントを比較的簡単に作ることができて便利です。自分も実際に業務やプライベートアプリに使っています。

この機能を使う場合、YAML と言われるフォーマットをベースにした記述方法で API の仕様を記述するだけで動く API ドキュメントページを作ることができます。

で、この YAML で仕様を記述する際に「コメント」を記述したくなることがあります。実質的にプログラミングする必要なく API テストページを作れるのは便利で、プログラミング時と同様にコメントを残したくなることもあると思います。 が、YAML でコメントを書いたことがなかったので、改めて明示的にコメントを残そうとした際の手法がわからず、調べてみました。

答えとしては「# から行末までがコメント」となるようです。つまり一行単位でコメントが生成されます。「ここからここまで」という範囲コメントは存在していないようです。
info:
  description: 普通の行
#  description: コメント行
  titie: タイトル   # ここはコメント  

なお、コメント扱いにしたくない # を含めたい場合は \# のようにバックスラッシュでエスケープすることで実現できます。




 

業務で「リモート操作で扉の鍵を施錠/解錠する」必要があり、いろいろ調査した結果 Akerun という入退室管理システムを使ってみました。その様子をメモ目的でブログにしました。
2019030400


扉の鍵をリモート操作で開ける、という需要はあると思っています。特定の条件を満たす人だけが入れる部屋を作りたい(そのためのロジックを加えて実装したい)とか、締め忘れて外出してしまった可能性のある家の扉の鍵をいま居る場所から施錠したいとかです。

で、いくつか調べてみました。Bluetooth や NFC などを使って比較的近い距離間で通信できるものは多く提供されているようでしたが、現在 REST API を使って離れた場所からも操作できるもの、となると(2019年2月に私が探した限りで※)株式会社フォトシンスから提供されている Akerun (Pro) という製品だけのようでした。

※他に探した範囲では REST API が提供されていなかったり、以前は提供されていたが現在は提供されていなかったり、日本向けの情報が提供されておらずそもそも日本で入手できるのか不明だったり・・・という結果でした。

なお、Akerun 自体には(買い取り式の)個人向け製品も存在しているのですが、REST API が提供されているのは業務用の Akerun Pro という月次レンタル製品のみとのことでした。気軽に使ってみるにはちとハードルが高いかもしれないと感じたのと、それ故かあまり技術情報をウェブで見かけることがあまりありませんでした。そんな背景もあって今回ブログで紹介しようかな、と思い立ったのでした。


【システム構成】
まず Akerun Pro を使った今回のシステム構成はこんな感じになります:
2019022601


Akerun(今回利用するのは正確には "Akerun Pro" ですが、以下 "Akerun" と表記します)は既存のドアに設置可能なデバイスです。外部から信号を送ってドアのサムターン部分を回して解錠/施錠します(要はサムターンが回せる位置に Akerun を取り付けて使う、というものです)。実際には NFC などのカードを使って開閉することもできます(注 Akerun Pro では一式揃っています)が、今回は使いません。

特に REST API でリモート操作する場合は、Akerun デバイスに加えて Akerun Remote と呼ばれるインターネットとのルーターとなるデバイスを追加設置します(Akerun Remote も Akerun Pro に含まれています)。上図のように Akerun と Akerun Remote は Bluetooth で接続されます。Akerun Remote は有線または無線LANでインターネットに接続します(私は WiFi テザリングで試しました)。無線 LAN の設定等はスマホ用の専用アプリを使って Akerun Remote に設定することができます。

このようにして Akerun Remote をインターネットに接続した後は管理用画面や API を使って解錠/施錠の指示を出すことができるようになります。それらの指示はインターネットを経由して Akerun Remote へ伝わり、Akerun Remote から Akerun へ Bluetooth による指示が送られてサムターンが(指示されたように)動く、というものです。


【準備】
API の使用は申込み制となっていて、こちらのページ内の「こちらのお申込みフォーム」と書かれたリンクから申し込みを行う必要があります:
https://developers.akerun.com/#introduction

申込時に名前やメールアドレス、電話番号等を登録していくのですが、 OAuth 認証のリダイレクト URI を指定する箇所があります:
2019022602

 
この URI は実在している必要はないのですが、実在しない場合はエラー時にリダイレクトされない URI である必要があります(OAuth リダイレクト時のパラメーターを受け取る必要があるため、実在しない場合でもパラメータを保持した URI でエラー表示される必要があります)。また https:// の URI である必要がある点に注意が必要です。ここで指定した URI は後で使うのでメモしておきましょう。ここでは仮に https://myapp_for_akerun.mybluemix.net/callback という URI を指定したものとして以下を紹介します。

申し込みの手続きが完了すると(数日後に) OAuth 認証用の client_id と client_secret が記載されたメールが送信されてきます。ここでは仮に
 client_id: "my_client_id"
 client_secret: "my_client_secret"
という値が送られてきたものと仮定して以下を紹介します(実際にはランダムな文字列です)。

ここまで完了するとアクセストークンの発行ができるようになります。


【アクセストークンの取得】
ウェブブラウザで以下の URL にアクセスします:
https://api.akerun.com/oauth/authorize/?client_id=(送られてきた client_id の値)&redirect_uri=(申込時に指定したリダイレクト URI の値)&response_type=code

上記の前提であれば、具体的には以下の URL となります:
https://api.akerun.com/oauth/authorize/?client_id=my_client_id&redirect_uri=https://myapp_for_akerun.mybluemix.net/callback&response_type=code


正しい値が指定されていると redirect_uri のアドレスにリダイレクトされます。その時の URI に code 
というパラメータが付与されているので、この値を取り出します。例えばリダイレクト先が
 https://myapp_for_akerun.mybluemix.net/callback?code=XXXXXXXXXX
という URI であれば、XXXXXXXXXX 部分が該当します。この値を code 値として以下を続けます(code 値は取得から 30 分間有効なので、取得から 30 分以内に以下のアクセストークンの取得を行ってください)。

取得した code 値と HTTP POST を実行できるツール(curl など)を使って、以下の HTTP POST リクエストを実行します(実際には改行せず一行で入力します):
$ curl -X POST "https://api.akerun.com/oauth/token"
  -d grant_type=authorization_code
  -d client_id=(client_id の値)
  -d client_secret=(client_secret の値)
  -d code=(code の値)
  -d redirect_uri=(申込時に指定したリダイレクト URI の値)



上記までに取得した例の場合だと、このような(一行の)リクエストになります:
$ curl -X POST "https://api.akerun.com/oauth/token"
  -d grant_type=authorization_code
  -d client_id=
my_client_id
  -d client_secret=
my_client_secret
  -d code=XXXXXXXXXX
  -d redirect_uri=
https://myapp_for_akerun.mybluemix.net/callback


成功すると以下のような JSON がレスポンスとして返されます:
{
  "access_token": "**********",
  "token_type": "bearer",
  "refresh_token": "xxxxxxxxxx.....",
  "expires_in": 7776000,
  "created_at": 1500853017
}



この結果の "access_token" の値(********** 部分)がアクセストークンです。


【REST API の実行】
ここまでの手順でアクセストークンが取得できていれば、その値を HTTP リクエストヘッダを使って、
 Authorization: Bearer (アクセストークンの値)

のように指定して、各種 REST API を実行することができるようになります。例えばアクセストークンのオーナーが所属する組織 ID の一覧は GET https://api.akerun.com/v3/organization で取得できるのですが、このリクエスト時に
 Authorization: Bearer **********
という HTTP リクエストヘッダを付与することで正しい権限で実行できます。

例えば組織 ID : OOO1、アケルン ID : AAA1 の鍵をリモートで解錠するには、以下の HTTP リクエストを発行します:
$ curl -X POST "https://api.akerun.com/v3/organizations/OOO1/akeruns/AAA1/jobs/unlock"
  -H "Authorization: Bearer **********"



同様にして、同じ鍵をリモートで施錠する場合は以下になります:
$ curl -X POST "https://api.akerun.com/v3/organizations/OOO1/akeruns/AAA1/jobs/lock" 
  -H "Authorization: Bearer **********"




なお、開発者向けの API 情報はこちらです:
https://developers.akerun.com/#introduction


グーグルマップは今やナビ代わりにも使えて非常に便利です。

この「グーグルマップでナビをする」という機能を一発で起動する URL を調べてみました。前提条件として GPS 機能が有効になったスマホのブラウザで起動し、現在地から目的地までのナビゲーションを行う画面にジャンプさせたいものとします。結論としては意外と簡単でした。

以下、いくつかのパターンの URL リンクを作成したので、このページを実際にスマホのブラウザで参照した後にリンクをクリックすると実際にナビゲーションを開始することができるので試してみてください。


【原則フォーマット】
具体例を以下に紹介しますが、原則的には以下のフォーマットの URL となります:
https://www.google.co.jp/maps/dir/出発地(/経由地のリスト)/目的地

出発地や経由地、目的地は 緯度,経度 で表します。

例えば(私の職場オフィスがある)東京の銀座シックスの位置は北緯 35.6696206 度、東経 139.7618279 度なので、35.6696206,139.7618279 と表現します。


【直接指定】
現在地から銀座シックスへの道案内は以下の URL です(経由地を指定していません):
https://www.google.co.jp/maps/dir//35.6696206,139.7618279

銀座シックスから東京タワー(35.658886,139.745787)への道案内はこちらの URL です:
https://www.google.co.jp/maps/dir/35.6696206,139.7618279/35.658886,139.745787


【経由地指定】
現在地から東京タワー(35.658886,139.745787)を経由して銀座シックスへ向かう道案内は以下の URL です:
https://www.google.co.jp/maps/dir//35.658886,139.745787/35.6696206,139.7618279

現在地から秋葉原(35.697850,139.771179)と東京タワーを経由して銀座シックスへ向かう道案内は以下の URL です:
https://www.google.co.jp/maps/dir//35.697850,139.771179/35.658886,139.745787/35.6696206,139.7618279


 

このページのトップヘ