naotakigawa commited on
Commit
0a9b238
·
1 Parent(s): d153ab3

Upload 3 files

Browse files
Files changed (3) hide show
  1. app.py +1 -1
  2. common.py +61 -63
  3. pages/ChatbotWebRead.py +62 -13
app.py CHANGED
@@ -150,7 +150,7 @@ if st.session_state.login_token:
150
  - **ChatbotWebRead**
151
  入力したURLのサイトの情報に関して、GenerativeAIが回答します。
152
  スクレイピングが禁止されているサイトは入力しないでください。
153
- ImportAllFileの内容は登録されていません。
154
 
155
  - **ImportAllFile**
156
  テキストファイル,mdファイル,Excel,PDF,PowerPoint,Wordをインポートできます。
 
150
  - **ChatbotWebRead**
151
  入力したURLのサイトの情報に関して、GenerativeAIが回答します。
152
  スクレイピングが禁止されているサイトは入力しないでください。
153
+ ImportAllFileの内容は登録されていません。
154
 
155
  - **ImportAllFile**
156
  テキストファイル,mdファイル,Excel,PDF,PowerPoint,Wordをインポートできます。
common.py CHANGED
@@ -9,7 +9,9 @@ from streamlit import runtime
9
  from streamlit.runtime.scriptrunner import get_script_run_ctx
10
  from streamlit.web.server.websocket_headers import _get_websocket_headers
11
  from llama_index import SimpleDirectoryReader
12
- from llama_index import Prompt
 
 
13
  from llama_index.chat_engine import CondenseQuestionChatEngine;
14
  from llama_index.response_synthesizers import get_response_synthesizer
15
  from llama_index import ServiceContext, SimpleDirectoryReader
@@ -20,6 +22,8 @@ from llama_index.response_synthesizers import get_response_synthesizer
20
  from llama_index.callbacks import CallbackManager
21
  from llama_index.llms import OpenAI
22
  from log import logger
 
 
23
 
24
  # 接続元制御
25
  ALLOW_IP_ADDRESS = os.environ["ALLOW_IP_ADDRESS"]
@@ -78,25 +82,72 @@ text_splitter = TokenTextSplitter(separator="。", chunk_size=1500
78
  , chunk_overlap=DEFAULT_CHUNK_OVERLAP
79
  , tokenizer=tiktoken.encoding_for_model("gpt-3.5-turbo").encode)
80
  node_parser = SimpleNodeParser(text_splitter=text_splitter)
81
- custom_prompt = Prompt("""\
82
  以下はこれまでの会話履歴と、ドキュメントを検索して回答する必要がある、ユーザーからの会話文です。
83
  会話と新しい会話文に基づいて、検索クエリを作成します。
84
- 挨拶された場合、挨拶を返してください。
85
- 答えを知らない場合は、「わかりません」と回答してください。
86
- 全ての回答は日本語で行ってください。
87
- 会話履歴:
88
  {chat_history}
89
- 新しい会話文:
90
  {question}
91
- Search query:
92
  """)
93
 
94
- chat_history = []
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
95
 
96
  def setChatEngine():
97
  callback_manager = CallbackManager([st.session_state.llama_debug_handler])
98
  service_context = ServiceContext.from_defaults(llm=llm,node_parser=node_parser,callback_manager=callback_manager)
