挑戦者が現れた時に通知してくれるSlack Botを作った

公開日:2019-01-15
最終更新:2019-01-15
※この記事は外部サイト(https://qiita.com/hatunina/items/8db78037a...)からのクロス投稿です

クロス投稿のテストです。
Qiitaに書いた記事はこちら
https://qiita.com/hatunina/items/8db78037aa1b119dca06

概要

  • 会社の人たちと「Slackを使ったおもしろいアプリを作る」というテーマで土善旅館で最高な開発合宿をしてきました。

  • 「参戦」という文字を入れてメンションを飛ばすと、そのユーザのアイコンでスマブラ風なコラ画像を作成し返信してくれるSlack botを作りました。

  • 土善旅館は最高

成果物

主な処理

  • botへ「参戦」という文字を入れてメンションを飛ばす
  • Slack Real Time Messaging(RTM)がメンションを検知
  • コラ画像生成
      メンションを飛ばしたユーザのアイコン、チャンネルを取得
      素材画像とアイコンを合成・マスク処理
  • コラ画像を投稿

プロジェクト構成

run.py を起動することでメンションを検知しコラ画像を返信することができます。
AWSで常時稼働させたかったのですがそこまで作る時間がなかったため、今回はおうちオンプレ(ローカルホスト)で運用予定です。

$ tree -I "__pycache__"  
.  
├── LICENSE  
├── README.md  
├── images  
│   └── challenger.jpg  
├── run.py  
├── slack_rtm_src  
│   ├── __init__.py  
│   └── rtm.py  
├── slackbot_settings.py  
└── src  
    ├── collage_generator.py  
    ├── main_pipeline.py  
    ├── slack_util.py  
    └── util.py

また、ソースコード、各種設定は下記リポジトリにあるので詳細はそちらをご覧ください。
https://github.com/hatunina/slack_sannsenn_bot


コラージュ生成処理

images に置いてあるベースになる素材画像です。この記事では縮小して表示していますが元のサイズは1,200×675です。

メンション検知後、メンションを飛ばしたユーザーのアイコンです。512×512のサイズで取得しています。

白い部分に合わせ素材画像にアイコンをペーストします。

白い部分を切り抜くためにマスク画像を用意します。

ペーストした画像とマスク画像を合わせます。


コラージュ生成処理(コード)

以下は先ほどの処理を行なっているコードです。
メンション検知後にこれらの処理が呼ばれコラ画像作成後に返信を行なっています。


from PIL import Image  
from PIL import ImageDraw  
from PIL import ImageFilter  


def collage_generate_pipeline(icon_image):  
    # 素材画像を開く  
    challenger_format = open_image()  
    # 素材画像にアイコンを貼り付け  
    back_im = back_image_generate(challenger_format, icon_image)  
    # マスク処理と複合処理  
    im = mask_image(challenger_format, back_im)  

    return im  


def open_image():  
    # 素材画像を開く  
    challenger_format = Image.open('./images/challenger.jpg')  
    return challenger_format  


def back_image_generate(challenger_format, icon):  
    # 素材画像にアイコンを貼り付け  
    back_im = challenger_format.copy()  
    # x, y  
    back_im.paste(icon, (580, 80))  
    return back_im  


def mask_image(challenger_format, back_im):  
    # マスク処理と複合処理  
    mask = Image.new("L", back_im.size, 0)  
    draw = ImageDraw.Draw(mask)  

    # 楕円を切り抜く(x0, y0, x1, y1)  
    draw.ellipse((650, 90, 1030, 590), fill=255)  

    # 枠をぼやかす  
    mask_blur = mask.filter(ImageFilter.GaussianBlur(10))  
    im = Image.composite(back_im, challenger_format, mask_blur)  

    return im

collage_generate_pipeline 関数の引数 icon_image はこの処理の前に以下の関数で取得しています。

import requests  
from PIL import Image  
import io  


def get_icon(message):  
    icon_url = message.user.get('profile').get('image_512')  
    icon = requests.get(icon_url, stream=True)  

    # 取得したバイナリデータはオンメモリで処理するのでImage型に変換  
    icon_image = Image.open(io.BytesIO(icon.content))  

    return icon_image

改善点

  • 素材画像へのアイコン貼り付け位置や楕円の切り取り範囲がベタ打ちになってしまっているので、別の素材画像やユーザのアイコンによってはいい感じのコラ画像が作成されない
  • おうちオンプレ環境を想定しているのでPCを持ち出したりするとメンションを検知できない(AWS lambdaで動かすとかしたかった)
  • エラーハンドリング、ログ等…

本当はこんな感じにしたかったやつ

下図のような「参戦!!」をSlackに新メンバーがジョインした後にbotにメンションを飛ばすとアイコン・ユーザ名を取得して返信してくれるbotを作りたかったのですが…

輪郭の切り取り(背景の削除)やユーザ名の書き込みがうまくいかず時間切れに。
下図のようなクオリティになってしまったので「挑戦者が現れました!!」に変更しました。

なんだか思ってたのと違う…

まとめ

土善旅館は猫もいるしご飯もうまいし開発環境も揃っているしホスピタリティ最高!!

参考

https://qiita.com/sukesuke/items/1ac92251def87357fdf6
https://note.nkmk.me/python-pillow-paste/
https://note.nkmk.me/python-pillow-composite/
https://qiita.com/ekzemplaro/items/6bd539983ba8997003b9

「参戦!!」の方のフォント
http://mplus-fonts.osdn.jp/about.html#multilingual-2

土善旅館については下記記事が最高な感じです。
https://darui.io/saikou-no-natsu/

記事が少しでもいいなと思ったらクラップを送ってみよう!
54
+1
@hatuninaの技術ブログ

よく一緒に読まれている記事

0件のコメント

ブログ開設 or ログイン してコメントを送ってみよう
目次をみる

技術ブログをはじめよう

Qrunch(クランチ)は、ITエンジニアリングに携わる全ての人のための技術ブログプラットフォームです。

技術ブログを開設する

Qrunchでアウトプットをはじめよう

Qrunch(クランチ)は、ITエンジニアリングに携わる全ての人のための技術ブログプラットフォームです。

Markdownで書ける

ログ機能でアウトプットを加速

デザインのカスタマイズが可能

技術ブログ開設

ここから先はアカウント(ブログ)開設が必要です

英数字4文字以上
.qrunch.io
英数字6文字以上
ログインする