複数の ChatGPT プラグインを開発し AI オーケストレーションを実行するサンプルコード

今回は Copilot stack のカスタマイズの中心となるプラグイン開発について紹介します。

# Copilot stack
Copilot stack は大規模 LLM をオーケストレーターとして利用し、複数のプラグインや外部システムの情報と連携させて GPT-4 のプラグイン機能や Microsoft の各製品に搭載される Copilot と連携したり独自の Copilot を開発できるフレームワークです。

https://qiita.com/nohanaga/items/c3e92c9adeca7c84a8d5

# プラグイン開発
[ChatGPT 規格のプラグイン](https://platform.openai.com/docs/plugins/introduction)を開発すれば、以下のようにブラウザ版 GPT-4 だけでなく、Bing や Microsoft 365 Copilot、Windows Copilot などからも利用可能になります。当然、組織独自の Copilot と統合することもできます。このプラグインによって、最新の情報や組織内のデータを反映させた（Grounding）回答を行ったり、ReAct などのタスクを実行させることが可能になります。Microsoft では、業界全体の連携を推進するために、プラグインの標準として [OpenAPI プラグイン仕様](https://swagger.io/specification/)の採用を進めています。
![0033.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/674344/d75295d9-0a6a-3495-8b97-0e6caaebc582.png)
以下参考になります。

https://note.com/npaka/n/n16b35e48fd4d

# 複数のシステムをプラグイン化する
はい、いつもの戦国武将ネタでデモを行おうと思います。コードはデモ用に極限までシンプル化しています。
![スクリーンショット 2023-07-03 13.54.11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/674344/eb85baf9-ecaf-b821-c035-eef024cbcb1a.png)
今回はこのような 2 つの異なるシステムを ChatGPT プラグインとして公開し、これを AI オーケストレーターである LangChain から呼ぶデモを構築します。

「**源範頼に関連するカフェ名を検索して、7/1の18時に予約に空きがあるか教えて。もし空いていたら予約しておいて。**」というユーザーからの指示に回答できるようなシステムを構築します。


## 開発するプラグインとエンドポイント
 - 武将カフェ検索プラグイン: カフェ検索システム スタブ
     - `/search` カフェ検索
 - レストラン予約プラグイン: レストラン予約システム スタブ
     - `/search` 予約検索
     - `/reserve` 予約

## 制約条件
 - 使用するモデルは `gpt-4-0613`。ReAct で `gpt-35-turbo` を使用すると失敗する確率が高い。
 - langchain のバージョンは `0.0.218`, `0.0.268` で動作確認済

# フロー解説
1. UI からユーザーの指示が投げられます。
1. クエリは LangChain が受け取り、`ZERO_SHOT_REACT_DESCRIPTION` Agent が Reasoning を行います。　
1. **武将カフェ検索プラグイン**にアクセスし、 API 仕様をロードし、エンドポイントの情報と説明書きを受け取ります。その結果、検索ができそうだと判定します。実際に検索するには、「GET リクエストを `/search` エンドポイントに送信して、クエリパラメータとしてカフェの名前を指定する必要があります。」と考えて、「源範頼」を `5005` 番ポートに検索リクエストを投げます。
1. 次に**レストラン予約プラグイン**を呼び出して、「カフェかば殿」で 7/1 の 18 時に予約が可能かどうかを確認します。「そのためには、`/search` エンドポイントをGETリクエストで使用します。パラメータとして `q` （レストラン名）と `datetime` （日時）を必要とします。」と考えます。`5006` ポートにアクセスして、カフェ名と空き状況の情報を検索してます。
1. このカフェでは予約可能であることが確認できましたので、今度は `/reserve` エンドポイントに POST リクエストを送信して予約を行います。**OK** が返ってきましたので予約完了です。
1. 最後に UI に「カフェかば殿で 7/1 の 18-19 時で予約を行いました」と返却します。

# AIPluginTool へプラグインをロード
```python
llm = ChatOpenAI(model_name="gpt-4-0613", temperature=0)
tools = load_tools(["requests_all"])
plugin_urls = ["http://localhost:5005/.well-known/ai-plugin.json", "http://localhost:5006/.well-known/ai-plugin.json"]

tools += [AIPluginTool.from_plugin_url(url) for url in plugin_urls]
```

# Agent の初期化
制約条件や言語の設定をプロンプトに含めています。
```python
SUFFIX = """
Answer should be in Japanese. Use http instead of https for endpoint.
If there is no year in the reservation, use the year 2023. 
"""

# Responsible AI MetaPrompt
#**IMPORTANT**
#If a restaurant reservation is available, must check with the user before making a reservation if yes.'

agent_chain = initialize_agent(tools,
                            llm,
                            agent=AgentType.ZERO_SHOT_REACT_DESCRIPTION, verbose=True,
                            agent_kwargs=dict(suffix=SUFFIX + prompt.SUFFIX))
```

# Function calling
`gpt-4-0613`、`gpt-3.5-turbo-0613` の最新モデルでは Function calling 機能が追加され、これまでAgent 、プロンプトでやっていた必要なツールの選定をモデル側でやってくれます。Langchain ではいち早く連携され、`AgentType.OPENAI_FUNCTIONS` と指定するだけで利用することができます。コチラを使うと Reasoning 全体の速度がめちゃくちゃ速くなります。

```python
import langchain
langchain.debug = True

agent_chain = initialize_agent(tools,
              llm,
              agent=AgentType.OPENAI_FUNCTIONS, verbose=True)
```

`AgentType.OPENAI_MULTI_FUNCTIONS` を使用すると呼び出しを並列化してコストを削減することもできます。

`langchain.debug = True` を設定すると LangChain によって隠蔽化されているリクエストの中身を見ることができるので便利です。

# ChatGPT プラグインを作るのがめんどくさい？
ChatGPT に作ってもらいましょう。
![008.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/674344/fbb3dc24-99b9-aa6e-74be-4256399a6a98.png)

# AI 安全性
このデモでは単純化するために、ユーザーへの確認プロセスなどを省いていますが、AI の安全性、 Responsible AI の観点から実際にアクションを実行する直前には人間からの最終確認のプロセスを導入することも検討してください。

# 今後
Azure AI Studio が使えるようになると、このような AI オーケストレーターをクラウド上で構築し、テストやエンドポイントのデプロイまでできるようになります。早く使えるようになって欲しいです。

# サンプルコードと Notebook
https://github.com/nohanaga/busho-plugins-demo

このデモだけのために究極に単純化したコードを Github に上げておきましたのでご参考まで。この部分、**複数の社内システム**ですとか、**開発した機械学習モデル**ですとかと繋げてみていただければできることが非常に広がるのではないでしょうか。