[Slack x 業務効率化] Slack APIを利用してCurlから画像をアップロードしてみた


2020/09/17
2022/01/10
蛸壺の技術ブログ|Slack APIを利用してCurlから画像をアップロードしてみた

Slackの自分用チャンネルにデータ処理中の画像をポーンと自動送信してくれるシェルスクリプトを作成したかったのですが、ローカルにある画像を送るにはどうもWebhookではダメそうでした。

ローカルから画像ファイルをアップロードするにはSlackのAPIを適切に設定してから利用する必要があるらしいので、こちらを試してみます。


下準備 ~ Slack APIを使う前の設定手順

何も設定していない段階では、Slack APIを使うことはできません。

まずはAPIを新規作成し、tokenと呼ばれる認証情報を取得するまでの手順を説明します。

Slack APIの作成 ~ Tokenを取得

まずはSlack Apiの作成画面まで行きます。

Slackのいつもの画面からクリックして進むには以下のように4回くらい飛ばされればたどり着けます。

合同会社タコスキングダム|蛸壺の技術ブログ

いつもどこにいけばいいのか迷うくらいなら、
https://api.slack.com/appsで直接画面に飛ぶことも可能です。

まずは
[Create an App]をクリックするとアプリ作成のダイアログが出てきます。

App Nameと対象のWorkspaceを入力します。

合同会社タコスキングダム|蛸壺の技術ブログ

アプリを新規作成すると以下のようなダッシュボード画面に移ります。

合同会社タコスキングダム|蛸壺の技術ブログ

手始めにダッシュボードのメニューから認証設定を行うため、
[Feature] > [OAuth & Permissions]を選択します。

最初にアプリの実行権限をスコープで設定していきます。

SlackのAPIダッシュボードのUIは結構な頻度で変わっているようです。

現在の2020年9月の段階では、
Bot Token ScopesUser Token Scopesを分けて権限の設定をするような仕様になっています。

合同会社タコスキングダム|蛸壺の技術ブログ

アプリの用途によってどちらのスコープを設定するかは分かれると思います。

今回はボットからアップロードしたいケースは
Bot Token Scopesを設定し、任意のユーザーから実行したいケースではUser Token Scopesを設定します。

また、ボットから画像アップロードとちょっとしたコメントを送信という形を取りたいので、
Bot Token Scopesに以下の2つのスコープを設定します。

            
            chat:write
files:write
        

合同会社タコスキングダム|蛸壺の技術ブログ

なおスコープの設定は複数選択可能です。

またスコープ設定後は自動で変更点を保存してくれます。

それではワークスペースにこのアプリをインストールしてみます。

ダッシュボードから
[Settings] > [Install App]に進み、[Install App to Workspace]を押します。

合同会社タコスキングダム|蛸壺の技術ブログ

後はワークスペースの管理者側がこのアプリを承認することでトークンを生成する仕組みです。

合同会社タコスキングダム|蛸壺の技術ブログ

これで無事トークンが得られました。

このトークンは後で利用しますので、コピーしてどこかに控えておきましょう。

ちなみにワークスペースにインストールされたアプリは、ボットユーザーとして登録されているようです。

合同会社タコスキングダム|蛸壺の技術ブログ

アプリをチャンネルに追加

今回のボットアプリを作成してそのままでは、どこにも投稿先のチャンネルが登録されていないため、利用できない状態です。

ということで、
アプリを利用したいチャンネルに追加する必要があります。

既にあるチャンネルやパブリックチャンネルへも追加できるのですが、以下はプライベートチャンネルを新規作成して、アプリを追加する手順を模式的に描いています。

合同会社タコスキングダム|蛸壺の技術ブログ

これで自分専用のチャンネルにボットが画像を投下してくれるような設定が完了しました。


シェルスクリプトの実装例

ここからは先程のチャンネルに画像が実際に送信されているかを見ていきたいと思います。

動作テスト

まずはcurlでテキストが送信されるかテストします。

公式の
Slack Api Reference | files.uploadの中のExampleを見ると、curlでテキストを送信しているサンプルがありますので、これを参考にします。

curl側の事情で、-dオプションと-Fオプションは混在させて使うことが出来ないので、

-Fオプションを利用する場合は、

            
            $ curl -XPOST \
    -F "content=launch plan" \
    -F channels="チャンネルの名前" \
    -H "Authorization: Bearer xoxb-xxxxxxxxx-xxxx" \
    https://slack.com/api/files.upload
        
もしくは-dオプションでやろうと思えば、

            
            $ curl -XPOST \
    -d "token=xoxb-xxxxxxxxx-xxxx&content=launch_plan&channels=チャンネルの名前" \
    https://slack.com/api/files.upload
        

-Fオプションでは、-dオプションのようなクエリ文字列(
"hoge=hogehoge&piyo=piyopiyo")みたいに書けません。

よって、複数のパラメータを送る場合は
"-F 'hoge=hogehoge' -F 'piyo=piyopiyo'..."と一つ一つ繋げて書く必要があります。

-dオプションのほうが便利そうですが、
&などの特殊文字を含むurlエンコードに注意が必要です。

変換の手間を考えると-Fを使っても良いと思います。

いずれにせよ、どちらかの作法で送ることができます。

画像の送信

いよいよ画像の送信を試します。

公式の
Slack Api Reference | files.uploadでもcurlでの画像アップロードで送信しているサンプルもあります。

これを参考にローカルの画像を上げてみます。

以下のようなスクリプトファイルを作成してみましょう。

            
            #!/bin/sh

#APIのトークン
SLACK_API_TOKEN=xoxp-xxx-xx-xx-xxxx

#アップロードしたいファイルまでの絶対パス
filepath=/path/to/graph.png

#アプリを追加したチャンネルの名前
channels="チャンネルの名前"

curl -F "file=@${filepath}" -F channels="$channels" -H "Authorization: Bearer ${SLACK_API_TOKEN}" https://slack.com/api/files.upload
        
このスクリプトを実行してチャンネルに画像が投下されていたら成功です。

合同会社タコスキングダム|蛸壺の技術ブログ


まとめ

Slack APIを上手く使うことで、画像を希望のチャンネルにアップロードできるようになりました。

ちょっとした画像ならば手軽にSlackに送り出すことが可能です。

他にも定点観測カメラの画像を一定間隔でSlackへ送信したりと、面白い応用が考えられます。
記事を書いた人

記事の担当:taconocat

ナンデモ系エンジニア

主にAngularでフロントエンド開発することが多いです。 開発環境はLinuxメインで進めているので、シェルコマンドも多用しております。 コツコツとプログラミングするのが好きな人間です。