99
- response_synthesizer = get_response_synthesizer(response_mode='refine')
 
 
 
 
100
  st.session_state.query_engine = st.session_state.index.as_query_engine(
101
  response_synthesizer=response_synthesizer,
102
  service_context=service_context,
@@ -104,58 +155,5 @@ def setChatEngine():
104
  st.session_state.chat_engine = CondenseQuestionChatEngine.from_defaults(
105
  query_engine=st.session_state.query_engine,
106
  condense_question_prompt=custom_prompt,
107
- chat_history=chat_history,
108
  verbose=True
109
  )
110
-
111
- # chat mode reacの記述
112
- # from langchain.prompts.chat import (
113
- # ChatPromptTemplate,
114
- # HumanMessagePromptTemplate,
115
- # SystemMessagePromptTemplate,
116
- # )
117
- # from llama_index.prompts.prompts import RefinePrompt, QuestionAnswerPrompt
118
- # from llama_index.prompts import Prompt
119
- # chat_text_qa_msgs = [
120
- # SystemMessagePromptTemplate.from_template(
121
- # "文脈が役に立たない場合でも、必ず日本語で質問に答えてください。"
122
- # ),
123
- # HumanMessagePromptTemplate.from_template(
124
- # "以下に、コンテキスト情報を提供します。 \n"
125
- # "---------------------\n"
126
- # "{context_str}"
127
- # "\n---------------------\n"
128
- # "回答には以下を含めてください。\n"
129
- # "・最初に問い合わせへのお礼してください\n"
130
- # "・回答には出典のドキュメント名を含めるようにしてください。\n"
131
- # "・質問内容を要約してください\n"
132
- # "・最後に不明な点がないか確認してください \n"
133
- # "この情報を踏まえて、次の質問に回答してください: {query_str}\n"
134
- # "答えを知らない場合は、「わからない」と回答してください。また、必ず日本語で回答してください。"
135
- # ),
136
- # ]
137
- # REFINE_PROMPT = ("元の質問は次のとおりです: {query_str} \n"
138
- # "既存の回答を提供しました: {existing_answer} \n"
139
- # "既存の答えを洗練する機会があります \n"
140
- # "(必要な場合のみ)以下にコンテキストを追加します。 \n"
141
- # "------------\n"
142
- # "{context_msg}\n"
143
- # "------------\n"
144
- # "新しいコンテキストを考慮して、元の答えをより良く洗練して質問に答えてください。\n"
145
- # "回答には出典のドキュメント名を含めるようにしてください。\n"
146
- # "コンテキストが役に立たない場合は、元の回答と同じものを返します。"
147
- # "どのような場合でも、返答は日本語で行います。")
148
- # refine_prompt = RefinePrompt(REFINE_PROMPT)
149
-
150
- # def setChatEngine():
151
- # callback_manager = CallbackManager([st.session_state.llama_debug_handler])
152
- # service_context = ServiceContext.from_defaults(node_parser=node_parser,callback_manager=callback_manager)
153
- # response_synthesizer = get_response_synthesizer(response_mode='refine')
154
- # st.session_state.chat_engine = st.session_state.index.as_chat_engine(
155
- # response_synthesizer=response_synthesizer,
156
- # service_context=service_context,
157
- # chat_mode="condense_question",
158
- # text_qa_template= Prompt.from_langchain_prompt(ChatPromptTemplate.from_messages(chat_text_qa_msgs)),
159
- # refine_template=refine_prompt,
160
- # verbose=True
161
- # )
 
9
  from streamlit.runtime.scriptrunner import get_script_run_ctx
10
  from streamlit.web.server.websocket_headers import _get_websocket_headers
11
  from llama_index import SimpleDirectoryReader
12
+ # from llama_index import Prompt
13
+ from llama_index.prompts.base import PromptTemplate
14
+
15
  from llama_index.chat_engine import CondenseQuestionChatEngine;
16
  from llama_index.response_synthesizers import get_response_synthesizer
17
  from llama_index import ServiceContext, SimpleDirectoryReader
 
22
  from llama_index.callbacks import CallbackManager
23
  from llama_index.llms import OpenAI
24
  from log import logger
25
+ from llama_index.llms.base import ChatMessage, MessageRole
26
+ from llama_index.prompts.base import ChatPromptTemplate
27
 
28
  # 接続元制御
29
  ALLOW_IP_ADDRESS = os.environ["ALLOW_IP_ADDRESS"]
 
82
  , chunk_overlap=DEFAULT_CHUNK_OVERLAP
83
  , tokenizer=tiktoken.encoding_for_model("gpt-3.5-turbo").encode)
84
  node_parser = SimpleNodeParser(text_splitter=text_splitter)
85
+ custom_prompt = PromptTemplate("""\
86
  以下はこれまでの会話履歴と、ドキュメントを検索して回答する必要がある、ユーザーからの会話文です。
87
  会話と新しい会話文に基づいて、検索クエリを作成します。
88
+ <Chat History>
 
 
 
89
  {chat_history}
90
+ <Follow Up Message>
91
  {question}
92
+ <Standalone question>
93
  """)
94
 
