はじめに
2023年6月にOpenAIからAPIの新機能、Function callingがリリースされました。
この記事はOpenAIのFunction callingについて、自分なりの覚え書きです。
自分の理解を深めるためのアウトプットの一環として。
言語はPythonです。
Function callingの概要
例として、会話文から郵便番号を検索するプログラムを考えます。
郵便番号を検索する外部のAPIを使います。
郵便番号検索API
住所(の一部)から郵便番号が返ります。
このAPIには住所を渡す必要があります。会話文をそのまま渡すとエラーになります。
Function callingがリリースされる前
OpenAI API に会話文から住所を抜き出してもらいます。
住所を抜き出してもらうための前提条件(プロンプト)も合わせて渡します。
渡した前提条件が適切であれば、OpenAI APIは正しく必要な引数だけを返してくれます。
しかし、ChatGPTは出力に「揺らぎ」があるので、会話文の内容や前提条件によっては、期待している形の引数を返してもらえないことがありました。
たとえばこんな感じ。
この揺らぎを抑えるために前提条件をうんうん作り込む必要がありました。
前提条件のガイドラインというのもなく、試行錯誤です。
しかも、どこまで作り込めば揺らぎがなくなるのか皆目見当がつかないので、デスマーチでした。
回答が揺らいだ時に備えて、プログラム側で対処しようにも、限界があります。
趣味でやる分にはいいですが、サービスとして提供するとなると、ちょっと困りますよね。
Function callingをつかう
Function callingは会話文と関数の定義を送ることで、OpenAI APIが会話文から判断して関数に必要な引数を抽出してくれるようになりました。
出力の揺らぎがなくなり、安定して期待している関数の引数を取得できます。
サンプルコード
今回のサンプルコードはこちらです。
処理内容
考察
Function callingは関数自体を実行してくれません。
あくまで関数を実行するために必要な引数を返すだけです。
→はじめ、OpenAI APIのサーバーの方で関数を実行してくれると思ってました(汗
関数を実行するコードを自分で実装する必要があります。
サンプルコードの中の関数の実行箇所はStep4のこちらです。
function_response = function_to_call(
address=function_args.get("address"),
)
関数の定義したJSONデータをもとに、ChatGPTが会話文から必要な引数を取り出してくれます。
JSONデータにある関数の説明文がサラッと一言なのに、ChatGPTがきちんと意味を読み取ってくれるんですよね。
日本語でもOKなのが助かります。
おわりに
Function callingはエンドユーザー的にはインパクトはないですが、
システム開発者的にはありがたい機能です。
ChatGPTからの出力は「揺らぎ」があるので、JSON形式などで出力するように前提条件で頑張るのも限界があると言うか、そもそもそこにリソースを注ぎ込むのはもったいないです。
なので、OpenAIさんには感謝ですし、開発のスピードが速い!
あと、この投稿をするきっかけとなったのが、2023年11月にリリースされたGPTsのCustom Actionsでした。
Custom Actionsでは、呼び出す関数の定義をJSON形式で記述します。
このフォーマットについて、コピペだの見よう見まねでコネコネしていたので、いまいち理解してませんでした。(汗)
基本的な考え方は、先にリリースしたこのFunction callingがベースになっているので、自分なりに良い勉強になりました。
走り書きみたいな覚え書きですが、お役に立てれば幸いです。
参考資料
郵便番号検索API - 郵便番号の一覧を取得
https://postcode.teraren.com/doc/redoc#tag/Postcode/operation/getPostcodes
ChatGPTの新機能 "GPTs" でCustom Actionsを使って住所から郵便番号を検索してみた
https://qiita.com/iconss/items/abad02ad618a4e795c94