🧪

DifyとLINEでAIチャットボットをつくる

に公開

TimelabLynx というカレンダーサービスを開発している takahashi(@stak_22)です。

今日のトレンドのキャッチアップがてら、AIワークフローツール「Dify」を初めて触ってみました。今回はLINEの公式アカウントを使って、Difyで設定するワークフローのAIと対話できるようにしました。
案外サクッと実装できるので、Difyのキャッチアップを兼ねてやってみるのも良いかと思います。

作ったもの

最終アウトプットとしては、LINE公式アカウントという名のAIと対話できるという、シンプルなチャットボットです。
これはプロンプト次第でいろんな使い方ができそうです。ただ今回は作り込んでいないので、ユーザーの名前を取るとか、連続してメッセージを送信するとか、会話のコンテキストを理解できるとか、そういうのはやっていないです。

システム構成

ざっくりと全体像を説明すると、使っている技術は、LINE、GAS、Difyの大きく三つです。
LINEにメッセージを送信すると、LINEのウェブフックに設定したGASが発火し、それがDifyのワークフローを発火させます。AIのレスポンスをGAS経由でLINEに送信します。
今回はDifyはプロンプトを渡して返答を受け取るだけの簡易的なワークフローだけを設定しています。

⭐️ Dify

今回の主役の Dify です。
AI agent を組み込んだワークフローをGUIで作成できます。感覚的には Figma でバックエンドを構築しているみたいな。いつか本当にそういう感じの世界になるかもしれませんね。

今回は単純なAIチャットボットなので、開始→LLM→回答 だけです。
LLMではGeminiを選択していました。モデルはいろいろあります(Difyにプラグインをインストールするみたいな感じで、いろいろあります)。
プロンプトは自由に入れて遊んだりしてます。

⭐️ LINE

まず、LINEの公式アカウントを作ります。LINEのOfficial Account Managerというウェブサイトに自分のLINEアカウントでアクセスすると、作れたりします。
チャットに関しては応答機能など自由にカスタマイズできるみたいです。とりあえずWebhookはオンにしておきます。

あとは、GASを発火させるためのWebhookを設定する必要があります。
これは、LINEにメッセージが飛んできたらそれをGASに受け流すためのものです。GASをデプロイするとウェブアプリのURL(※)が表示されるので、それをここに入れます。詳細は次項で記します。

⭐️ Google App Script

ここだけコードを書きます。
以下が私が実際に使った雑多なコードです、そのまま使えます。(3つの環境変数だけ入れてください)
スプシにログを吐き出すとかでデバッグをしてました。

// Difyのワークフローを作っているページから見つけて入れる
const DIFY_API_KEY = "dify-api-key-wo-ireru"
const DIFY_WORKFLOW_ID = "dify-workflow-id-wo-ireru"

// LINEのOfficial Account Managerから見つけて入れる
const LINE_CHANNEL_ACCESS_TOKEN = "line-channel-access-token-wo-ireru"

function doPost(e) {
  try {
    const json = JSON.parse(e.postData.contents);
    const events = json.events;

    events.forEach(function(event) {
      if (event.type === "message" && event.message.type === "text") {
        const userMessage = event.message.text;
        const userId = event.source && event.source.userId ? event.source.userId : "unknown";

        // ---- Dify Workflow API呼び出し ----
        const difyUrl = `https://api.dify.ai/v1/chat-messages`;
        const difyPayload = {
          inputs: {
            user_input: userMessage,
          },
          query: userMessage,
          response_mode: "blocking",
          user: "googleappsscript"
        };

        let aiResponse = "エラーが発生しました";
        try {
          const difyRes = UrlFetchApp.fetch(difyUrl, {
            method: "post",
            contentType: "application/json",
            headers: {
              Authorization: "Bearer " + DIFY_API_KEY
            },
            payload: JSON.stringify(difyPayload),
            muteHttpExceptions: true
          });

          const difyJson = JSON.parse(difyRes.getContentText());
          aiResponse = difyJson.answer.trim() || "すみません、もう一度お願いします!";
        } catch (error) {
          aiResponse = "Dify呼び出しエラー";
        }

        // ---- LINE Reply API ----
        const lineUrl = "https://api.line.me/v2/bot/message/reply";
        const linePayload = {
          replyToken: event.replyToken,
          messages: [{ type: "text", text: aiResponse }]
        };

        try {
          UrlFetchApp.fetch(lineUrl, {
            method: "post",
            contentType: "application/json",
            headers: {
              Authorization: "Bearer " + LINE_CHANNEL_ACCESS_TOKEN
            },
            payload: JSON.stringify(linePayload)
          });
        } catch (error) {
          // error handling
        }
      }
    });
  } catch (error) {
    // error handling
  }

  return ContentService.createTextOutput("OK");
}

できたら、「デプロイ」を押し、「新しいデプロイ」を作成します。
すると以下のようなダイアログが出てくるので、このように設定します。全員に公開しないと、LINEでせっかく発火させようとしてもGASに到達しないので、必須です。

これを完了すると、「ウェブアプリ」のURLが出てくるので、これを前述で出てきたLINEのWebhook(→※)に設定して保存します。

以上で実装は完了です。爆速でAIチャットボットの出来上がり👏

まとめ

今回は必要最低限の設定しかしませんでしたが、Dify を使うことでバックエンドの実装を要さず、簡単にワークフローを組み立てることができました。このワークフローを拡張することで、RAGを組み込んだりもできると思うので、クオリティの高いAIチャットボットを実現できそうです。

近い未来かもわかりませんが、いずれコーディングをほとんどせずにAIをいろんなものに組み込めるようになる未来を感じました。こういった技術によって今までよりずっと簡単にいろんなことが実現できるようになってきています。明日もAIの成長に目が離せません。

Timelabテックブログ

Discussion