95
+ TEXT_QA_SYSTEM_PROMPT = ChatMessage(
96
+ content=(
97
+ "あなたは世界中で信頼されているQAシステムです。\n"
98
+ "事前知識ではなく、常に提供されたコンテキスト情報を使用してクエリに回答してください。\n"
99
+ "従うべきいくつかのルール:\n"
100
+ "1. 回答内で指定されたコンテキストを直接参照しないでください。\n"
101
+ "2. 「コンテキストに基づいて、...」や「コンテキスト情報は...」、またはそれに類するような記述は避けてください。"
102
+ ),
103
+ role=MessageRole.SYSTEM,
104
+ )
105
+
106
+ # QAプロンプトテンプレートメッセージ
107
+ TEXT_QA_PROMPT_TMPL_MSGS = [
108
+ TEXT_QA_SYSTEM_PROMPT,
109
+ ChatMessage(
110
+ content=(
111
+ "コンテキスト情報は以下のとおりです。\n"
112
+ "---------------------\n"
113
+ "{context_str}\n"
114
+ "---------------------\n"
115
+ "事前知識ではなくコンテキスト情報を考慮して、クエリに答えます。\n"
116
+ "Query: {query_str}\n"
117
+ "Answer: "
118
+ ),
119
+ role=MessageRole.USER,
120
+ ),
121
+ ]
122
+ CHAT_TEXT_QA_PROMPT = ChatPromptTemplate(message_templates=TEXT_QA_PROMPT_TMPL_MSGS)
123
+
124
+ CHAT_REFINE_PROMPT_TMPL_MSGS = [
125
+ ChatMessage(
126
+ content=(
127
+ "あなたは、既存の回答を改良する際に2つのモードで厳密に動作するQAシステムのエキスパートです。\n"
128
+ "1. 新しいコンテキストを使用して元の回答を**書き直す**。\n"
129
+ "2. 新しいコンテキストが役に立たない場合は、元の回答を**繰り返す**。\n"
130
+ "回答内で元の回答やコンテキストを直接参照しないでください。\n"
131
+ "疑問がある場合は、元の答えを繰り返してください。"
132
+ "New Context: {context_msg}\n"
133
+ "Query: {query_str}\n"
134
+ "Original Answer: {existing_answer}\n"
135
+ "New Answer: "
136
+ ),
137
+ role=MessageRole.USER,
138
+ )
139
+ ]
140
+ # チャットRefineプロンプト
141
+ CHAT_REFINE_PROMPT = ChatPromptTemplate(message_templates=CHAT_REFINE_PROMPT_TMPL_MSGS)
142
 
143
  def setChatEngine():
144
  callback_manager = CallbackManager([st.session_state.llama_debug_handler])
145
  service_context = ServiceContext.from_defaults(llm=llm,node_parser=node_parser,callback_manager=callback_manager)
146
+ response_synthesizer = get_response_synthesizer(
147
+ response_mode='refine',
148
+ text_qa_template= CHAT_TEXT_QA_PROMPT,
149
+ refine_template=CHAT_REFINE_PROMPT,
150
+ )
151
  st.session_state.query_engine = st.session_state.index.as_query_engine(
152
  response_synthesizer=response_synthesizer,
153
  service_context=service_context,
 
155
  st.session_state.chat_engine = CondenseQuestionChatEngine.from_defaults(
156
  query_engine=st.session_state.query_engine,
157
  condense_question_prompt=custom_prompt,
 
158
  verbose=True
159
  )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
pages/ChatbotWebRead.py CHANGED
@@ -10,28 +10,74 @@ from llama_index.langchain_helpers.text_splitter import TokenTextSplitter
10
  from llama_index.constants import DEFAULT_CHUNK_OVERLAP
11
  from llama_index.response_synthesizers import get_response_synthesizer
12
  from llama_index import SimpleWebPageReader
13
-
 
 
14
  # from llama_index.prompts import Prompt
15
  from llama_index import Prompt
 
 
16
  import tiktoken
17
  import common
18
  langchain.verbose = True
19
 
20
- custom_prompt = Prompt("""\
21
  以下はこれまでの会話履歴と、ドキュメントを検索して回答する必要がある、ユーザーからの会話文です。
22
- 会話と新しい会話文に基づいて、検索クエリを作成します。回答は日本語で行います。
23
- 新しい会話文が挨拶の場合、挨拶を返してください。
24
- 新しい会話文が質問の場合、検索した結果の回答を返してください。
25
- 答えがわからない場合は正直にわからないと回答してください。
26
- 会話履歴:
27
  {chat_history}
28
- 新しい会話文:
29
  {question}
30
- Search query:
31
  """)
32
- chat_history = []
33
 
34
- from log import logger
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
35
 
36
  common.check_login()
37
 
@@ -59,7 +105,11 @@ if st.button("URL reading",use_container_width=True):
59
  )
60
  logger.info(webDocuments)
61
  webIndex = VectorStoreIndex.from_documents(webDocuments,service_context=service_context)
