kubell Creator's Note

ビジネスチャット「Chatwork」のエンジニアのブログです。

ビジネスチャット「Chatwork」のエンジニアのブログです。

読者になる

ChatworkとGoogle ColaboratoryでMidJourneyライクなAIアート体験を作ってみよう!

こんにちは!お絵描きできるエンジニアのcw-ozakiです。

最近はAIアートが流行っていますね。お絵描き好きとしては乗るしかない!このビッグウェーブに!!! というわけでChatworkとGoogle Colaboratoryを使ってMidJourneyライクなChatOpsでAIアートを作れる環境を作ってみたのでその手法を紹介してみます。

まぁ、MidJourney使ったことないのであってるかは知らないんですけどね。

事前準備

各種アカウントを作成しましょう。 特に理由はないけどChatworkはビジネスアカウントにすると便利ですよ!

ノートブックの作成&実行

環境のセットアップ

colab.research.google.com

それではColabを開いて早速作っていきましょう。 まずはランタイム > ランタイムのタイプを変更をクリックしてGPUを有効にします。 Colab Pro+に入るとバックグラウンド実行ができるので、そちらにアップグレードした方はバックグラウンド実行にもチェックしておくと便利です。

まずは後々利用するための変数を設定します。

# APIトークンの設定
CHATWORK_ROOM_ID="[ChatworkでAIアートを投稿するルームのID]"
CHATWORK_API_TOKEN="[ChatworkのAPIトークン]"
HUGGING_FACE_TOKEN="[Hugging Faceで発行したAPIトークン]"
NGROK_AUTH_TOKEN="[ngrogのAuthトークン]"

グループチャットを作成する – ヘルプ | Chatwork

APIトークンを発行する – ヘルプ | Chatwork

User access tokens

Getting Started | ngrok Documentation

それぞれの値はこの辺を参考にすると取得できるかと思います。

次に生成した画像を保存するディレクトリを作成しましょう。

# ディレクトリの作成
!mkdir /content/tmp

もし画像をGoogle Driveに保存したい場合は

# Google Driveのマウント
from google.colab import drive
drive.mount('/content/drive') # /content/drive/MyDrive/path/to が保存先になる

とすると保存可能になります。この場合は後に出てくる保存先のパスを/content/drive/MyDrive/path/toとGoogle Driveの保存したいディレクトリに変更してください。

次に依存パッケージをインストールします

# 依存パッケージのインストール
!pip install diffusers==0.2.4 transformers scipy ftfy flask pyngrok requests werkzeug

ここまで設定できたら環境のセットアップが完了です。

Stable Diffusionのセットアップ

Stable Diffusionのパイプラインを設定して、Hugging Faceからモデルのダウンロードを行います。

# StableDiffusionパイプラインの準備
from diffusers import StableDiffusionPipeline

pipe = StableDiffusionPipeline.from_pretrained("CompVis/stable-diffusion-v1-4", use_auth_token=HUGGING_FACE_TOKEN)
pipe.to("cuda")

もしここでエラーが出る場合はリポジトリへのアクセス権限を取得してください。

huggingface.co

ChatworkのWebhookを受け取りAIアートを生成するサーバーの作成

Chatworkからメッセージを受けとり、AIアートを生成してChatworkに投稿するためのサーバーを作成します。

# Webhook Serverの起動
import threading
import torch
import requests
import uuid
import os
from flask import Flask, request, abort
from werkzeug.serving import run_simple

app = Flask(__name__)

index = 0

def do_work(path, prompt):
    image = pipe(prompt,
                height=512,
                width=512,
                guidance_scale=7.5,
                num_inference_steps=50,
                generator=torch.Generator("cuda").manual_seed(0),
                )["sample"][0]
    image.save(path)

    file_data = open(path, 'rb').read()
    files = {
        "file": (os.path.basename(path), file_data, "image/png"),
    }
    post_message_url = f"https://api.chatwork.com/v2/rooms/{CHATWORK_ROOM_ID}/files"
    headers = {'X-ChatWorkToken': CHATWORK_API_TOKEN}
    response = requests.post(
        post_message_url,
        headers=headers,
        files=files,
    )

@app.route("/", methods=['POST'])
def callback():
    json = request.get_json()
    if not json:
        return 'OK'
    if not json["webhook_event"]:
        return 'OK'
    if not json["webhook_event"]["body"]:
        return 'OK'
    body = json["webhook_event"]["body"]
    if body.startswith("/") != 1:
        return 'OK'

    prompt = body.strip('/')

    filename = f"{str(uuid.uuid4())}.png"
    filepath = f"/content/tmp/{filename}"

    thread2 = threading.Thread(target=do_work, kwargs={'path': filepath, 'prompt': prompt})
    thread2.start()

    return 'OK'

thread = threading.Thread(target=lambda: run_simple("0.0.0.0", 5000, app))
thread.start()
thread.join()

ngrokを経由して外部からアクセス可能にする

ngrokを起動して先ほど立ち上げたサーバーを外部に公開します。

# NGROKの認証
!ngrok authtoken $NGROK_API_KEY
# NGROKの起動
import os

from pyngrok import ngrok
from pyngrok.conf import PyngrokConfig

os.system('kill -9 $(pgrep ngrok)')
webhook_url = ngrok.connect(addr='127.0.0.1:5000', pyngrok_config=PyngrokConfig(start_new_session=True))
print (webhook_url)

実行するとngrokのURLが表示されるので大切に保管しましょう。

ChatworkでWebhookを設定する

最後に先ほど取得したngrokのURLを使ってChatworkのWebhookを設定します。

注意点としてngrokのURLはhttpですがこちらをhttpsに直した上で設定するようにしてください。

これでWebhookを設定したルームで/好きな呪文という形式でメッセージを書くとChatwork上で好きなAIアートを生成できるようになります。

楽しい🎉🎉🎉 私の環境はColab+なのでだいたい30秒から60秒ぐらいで生成できるのでなかなか良い感じです。

注意点

Colabの環境は常時起動環境ではないため、だいたい数時間から24時間ぐらいで止まってしまいます。(Colabのプラン次第) 手軽に試すための環境なので、もし常時起動したいならColab以外でちゃんと組みましょう。たぶんSQSとECSのGPUインスタンスとかを使うと良いんじゃないでしょうか。未検証ですけど。

あと、特にキューイングなどの制御はしてないので同時にメッセージを送ると生成に失敗します。 Python詳しくなくてオンメモリキューのライブラリとか知らなくて面倒だったので諦めてます。その辺で詳しい方がいたらいい感じに直してください。

終わりに

AIアート楽しいですね! Chatworkにはアップロードしたファイルを取得するAPIもあるのでimage2imageや、Fine Tuningなんかも同じような仕組みで実現できそうです。

ちょっとまだガチャ感が強いですが、Chatworkに組み込むと面白そうな雰囲気はありますね!どう組み込もうかなぁ。