ChatGPTを用いて、OpenAI APIのファインチューニング向けデータセット作成ツールを作ってみた。

OpenAI APIには簡単にファインチューニング出来る機能があるので、ファインチューニングしてみることにしました。
※この記事は連作の1/2です。※[続きはこちら](https://qiita.com/katsuki_ono/items/ae67eee30efe1f7c61f9)

ただ、そうは言ってもデータがないし、自力でデータを用意するのは面倒なので、ChatGPTを用いてデータを作成するツールを作って、このツールで、データを用意することにしました。

作成したツールは、Slack botを使って、Slackへの入力とChatGPTが生成したテキストをセットでJSONファイルに保存するツールです。

今回は、ツールを実行中にした方がいいので、インスタンスイメージがubuntuのAWSを使用します。

手順は、OpenAI APIのファインチューニング向けデータセット作成ツールを実行中にするだけです。

# OpenAI APIのファインチューニング向けデータセット作成ツールを実行中にする
まず、インスタンスに接続したら、以下をインストールします。

aptのアップデート
```
sudo apt update
```

pipのインストール
```
sudo apt install python3-pip
```

slack boltのインストール
```
sudo pip install slack-bolt
```

openaiのインストール
```
sudo pip install openai
```

次にJSONのファイルを保存するディレクトリを作成します。
```
mkdir ディレクトリ名
```

作成したディレクトリに移動します。
```
cd ディレクトリ名
```

以下のpythonコードを実行して、データを保存するJSONファイルを作成します。
pythonを起動
```
python3
```

JSONファイルを作成
```python
import json

conversations_file = "conversations.json"

# 空のJSONファイルを作成
with open(conversations_file, 'w') as f:
    pass
```

作成したディレクトリでファイルを作成します。
```
nano ファイル名
```

作成したファイルの中に下記のbotのコードを入れて、ctrl Oでファイルを保存して、ctrl Xでファイルを閉じます。
※Slackとopenaiのキーやトークンをあらかじめ入れておいてください。
※このSlack botにはSlack APIの設定も必要になります。
※詳しくは[こちら](https://qiita.com/katsuki_ono/items/5ba8d6b541bcbc633f56)をご覧ください。
```python
import json
import os

import openai

from slack_bolt import App
from slack_bolt.adapter.socket_mode import SocketModeHandler

os.environ["SLACK_BOT_TOKEN"] =  ""
os.environ["SLACK_SIGNING_SECRET"] = ""
os.environ["SLACK_APP_TOKEN"] =  ""

openai_api_key = ""

app = App(
    token=os.environ.get("SLACK_BOT_TOKEN"),
    signing_secret=os.environ.get("SLACK_SIGNING_SECRET")
)

openai.api_key = openai_api_key


assist1 = ""
conversations_file = "conversations.json"
conversations_list = []

# 初回起動時にJSONファイルを読み込む
try:
    with open(conversations_file, "r") as f:
        for line in f:
            if line.strip():  # 空行をスキップ
                conversations_list.append(json.loads(line))
except FileNotFoundError:
    pass  # ファイルが存在しない場合、何もしない

@app.event("message")
def handle_message(event, say):
    global assist1
    global conversations_list
    text = event["text"]
    
    if text.strip().lower() == "削除":
        if len(conversations_list) > 0:
            conversations_list.pop()
            with open(conversations_file, "w") as f:
                for conv in conversations_list:
                    f.write(json.dumps(conv) + '\n')
            say("最新のデータを削除しました。")
        else:
            say("もう削除するデータはありません。")
        return

    response = openai.ChatCompletion.create(
        model="gpt-3.5-turbo",
        messages=[
            {"role": "system", "content": "任意の設定"},
            {"role": "assistant", "content": assist1},
            {"role": "user", "content": text},
        ]
    )
    assist1 = response["choices"][0]["message"]["content"]  # assist1を更新

    conversation = {"prompt": text + "\n\n###\n\n", "completion": " " + assist1 + "\n"}
    conversations_list.append(conversation)

    with open(conversations_file, "a") as f:
        f.write(json.dumps(conversation) + '\n')

    say(assist1)


if __name__ == "__main__":
    handler = SocketModeHandler(app,app_token=os.environ.get("SLACK_APP_TOKEN"))
    handler.start()
```

一度、上手くファイルが作成されているか下記のコマンドで確認します。
```
find ~
```

上手くファイルが作成されていたら、screenを作成します。
```
screen -S スクリーン名
```

screen内でpythonで作成したファイルを実行します。
```
python3 ファイル名.py
```

bolt run!と表示されたら、botのいるSlackのチャンネルでbotに話しかけてみます。
botから上手く返答があったら、インスタンスからSFTP等を用いてローカルマシンにJSONファイルをダウンロードします。
JSONファイルを開いてデータが保存されていたら成功です！
※日本語文字は一見文字化けしてますが、問題ないです。ChatGPTに渡すと日本語に翻訳します。

# 最後に
データセットは作れたので、いよいよ次回ファインチューニングを行います！
また何か作ってみます。