62
- response_synthesizer = get_response_synthesizer(response_mode='refine')
 
 
 
 
63
  st.session_state.webQuery_engine = webIndex.as_query_engine(
64
  response_synthesizer=response_synthesizer,
65
  service_context=service_context,
@@ -67,7 +117,6 @@ if st.button("URL reading",use_container_width=True):
67
  st.session_state.web_chat_engine = CondenseQuestionChatEngine.from_defaults(
68
  query_engine=st.session_state.webQuery_engine,
69
  condense_question_prompt=custom_prompt,
70
- chat_history=chat_history,
71
  verbose=True
72
  )
73
 
 
10
  from llama_index.constants import DEFAULT_CHUNK_OVERLAP
11
  from llama_index.response_synthesizers import get_response_synthesizer
12
  from llama_index import SimpleWebPageReader
13
+ from llama_index.llms.base import ChatMessage, MessageRole
14
+ from llama_index.prompts.base import ChatPromptTemplate
15
+ from llama_index.prompts.base import PromptTemplate
16
  # from llama_index.prompts import Prompt
17
  from llama_index import Prompt
18
+
19
+ from log import logger
20
  import tiktoken
21
  import common
22
  langchain.verbose = True
23
 
24
+ custom_prompt = PromptTemplate("""\
25
  以下はこれまでの会話履歴と、ドキュメントを検索して回答する必要がある、ユーザーからの会話文です。
26
+ 会話と新しい会話文に基づいて、検索クエリを作成します。
27
+ <Chat History>
 
 
 
28
  {chat_history}
29
+ <Follow Up Message>
30
  {question}
31
+ <Standalone question>
32
  """)
 
33
 
34
+ TEXT_QA_SYSTEM_PROMPT = ChatMessage(
35
+ content=(
36
+ "あなたは世界中で信頼されているQAシステムです。\n"
37
+ "事前知識ではなく、常に提供されたコンテキスト情報を使用してクエリに回答してください。\n"
38
+ "従うべきいくつかのルール:\n"
39
+ "1. 回答内で指定されたコンテキストを直接参照しないでください。\n"
40
+ "2. 「コンテキストに基づいて、...」や「コンテキスト情報は...」、またはそれに類するような記述は避けてください。"
41
+ ),
42
+ role=MessageRole.SYSTEM,
43
+ )
44
+
45
+ # QAプロンプトテンプレートメッセージ
46
+ TEXT_QA_PROMPT_TMPL_MSGS = [
47
+ TEXT_QA_SYSTEM_PROMPT,
48
+ ChatMessage(
49
+ content=(
50
+ "コンテキスト情報は以下のとおりです。\n"
51
+ "---------------------\n"
52
+ "{context_str}\n"
53
+ "---------------------\n"
54
+ "事前知識ではなくコンテキスト情報を考慮して、クエリに答えます。\n"
55
+ "Query: {query_str}\n"
56
+ "Answer: "
57
+ ),
58
+ role=MessageRole.USER,
59
+ ),
60
+ ]
61
+ CHAT_TEXT_QA_PROMPT = ChatPromptTemplate(message_templates=TEXT_QA_PROMPT_TMPL_MSGS)
62
+
63
+ CHAT_REFINE_PROMPT_TMPL_MSGS = [
64
+ ChatMessage(
65
+ content=(
66
+ "あなたは、既存の回答を改良する際に2つのモードで厳密に動作するQAシステムのエキスパートです。\n"
67
+ "1. 新しいコンテキストを使用して元の回答を**書き直す**。\n"
68
+ "2. 新しいコンテキストが役に立たない場合は、元の回答を**繰り返す**。\n"
69
+ "回答内で元の回答やコンテキストを直接参照しないでください。\n"
70
+ "疑問がある場合は、元の答えを繰り返してください。"
71
+ "New Context: {context_msg}\n"
72
+ "Query: {query_str}\n"
73
+ "Original Answer: {existing_answer}\n"
74
+ "New Answer: "
75
+ ),
76
+ role=MessageRole.USER,
77
+ )
78
+ ]
79
+ # チャットRefineプロンプト
80
+ CHAT_REFINE_PROMPT = ChatPromptTemplate(message_templates=CHAT_REFINE_PROMPT_TMPL_MSGS)
81
 
82
  common.check_login()
83
 
 
105
  )
106
  logger.info(webDocuments)
107
  webIndex = VectorStoreIndex.from_documents(webDocuments,service_context=service_context)
108
+ response_synthesizer = get_response_synthesizer(
109
+ response_mode='refine',
110
+ text_qa_template= CHAT_TEXT_QA_PROMPT,
111
+ refine_template=CHAT_REFINE_PROMPT,
112
+ )
113
  st.session_state.webQuery_engine = webIndex.as_query_engine(
114
  response_synthesizer=response_synthesizer,
115
  service_context=service_context,
 
117
  st.session_state.web_chat_engine = CondenseQuestionChatEngine.from_defaults(
118
  query_engine=st.session_state.webQuery_engine,
119
  condense_question_prompt=custom_prompt,
 
120
  verbose=True
121
  )
122