OpenAIのAPIとStreamlitで簡単なAutoMLCoding「GPT Paisen for AutoML」を作ってみた

[OpenAIの利用がAzure上で開始](https://azure.microsoft.com/ja-jp/products/cognitive-services/openai-service)されました！

[OpenAIのサイトからでも申請すればAPIは利用できますが](https://openai.com/blog/openai-api)、GPTの機能としてはAzureのものと大きな差はありません。　

手元のAzureからすぐに利用できそうなので、Azure上の機能で何か作ってみたいなあ、、、そういえば、[Streamlit](https://streamlit.io/)を使えば簡単にWebアプリ化できるし、これも組み合わせてみよう！

そうだ　データサイエンティストをサポートできるなにかをとりあえず作ってみよう！

ということで、CSVファイルを入力してターゲットを設定したら、**簡単な予測モデルを作成するpythonコードをChatGPTに作ってもらえるWebアプリケーション**をStremlitで作ろうと思いました！


注：[AzureからOpenAIサービスは利用申請が別途必要になります。 2023/4/6現在](https://azure.microsoft.com/ja-jp/products/cognitive-services/openai-service)

## まとめ

- **OpenAIのAPIは簡単に使えます！**
- **Streamlitを使えば、インプット・アウトプットのUIも簡単**に作成でき、**2時間たらずで簡単なアプリを作成**できました！
- 今回は雑なアイデアでアプリ化してみたが、ChatGPTの入力やアイデア次第では、**もっと活用はできそう**だと思いました！

画面はこんな感じです！

![img1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3322507/10cec271-917e-1c9a-f34c-96aa47c46b37.png)



CSVファイルをアップロードして（今回は適当に作成したダミーデータを使います）、

![img2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3322507/f77df2ab-031e-b0fe-7959-725417a7a3cc.png)


予測カラム名を選択して、


![img3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3322507/8612d076-f7ab-77f0-b9b9-223e81896268.png)



実行ボタン「Plase Tell Me, GPT PAISEN!!!!」をクリックすると、、、予測のpythonコードを書いてくれます！！！

![img4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3322507/0a04eb41-a9b0-21fa-8449-2635d826143e.png)



予測カラムのデータタイプがクラスなのか数値なのかも付加情報などで与えた方が良さそうなど、もろもろツッコみどころはある気がしますが、モックアプリが簡単に作れることが体感できました！


## 作成手順

なお、コードはモックとしてかなり簡単な書き方で書いています。

### 1. ライブラリのインポート

openai, streamlit, pandas　など諸々のライブラリはすでにインストールしてあるとします。


```python
import os
import requests
import json
from io import StringIO
import gc
gc.enable()

import pandas as pd
import streamlit as st
import openai
```

### 2. OpenAIのコンフィグ関係の設定

ここでは、AzureのCognitiveServiceから確認できるAPIキー、APIのエンドポイント、デプロイ名称など自分の環境のものを設定します。

```python
openai.api_key = ""  ## Azureから確認できるAPI Key
openai.api_base =  ""  ## Azureから確認できる APIのエンドポイント
openai.api_type = "azure"
openai.api_version = "" ## API バージョン名

_deployment_name = "" ## Azureでデプロイされた名称
```

### 3. アプリのUI

ここからは、Streamlitを利用してアプリのUI部分と処理部分を同時に作成していきます！

### 3.1 タイトル設定

まずは肝心なアプリのタイトルからです！
今回はGPTに教えていただく、ということでGPT PAISENのタイトルにしました。

```python
st.title("HELLO GPT PAISEN!")
st.title("*"*30)
```


続けて、アプリの左のサイドバー部分を作成していきます。

### 3.2 サイドバー　1. CSVファイルの読み込み
CSVファイルの読み込み部分では、アップロードのコンポーネントを作成します。
- 読み込まれたら（if文最初）、read_csvでpandasのDataFrameで読み込みます。
- 読み込まれなかったら、(else文)、空のDataFrameを用意します。

### 3.3 サイドバー　2. ファイルの先頭3行の取得
全てを読み込んでGPTに入力したり、画面上に表示するとかなり非効率なので、今回は先頭3行までを利用します。
　　　
### 3.4 サイドバー　3. ターゲット列の名前の指定
データを読み込んだら、どの列名が予測対象なのかGPTに教えるために、ここでプルダウンの選択式にしています。
もしCSVファイルが読み込まれていたらファイルのカラム列を選択する、ファイルが読み込まれていないなら、選択不可能になります。

### 3.5 サイドバー　4. GPTのハイパーパラメータ設定

- 4.1では、GPTの出力の最大トークン数を指定します。最大とはいいつつも、あまり出すぎると料金も比例して増えていくので、いったん1000を最大にできるようにしました。　デフォルトは300です。
- 4.2では、temperature（温度）を設定します。ここでいう温度とは、出力のランダム性を示すもので、temperatureが高いほど、出力のたびによりバリエーションに富んだ文章が出力されます。　デフォルト値ではいったん0.8としました。
- 4.3では、GPTに与えるロールの役割を設定します。今回は、予測モデルを作成してほしいので、デフォルトで「data science expert」としています。

```python
with st.sidebar:

    ## 3.2 CSVファイルを読み込み
    st.markdown("# Give me CSV")
    _uploaded_file = st.file_uploader("")

    if _uploaded_file is not None:
        _df = pd.read_csv(_uploaded_file)
    else:
        _df = pd.DataFrame()

    ## 3.3 ファイルの先頭3行の取得
    _df_sample = _df.head(3)

    ## 3.4 ターゲット列の名前の指定
    st.markdown("# Give me target column")
    _target_col = st.selectbox('', _df_sample.columns)

    ## 3.5 GPTのハイパーパラメータ設定
    st.markdown('## GPT Config')
    
    ## 3.5 出力の最大トークン設定
    _max_tokens = st.number_input("max tokens", 10, 1000, 300)

    ## 3.5 出力のtemperature設定
    _temperature = st.slider('temperature', 0., 1., 0.8, step=0.001)
    
    ## 3.5 AIへのロール設定
    _system_role = st.text_area("AI Role  (this value is given as '''You are a VALUE.''')", value="data science expert")
```

### 3.6 プロンプト入力

ここではGPTで最も大切なプロンプト入力のコンポーネントを作成します。
とはいいつつも、今回は予測モデルを作ってほしいので、デフォルトにある程度のテンプレを埋め込もうと思います。

ここで、サイドバー3の入力したカラム名を埋め込むようなコードにしています。これによって、なるべくユーザーには画面をポチっとするだけで操作してもらえるようにしました。

st.markdown(_df_sample.to_markdown()) では、入力したCSVファイルを表示するようにしています。


```python
_text_input = st.text_area("your prompt", value=f"tell me favorable algorithm to predict '''{_target_col}''' using below sample table and write python code")

st.markdown(_df_sample.to_markdown())

st.write('\n\n\n')
```

### 3.7 ボタンクリックでGPTへ入力・出力を表示

ここまで準備できたら、あとはGPTのAPIをコールするだけです！

今回はボタンを推したら、APIを呼ぶようにしました。（if st.button(): の構造）

### 3.8 入力プロンプト整形
GPTに入力するプロンプトを整形します。3.6の入力文章に加え、読み込んだCSVファイルの先頭をマークダウンに落とし込んで入力としてみました。

### 3.9 APIコール
openai.ChatCompletion.create()を利用しました。
- システムに演じてほしい対象を入力するために、{"role": "system", "content": f"You are a {_system_role}."}　で表現しました。
- 入力プロンプトは　{"role": "user", "content": _prompt}　で表現しました。
- トークン最大長や、温度もそのまま引数で渡しています。

### 3.10 GPTの出力結果の表示
GPTの結果を取り出し、markdownで表示します。



```python
## 3.7 ボタンクリックでGPTへ入力・出力を表示
if st.button("Please Tell Me,  GPT PAISEN !!!!"):
    
    ## 3.8 入力プロンプト整形
    _prompt = _text_input + '\n' + _df_sample.to_markdown()
    

    ## 3.9 APIコール
    response = openai.ChatCompletion.create(
        engine = _deployment_name,
        messages = [
            {"role": "system", "content": f"You are a {_system_role}."},
            {"role": "user", "content": _prompt},
        ],
        max_tokens = _max_tokens,
        temperature = _temperature,
    )
    
    ## 3.10 GPTの出力結果の表示
    _text_output = response["choices"][0]["message"]["content"]
    st.markdown("\n\n")
    st.markdown(f"[GPT Paisen]\n{_text_output}")
```


以上でコードは終了です！
約80行ほどのコードでGPT先輩にコードを教えてもらえるアプリができました！

Streamlitもそうですが、OpenAIのAPIもかなり簡単に利用できることが確認できました。
システムに組み込むなどすれば、さらに広い活用先が考えられそうです！

## 参照元

- [Azure OpenAI Service](https://azure.microsoft.com/ja-jp/products/cognitive-services/openai-service)
- [OpenAI API](https://openai.com/blog/openai-api)
- [クイック スタート: Azure OpenAI Service で ChatGPT (プレビュー) と GPT-4 (プレビュー) の使用を開始する](https://learn.microsoft.com/ja-jp/azure/cognitive-services/openai/chatgpt-quickstart?tabs=command-line&pivots=programming-language-python)
- [Streamlit](https://streamlit.io/)


## 仲間募集
NTTデータ テクノロジーコンサルティング事業本部 では、以下の職種を募集しています。
<details><summary>1. クラウド技術を活用したデータ分析プラットフォームの開発・構築(ITアーキテクト/クラウドエンジニア)</summary>
クラウド／プラットフォーム技術の知見に基づき、DWH、BI、ETL領域におけるソリューション開発を推進します。
https://enterprise-aiiot.nttdata.com/recruitment/career_sp/cloud_engineer
</details>
<details><summary>2. データサイエンス領域（データサイエンティスト／データアナリスト）</summary>
データ活用／情報処理／AI／BI／統計学などの情報科学を活用し、よりデータサイエンスの観点から、データ分析プロジェクトのリーダーとしてお客様のDX／デジタルサクセスを推進します。
https://enterprise-aiiot.nttdata.com/recruitment/career_sp/datascientist
</details>

## ソリューション紹介
<details><summary> Trusted Data Foundationについて</summary><div>
～データ資産を分析活用するための環境をオールインワンで提供するソリューション～
https://enterprise-aiiot.nttdata.com/tdf/
最新のクラウド技術を採用して弊社が独自に設計したリファレンスアーキテクチャ（Datalake+DWH+AI/BI）を顧客要件に合わせてカスタマイズして提供します。
可視化、機械学習、DeepLearningなどデータ資産を分析活用するための環境がオールインワンで用意されており、これまでとは別次元の量と質のデータを用いてアジリティ高くDX推進を実現できます。
</div></details>
<details><summary> NTTデータとInformaticaについて</summary><div>
データ連携や処理方式を専門領域として10年以上取り組んできたプロ集団であるNTTデータは、データマネジメント領域でグローバルでの高い評価を得ているInformatica社とパートナーシップを結び、サービス強化を推進しています。
https://enterprise-aiiot.nttdata.com/service/informatica
</div></details>
<details><summary> TDFⓇ-AM（Trusted Data Foundation - Analytics Managed Service）について</summary><div>
～データ活用基盤の段階的な拡張支援（Quick Start) と保守運用のマネジメント（Analytics Managed）をご提供することでお客様のDXを成功に導く、データ活用プラットフォームサービス～
https://enterprise-aiiot.nttdata.com/service/tdf/tdf_am
TDFⓇ-AMは、データ活用をQuickに始めることができ、データ活用の成熟度に応じて段階的に環境を拡張します。プラットフォームの保守運用はNTTデータが一括で実施し、お客様は成果創出に専念することが可能です。また、日々最新のテクノロジーをキャッチアップし、常に活用しやすい環境を提供します。なお、ご要望に応じて上流のコンサルティングフェーズからAI/BIなどのデータ活用支援に至るまで、End to Endで課題解決に向けて伴走することも可能です。
</div></details>