![見出し画像](https://assets.st-note.com/production/uploads/images/143010286/rectangle_large_type_2_5ed4a4794e705c5872c2b1f2a9a994cc.png?width=1200)
【Python】ChatGPTと外部データ連携!LlamaIndexでQ&Aアプリを作る。
Pythonの基礎を習得済みの方向けに、外部データを使うLlamaIndexの基本的な使い方を段階的に解説していきます。
Streamlitとは?
まずは、今回使用するStreamlitについて簡単に説明します。Streamlitは、WEBアプリを簡単に作れるPythonライブラリです。HTMLやCSSの知識がなくても、PythonコードだけでインタラクティブなWEBアプリを作成できます。
Streamlitの特徴
WEBアプリが簡単に作れる
HTML、CSSの知識が不要
デプロイが簡単
サーバー使用料が無料(Streamlit Community Cloud)
小さな組織やチームでのアプリ共有に最適
今回の内容
今回は、LlamaIndexを使って外部からデータを取り込み、ChatGPTと連携してQ&AができるWEBアプリを作成します。
具体的には、外部データとしてテキストファイルを読み込み、LlamaIndexを使ってインデックスを作成します。このインデックスをChatGPTと連携させることで、外部データの内容に基づいた回答を生成できるようにします。
ChatGPTのAPIキーを取得する
まず、ChatGPTのAPIキーを取得する手順を説明します。
動画の1:05から
今回使用するファイル
![](https://assets.st-note.com/img/1717540138767-YGQ9U7kks3.jpg?width=1200)
今回使用するファイルに関しては動画の4:37からご覧ください。
実装方法
必要なライブラリのインストール
まず、以下のライブラリをインストールする必要があります。
pip install streamlit llama-index
llama-indexの基本
import streamlit as st
from llama_index import VectorStoreIndex, SimpleDirectoryReader
# pip install streamlit llama-index
st.set_page_config(page_title='llamaindex')
st.title('llamaindex')
############ 基礎
st.markdown('### llamaindex 基礎')
# ローカルのテキストファイルを読み込む
documents = SimpleDirectoryReader('data').load_data() # フォルダを指定
_='''
VectorStoreIndex
・文章をベクトル表現に変換
・各Nodeに対応する埋め込みベクトルと共に順序付けせずに保持
・埋め込みベクトルを使用してNodeを抽出し、それぞれの出力を合成
※_=で画面表示を防ぐ。streamlitのmagic対策。
'''
index = VectorStoreIndex.from_documents(documents)
# 質問に対して、indexを使用して回答を生成
query_engine = index.as_query_engine()
message_text = '商品が届きません。'
response = query_engine.query(message_text)
with st.expander('response', expanded=False):
st.write(response)
message_user = st.chat_message('user')
message_user.write(message_text)
message = st.chat_message('assistant')
message.write(response.response)
上記のコードでは、まずSimpleDirectoryReaderを使って、ローカルのdataフォルダ内のテキストファイルを読み込み、documents変数に格納します。
次に、VectorStoreIndex.from_documents()を使って、documentsをベクトル表現に変換し、indexを作成します。このindexをas_query_engine()を使ってクエリエンジンに変換し、query_engine変数に格納します。
そして、st.text_input()でユーザーからの質問を受け付け、message_text変数に格納します。
ユーザーからの質問が入力されたら、query_engine.query()を使って、indexに基づいた回答を生成し、response変数に格納します。
最後に、st.chat_message()を使って、ユーザーとChatGPTのチャット画面を表示します。ユーザーからの質問は「user」として表示され、ChatGPTからの回答は「assistant」として表示されます。
index保存/読み込み
毎回、index化すると時間とコストがかかるため保存、読み込み機能を実装します。
import streamlit as st
from llama_index import VectorStoreIndex, SimpleDirectoryReader
import os.path
from llama_index import (
VectorStoreIndex,
SimpleDirectoryReader,
StorageContext,
load_index_from_storage,
)
# pip install streamlit llama-index
st.set_page_config(page_title='llamaindex')
st.title('llamaindex')
st.markdown('### llamaindex index保存/読み込み')
# storageフォルダの存在の確認
if not os.path.exists("./storage"):
# ローカルのテキストファイルを読み込む
documents = SimpleDirectoryReader('data').load_data() # フォルダを指定
_='''
VectorStoreIndex
・文章をベクトル表現に変換
・各Nodeに対応する埋め込みベクトルと共に順序付けせずに保持
・埋め込みベクトルを使用してNodeを抽出し、それぞれの出力を合成
※_=で画面表示を防ぐ。streamlitのmagic対策。
'''
index = VectorStoreIndex.from_documents(documents)
# "./storage"に保存
index.storage_context.persist()
else:
# 保存したデータの読み込み
storage_context = StorageContext.from_defaults(persist_dir="./storage")
# indexの読み込み
index = load_index_from_storage(storage_context)
# 質問に対して、indexを使用して回答を生成
query_engine = index.as_query_engine()
message_text = '商品が故障していました。'
response = query_engine.query(message_text)
with st.expander('response', expanded=False):
st.write(response)
message_user = st.chat_message('user')
message_user.write(message_text)
message = st.chat_message('assistant')
message.write(response.response)
上記のコードでは、indexの保存と読み込みを行う部分も含まれています。
if not os.path.exists("./storage")という条件分岐で、storageフォルダが存在しない場合は、SimpleDirectoryReaderでテキストファイルを読み込み、VectorStoreIndexを作成し、index.storage_context.persist()を使ってstorageフォルダにindexを保存します。
storageフォルダが存在する場合は、StorageContext.from_defaults()を使ってstorageフォルダからindexを読み込みます。
OpenAIの設定
import streamlit as st
from llama_index.llms import OpenAI
from llama_index import VectorStoreIndex, SimpleDirectoryReader
# pip install streamlit llama-index
st.set_page_config(page_title='llamaindex')
st.title('llamaindex')
st.markdown('### llamaindex LLMを使う')
response = OpenAI().complete("2018年のサッカーワールドカップのMVPは?")
st.write(response)
ServiceContext, RetrieverQueryEngineの設定
詳細設定する。
import streamlit as st
from llama_index import VectorStoreIndex, SimpleDirectoryReader
from llama_index.llms import OpenAI
from llama_index import (
VectorStoreIndex,
SimpleDirectoryReader,
ServiceContext,
get_response_synthesizer
)
from llama_index.retrievers import VectorIndexRetriever
from llama_index.query_engine import RetrieverQueryEngine
from llama_index.postprocessor import SimilarityPostprocessor
# pip install streamlit llama-index
st.set_page_config(page_title='llamaindex')
st.title('llamaindex')
st.markdown('### ServiceContext, RetrieverQueryEngineの設定')
llm = OpenAI(temperature=0.1, model="gpt-3.5-turbo")
service_context = ServiceContext.from_defaults(llm=llm) #llmやembed_modelなどの設定
documents = SimpleDirectoryReader("data").load_data()
index = VectorStoreIndex.from_documents(
documents, service_context=service_context
)
# retriever 設定 ベクトル空間モデルを使用して、類似性の高い文書を抽出
retriever = VectorIndexRetriever(
index=index,
similarity_top_k=2, # 上位何件を返すか
)
# response synthesizerのインスタンス化 検索結果を元に、自然言語で回答を生成するためのモデル
response_synthesizer = get_response_synthesizer()
# 類似性の高い文書から回答生成までの組み立て
query_engine = RetrieverQueryEngine(
retriever=retriever, # 類似性の高い文書を抽出
response_synthesizer=response_synthesizer, # 検索結果を元に、自然言語で回答を生成
node_postprocessors=[SimilarityPostprocessor(similarity_cutoff=0.7)],
# 抽出された文書を後処理 類似性が0.7以上の文書を抽出
)
# 質問の入力
question = st.chat_input('質問を入力してください')
if question:
response = query_engine.query(question)
with st.expander('response', expanded=False):
st.write(response)
message = st.chat_message("assistant")
message.write(response.response)
次に、VectorStoreIndex.from_documents()でindexを作成する際に、service_contextを指定することで、OpenAIを使ってindexを作成します。
また、index.as_retriever()を使って、類似性スコアの高い上位2件のノードを抽出するリトリーバーを作成し、retriever変数に格納します。
RetrieverQueryEngine()を使って、リトリーバーとレスポンスシンセサイザーを組み合わせてクエリエンジンを作成します。
まとめ
今回は、LlamaIndexを使ってChatGPTと外部データを連携させる方法を紹介しました。
LlamaIndexは、ChatGPTと外部データを連携させるための強力なツールです。ぜひ活用して、より高度なWEBアプリを作成してみてください。
よろしければサポートお願いします! いただいたサポートはクリエイターとしての活動費に使わせていただきます!