この記事では、ChatGPTのAPIを活用して「チャットボット」を作成する方法をご紹介します。
プログラミング言語は、PHPの人気フレームワーク「Laravel」を使用します。
こちらが、完成後のイメージです。
前提
・Laravelはインストールされているとします。
・2023/8/17時点最新のLaravelのバージョン10で作成しています。
それでは、手順に沿って具体的なソースコードを元に説明していきます。
1. OpenAIのAPIクライアントをインストール
OpenAIのAPIを利用できるパッケージがPHPで用意されているので、 そちらを以下コマンドでインストールします。
composer require openai/openai
2. 環境変数の設定
インストールが完了したら、.envファイルに、OpenAIのAPIキーを追加します。
OPENAI_API_KEY=your_openai_api_key
OpenAIのAPIキーの取得方法は、OpenAIサイトのこちらにアクセスします。
アカウントを一度も作成されていない方は、アカウントを作成する必要があります。
ログインを行ったら、右上の「View API Keys」をクリックします。
「+Create new secret key」 ボタンをクリックして、APIキーを生成します。
キーをコピーします。
3. ルートとコントローラの設定
ChatbotControllerを作成する為に、以下コマンドを実行します。
php artisan make:controller ChatbotController
ChatbotController.phpに以下のコードを追加します。
App/Http/Controllers/ChatbotController.php
<?php namespace App\Http\Controllers; use Illuminate\Http\Request; use OpenAI\Laravel\Facades\OpenAI; use Illuminate\Support\Facades\Session; class ChatbotController extends Controller { public function index() { return view('chatbot'); } public function ask(Request $request) { $userMessage = $request->input('message'); // これまでの会話をセッションから取得 $conversation = Session::get('conversation', []); // ユーザーのメッセージを会話に追加 $conversation[] = $userMessage; // コンテキストとしてプロンプトを作成 $prompt = implode(" ", $conversation); $response = OpenAI::completions()->create([ 'model' => 'text-davinci-003', 'prompt' => $prompt, 'max_tokens' => 150 ]); // Botの応答を会話に追加 $conversation[] = $response['choices'][0]['text']; // 更新された会話をセッションに保存 Session::put('conversation', $conversation); return response()->json($response['choices'][0]['text']); } }
ソースコードを要約:
indexメソッドは、chatbotという名前のビューを表示する役割を持っています。
askメソッドは、ユーザーからのメッセージを受け取り、それを元にOpenAIのAPIを使ってボットの応答を生成します。
これまでの会話の履歴はセッションに保存され、それをプロンプトとしてAPIに提供することで、より文脈に合った応答を得られるようにしています。
それが、リロード時なのかXボタン押したタイミングなのか要件によって変わるので、本記事ではそちらの処理は省いています。
最後に、ボットの応答をJSON形式で返しています。
次にルートを設定します。
routes/web.php
use App\Http\Controllers\ChatbotController; Route::get('/chatbot', [ChatbotController::class, 'index']); Route::post('/chatbot/ask', [ChatbotController::class, 'ask']);
ソースコードを要約:
/chatbot へのGETリクエストは、ChatbotControllerのindexメソッドを実行します。
/chatbot/ask へのPOSTリクエストは、ChatbotControllerのaskメソッドを実行します。
Viewの作成
チャットボットのUI部分を作成します。
resources/view/chatbot.blade.php
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="csrf-token" content="{{ csrf_token() }}"> <title>Chatbot Interface</title> <script src="https://code.jquery.com/jquery-3.5.1.min.js"></script> <link href="{{ asset('css/app.css') }}" rel="stylesheet"> </head> <body> <!-- Chatbot button --> <div class="chatbot-button"> <button id="openChatbot">チャットボットを使う</button> </div> <!-- Chatbot window --> <div class="chatbot-window"> <div class="chatbot-header"> <p>チャットボット サポート</p> <button id="closeChatbot">x</button> </div> <div class="chatbot-messages" id="messages"></div> <div class="chatbot-input"> <input type="text" id="userInput" placeholder="質問..."> <button id="sendMessage">送信</button> </div> </div> <script> $.ajaxSetup({ headers: { 'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content') } }); $(document).ready(function() { $('#openChatbot').click(function() { $('#openChatbot').fadeOut(); $('.chatbot-window').fadeIn(); }); $('#closeChatbot').click(function() { $('.chatbot-window').fadeOut(); $('#openChatbot').fadeIn(); }); $('#sendMessage').click(function() { let message = $('#userInput').val(); $('#messages').append('<div>あなた: ' + message + '</div>'); <figure class="figure-image figure-image-fotolife" title="チャットボット デモ用GIF">[f:id:enginiya:20230817232731g:plain]<figcaption>チャットボット デモ用GIF</figcaption></figure> $.post( "{{ route('ask') }}" , { message: message }, function(data) { $('#messages').append('<div>Bot: ' + data + '</div>'); }); $('#userInput').val(''); }); }); </script> </body> </html>
ソースコードを要約:
メッセージ送信ボタンがクリックされたとき、ユーザーのメッセージがメッセージエリアに追加されます。
また、そのメッセージがJQueryのAjaxを使って、サーバーに送信され、応答が受信されるとメッセージエリアに追加されます。
シンプルですが、もしデザインも参考にしたい場合のcssはこちらです。
body { font-family: Arial, sans-serif; } p { margin: 0px; } .chatbot-button { position: fixed; bottom: 2%; right: 2%; } .chatbot-button button { background-color: #FFA500; padding: 15px 25px; font-size: 18px; border: none; border-radius: 5px; cursor: pointer; color: white; position: relative; } .chatbot-button button::after { content: ' \2191'; font-size: 20px; position: relative; top: -2px; } .chatbot-window { position: fixed; bottom: 10%; right: 2%; width: 300px; height: 400px; background-color: #f5f5f5; border-radius: 10px; box-shadow: 0 0 10px rgba(0, 0, 0, 0.1); display: none; /* initially hidden */ } .chatbot-header { padding: 10px; background-color: #333; color: white; border-top-left-radius: 10px; border-top-right-radius: 10px; display: flex; justify-content: space-between; } .chatbot-messages { padding: 10px; overflow-y: scroll; height: 300px; } .chatbot-input { padding: 10px; display: flex; justify-content: space-between; } .chatbot-input input { width: 80%; padding: 5px; border: 1px solid #ccc; border-radius: 5px; } .chatbot-input button { padding: 5px 15px; border: none; background-color: #007bff; color: white; border-radius: 5px; cursor: pointer; width: 80px; }
以上で完成となります!
補足
今回のチャットボットの実装は、基本的なものになります。
もし、本番環境で使用する場合には、エラーハンドリングやセキュリティの強化、レートリミットなどのさまざまな要素を考慮する必要があります。
また、例えば、特定の会社や商品の情報に特化しているカスタマーサポートのチャットボットを構築する際は、明示的な指示や文脈・データを与えていくことで、より適切な応答を得ることができます。
本記事では詳しく解説しませんが、構築する際は以下方法が考えられます。
プロンプトの強化:
プロンプト(質問や文脈)を強化することで、モデルに特定の文脈や方向性を与えることができます。
例えば、特定の製品やサービスに関する情報をモデルに伝えることで、より関連性の高い答えを得ることができます。
FAQデータベースの活用:
よくある質問とその答えをデータベースに保存し、ユーザーからの質問がFAQと一致する場合は、データベースから答えを返すようにすることで、より正確な答えを提供することができます。
フィードバックの収集:
ユーザーからのフィードバックを収集し、モデルの応答の質を評価します。
不適切な応答やエラーを修正するための情報として利用します。
モデルのチューニング:
GPTのモデル自体を、特定のタスクやドメインに対する学習を強化するためのファインチューニングを行う。
ファインチューニングとは、特定のタスクや目標に対してAIモデルの振る舞いを最適化するためのカスタマイズ手法です。
チャットログの解析:
ユーザーとのチャットログを解析して、どの質問がよくされるのか、どの質問に対してモデルが不適切な答えをしているのかなどを特定し、ボットの応答を改善します。
シナリオベースの学習:
特定のシナリオや問題解決の流れを設計し、それに基づいてユーザーの問題を解決するためのガイダンスを提供します。
これらのアプローチを組み合わせることで、カスタマーサポートボットのパフォーマンスとユーザーエクスペリエンスを向上させることができます。
お疲れ様でした!
今後もこのような情報を発信していくので、ぜひTwitterのフォローをお願いします!