Files changed (1) hide show
  1. final.py +432 -0
final.py ADDED
@@ -0,0 +1,432 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # -*- coding: utf-8 -*-
2
+ """Final.ipynb
3
+
4
+ Automatically generated by Colaboratory.
5
+
6
+ Original file is located at
7
+ https://colab.research.google.com/drive/1dpJeWTX6Urby-ciMSyjUWqxPjkBotFpI
8
+ """
9
+
10
+ # Commented out IPython magic to ensure Python compatibility.
11
+ # %pip install --upgrade --quiet langchain-text-splitters tiktoken
12
+
13
+ # Commented out IPython magic to ensure Python compatibility.
14
+ # %pip install -qU langchain-text-splitters
15
+
16
+ !pip install langchainhub
17
+
18
+ !pip install -qU faiss_cpu pandas
19
+
20
+ # Commented out IPython magic to ensure Python compatibility.
21
+ # %pip install --upgrade --quiet tavily-python
22
+
23
+ # %pip install -qU langchain langchain-openai langchain-community langchain-experimental pandas
24
+
25
+ import getpass
26
+ import requests
27
+ import os
28
+
29
+ os.environ["OPENAI_API_KEY"] = getpass.getpass()
30
+
31
+ from langchain import hub
32
+ from langchain.agents import AgentExecutor, create_openai_tools_agent
33
+ from langchain_community.tools.tavily_search import TavilySearchResults
34
+ from langchain_openai import ChatOpenAI
35
+
36
+ !wget https://raw.githubusercontent.com/monaejam/DataSource/main/Main.csv
37
+
38
+ !wget https://raw.githubusercontent.com/monaejam/DataSource/main/combined_extracted.json
39
+
40
+ import pandas as pd
41
+
42
+ lf = pd.read_csv("Main.csv")
43
+ print(lf.shape)
44
+ print(lf.columns.tolist())
45
+
46
+ from langchain_community.utilities import SQLDatabase
47
+ from sqlalchemy import create_engine, MetaData, Table
48
+
49
+ engine = create_engine("sqlite:///TrustWhole1.db")
50
+ lf.to_sql("MainTable", engine, index=True)
51
+ metadata = MetaData()
52
+ #main_table = Table('MainTable', metadata, autoload_with=engine)
53
+
54
+ db = SQLDatabase(engine=engine)
55
+
56
+ #from sqlalchemy import create_engine, MetaData, Table
57
+
58
+ # Create an engine instance
59
+ #engine = create_engine("sqlite:///TrustWhole1.db")
60
+
61
+ # Instantiate a MetaData object
62
+ #metadata = MetaData()
63
+
64
+ # Reflect the table from the database
65
+ #maindata_table = Table('MainData', metadata, autoload_with=engine)
66
+
67
+ # Drop the table
68
+ #maindata_table.drop(engine)
69
+
70
+ # Alternatively, if you want to drop the table without reflecting it:
71
+ #engine.execute("DROP TABLE IF EXISTS MainData")
72
+
73
+ print(db.dialect)
74
+ print(db.get_usable_table_names())
75
+
76
+ """To optimize agent performance, we can provide a custom prompt with domain-specific knowledge. In this case we’ll create a few shot prompt with an example selector, that will dynamically build the few shot prompt based on the user input. This will help the model make better queries by inserting relevant queries in the prompt that the model can use as reference.Now we can create an example selector. This will take the actual user input and select some number of examples to add to our few-shot prompt. We’ll use a SemanticSimilarityExampleSelector, which will perform a semantic search using the embeddings and vector store we configure to find the examples most similar to our input:Now we can create our FewShotPromptTemplate, which takes our example selector, an example prompt for formatting each example, and a string prefix and suffix to put before and after our formatted examples:Since our underlying agent is an OpenAI tools agent, which uses OpenAI function calling, our full prompt should be a chat prompt with a human message template and an agent_scratchpad MessagesPlaceholder. The few-shot prompt will be used for our system message:"""
77
+
78
+ examples = [
79
+ {"input": "List all companies.", "query": "SELECT Distinct companyName FROM MainTable;"},
80
+ {
81
+ "input": "Find Average Rating for Avant Company'.",
82
+ "query": "SELECT AVG(Rating) as Average_rating FROM MainTable WHERE companyName = 'Avant';",
83
+ },
84
+ {
85
+ "input": "find the average rating over the past 3 months for rise credit company.",
86
+ "query": "SELECT AVG(Rating) AS AverageRating FROM MainTable WHERE companyName = 'Risecredit 'AND `Date of Review` >= DATE_SUB(CURDATE(), INTERVAL 3 MONTH);",
87
+ },
88
+ {
89
+ "input": "find the average rating for Avant company based on BBB.",
90
+ "query": "SELECT AVG(Rating) AS AverageRating FROM MainTable WHERE companyName = 'Risecredit 'AND source ='BBB';",
91
+ },
92
+ ]
93
+
94
+ #SemanticSimilarityExampleSelector,
95
+ #which will perform a semantic search using the embeddings and vector store configured to find the examples most similar to the input
96
+ from langchain_community.vectorstores import FAISS
97
+ from langchain_core.example_selectors import SemanticSimilarityExampleSelector
98
+ from langchain_openai import OpenAIEmbeddings
99
+
100
+ example_selector = SemanticSimilarityExampleSelector.from_examples(
101
+ examples,
102
+ OpenAIEmbeddings(),
103
+ FAISS,
104
+ k=5,
105
+ input_keys=["input"],
106
+ )
107
+
108
+ #FewShotPromptTemplate
109
+ from langchain_core.prompts import (
110
+ ChatPromptTemplate,
111
+ FewShotPromptTemplate,
112
+ MessagesPlaceholder,
113
+ PromptTemplate,
114
+ SystemMessagePromptTemplate,
115
+ MessagesPlaceholder,
116
+ )
117
+ from langchain.memory import ConversationBufferMemory
118
+
119
+
120
+ system_prefix = """You are an agent designed to interact with a SQL database.
121
+ Given an input question, create a syntactically correct {dialect} query to run, then look at the results of the query and return the answer.
122
+ Unless the user specifies a specific number of examples they wish to obtain, always limit your query to at most {top_k} results.
123
+ You can order the results by a relevant column to return the most interesting examples in the database.
124
+ Never query for all the columns from a specific table, only ask for the relevant columns given the question.
125
+ You have access to tools for interacting with the database.
126
+ Only use the given tools. Only use the information returned by the tools to construct your final answer.
127
+ You MUST double check your query before executing it. If you get an error while executing a query, rewrite the query and try again.
128
+
129
+ DO NOT make any DML statements (INSERT, UPDATE, DELETE, DROP etc.) to the database.
130
+
131
+ If the question does not seem related to the database, just return "I don't know" as the answer.
132
+
133
+ Here are some examples of user inputs and their corresponding SQL queries:"""
134
+
135
+ few_shot_prompt = FewShotPromptTemplate(
136
+ example_selector=example_selector,
137
+ example_prompt=PromptTemplate.from_template(
138
+ "User input: {input}\nSQL query: {query}"
139
+ ),
140
+ input_variables=["input", "dialect", "top_k","history"],
141
+ prefix=system_prefix,
142
+ suffix="",
143
+ )
144
+ conversational_memory = ConversationBufferMemory(
145
+ memory_key='history',
146
+ return_messages=False
147
+ )
148
+
149
+ #full prompt should be a chat prompt with a human message template and an agent_scratchpad MessagesPlaceholder.
150
+ full_prompt = ChatPromptTemplate.from_messages(
151
+ [
152
+ SystemMessagePromptTemplate(prompt=few_shot_prompt),
153
+ ("human", "{input}"),
154
+ MessagesPlaceholder("agent_scratchpad"),
155
+
156
+ ]
157
+ )
158
+
159
+ from langchain_community.agent_toolkits import create_sql_agent
160
+ from langchain_openai import ChatOpenAI
161
+ from langchain.agents.agent_toolkits import SQLDatabaseToolkit
162
+ llm = ChatOpenAI(model="gpt-3.5-turbo", temperature=0)
163
+
164
+
165
+ toolkit_1 = SQLDatabaseToolkit(db=db, llm=llm)
166
+
167
+ agent_executor = create_sql_agent(llm, toolkit=toolkit_1, agent_type="openai-tools", verbose=True,prompt=full_prompt,agent_executor_kwargs={'memory': conversational_memory})
168
+
169
+ agent_executor.invoke({"input": "find the average rating for Avant company based on BBB.?"})
170
+
171
+ # Example formatted prompt
172
+ #prompt_val = full_prompt.invoke(
173
+ #{
174
+ #"input": "How many companies are there",
175
+ #"top_k": 5,
176
+ #"dialect": "SQLite",
177
+ #"agent_scratchpad": [],
178
+ #}
179
+ #)
180
+ #print(prompt_val.to_string())
181
+
182
+ #import json
183
+
184
+ # Opening JSON file
185
+ #g = open('AvantReview.json')
186
+
187
+ # returns JSON object as
188
+ # a dictionary
189
+ #data = json.load(g)
190
+
191
+ from google.colab import drive
192
+ drive.mount('/content/drive')
193
+
194
+ #import json
195
+
196
+ # Function to extract required fields from a single JSON file
197
+ #def extract_required_fields(file_path):
198
+ #with open(file_path, 'r') as file:
199
+ #data = json.load(file)
200
+ #extracted_data = [
201
+ #{'companyName': item['companyName'], 'reviewTitle': item['reviewTitle'], 'reviewDescription': item['reviewDescription']}
202
+ #for item in data
203
+ #]
204
+ #return extracted_data
205
+
206
+ # Paths to your JSON files
207
+ #file_paths = ['/content/drive/My Drive/database/AvantReview.json', '/content/drive/My Drive/database/RiseReview.json', '/content/drive/My Drive/database/OneMainReview.json']
208
+
209
+ # Extract and combine the data from all files
210
+ #combined_data = []
211
+ #for path in file_paths:
212
+ #combined_data.extend(extract_required_fields(path))
213
+
214
+ # Now combined_data contains the merged extracted data
215
+ # Write the combined data to a new JSON file
216
+ #with open('combined_extracted.json', 'w') as file:
217
+ #json.dump(combined_data, file, indent=4)
218
+
219
+ # The combined_extracted.json file now contains the merged extracted data from all files
220
+
221
+ #with open('/content/drive/My Drive/database/combined_extracted.json', 'w') as file:
222
+ #json.dump(combined_data, file, indent=4)
223
+
224
+ #load json
225
+ import requests
226
+ import json
227
+ !pip install jq
228
+
229
+ with open('combined_extracted.json', 'r') as file:
230
+ data = json.load(file)
231
+
232
+ #jq_schema = '.[] | {companyName, reviewTitle, reviewDescription}'
233
+
234
+ #loader = JSONLoader(
235
+ #file_path='/content/drive/My Drive/database/combined_extracted.json',
236
+ #jq_schema=jq_schema,
237
+ #text_content=False)
238
+
239
+ #data = loader.load()
240
+
241
+ #from langchain_community.document_loaders import JSONLoader
242
+
243
+
244
+ #import json
245
+ #from pathlib import Path
246
+ #from pprint import pprint
247
+
248
+
249
+ #file_path='/content/drive/My Drive/database/combined_extracted.json'
250
+ #data = json.loads(Path(file_path).read_text())
251
+
252
+ data = requests.get("https://raw.githubusercontent.com/monaejam/DataSource/main/combined_extracted.json").json()
253
+
254
+ #split them
255
+ texts_to_split = ""
256
+ for item in data:
257
+ texts_to_split += item['companyName'] + "\n" + item['reviewTitle'] + "\n" + item['reviewDescription'] + "\n\n"
258
+
259
+ texts_to_split
260
+
261
+ from langchain.text_splitter import CharacterTextSplitter
262
+ text_splitter=CharacterTextSplitter(
263
+ separator="\n",
264
+ chunk_size=2500,
265
+ chunk_overlap=100,
266
+ )
267
+ texts = text_splitter.split_text(texts_to_split)
268
+
269
+ # how many chain you decide to use QA or conversationalretrievalchain
270
+ #from langchain import hub
271
+ #from langchain.chains import (
272
+ # StuffDocumentsChain, LLMChain, ConversationalRetrievalChain
273
+ #)
274
+ from langchain_openai import OpenAIEmbeddings
275
+
276
+ embeddings = OpenAIEmbeddings(model="text-embedding-ada-002")
277
+ vectorstore = FAISS.from_texts(texts, embeddings)
278
+
279
+ #qa_chain = ConversationalRetrievalChain.from_llm(
280
+ # ChatOpenAI(),
281
+ # vectorstore.as_retriever(search_kwargs={'k': 3}),
282
+ # return_source_documents=True
283
+ #)
284
+
285
+ retriever = vectorstore.as_retriever()
286
+
287
+ from langchain import hub
288
+
289
+ prompt = hub.pull("hwchase17/openai-tools-agent")
290
+ prompt.messages
291
+
292
+ from langchain.prompts import ChatPromptTemplate
293
+
294
+ template = """Answer the question based only on the following context. If you cannot answer the question with the context, please respond with 'I don't know':
295
+
296
+ Context:
297
+ {context}
298
+
299
+ Question:
300
+ {question}
301
+ """
302
+
303
+ prompt = ChatPromptTemplate.from_template(template)
304
+
305
+ from langchain.chains import RetrievalQA
306
+ from langchain.chat_models import ChatOpenAI
307
+ qa = RetrievalQA.from_chain_type(llm=ChatOpenAI(), chain_type="stuff", retriever =vectorstore.as_retriever())
308
+
309
+ query = "can you list the title of the good reviews you have on OneMain Financial?"
310
+ qa.run(query)
311
+
312
+ from langchain.tools.retriever import create_retriever_tool
313
+
314
+ tool_retiv = create_retriever_tool(
315
+ retriever,
316
+ name="search_reviews",
317
+ description="search and returns reviews for the companies along with their title.if there is aggregation operation or if question was about numbers you do not need to use this tool",
318
+ )
319
+
320
+
321
+
322
+ toolkit_1.get_tools()[0].description="search and returns reviews for the companies along with their title."
323
+
324
+ toolkit_1.get_tools()[0]
325
+
326
+
327
+
328
+ toolkit_1 = SQLDatabaseToolkit(db=db, llm=llm)
329
+
330
+ #from langchain.agents import Tool
331
+
332
+ #tools_re = [
333
+ #Tool(
334
+ #name='search_reviews',
335
+ #func=qa.run,
336
+ #description=(
337
+ #'use this tool when answering general knowledge queries to Searche and returns reviews for the companies along with their title.'
338
+ #)
339
+ #)
340
+ #]
341
+ #tools=[tools_re]
342
+
343
+ [tool_retiv] +
344
+
345
+ """Integration
346
+
347
+ """
348
+
349
+ toolkit_1 = SQLDatabaseToolkit(db=db, llm=llm)
350
+ tools_final = [tool_retiv] +toolkit_1.get_tools()
351
+
352
+ from langchain_core.prompts import ChatPromptTemplate, MessagesPlaceholder
353
+
354
+ prompt = ChatPromptTemplate.from_messages(
355
+ [
356
+ (
357
+ "system",
358
+ "You are very powerful assistant, but don't know current events",
359
+ ),
360
+ ("user", "{input}"),
361
+ MessagesPlaceholder(variable_name="agent_scratchpad"),
362
+ ]
363
+ )
364
+
365
+ #llm_final=llm.bind_tools(tools_final)
366
+
367
+ from langchain.agents import AgentExecutor, create_openai_tools_agent
368
+
369
+ agent = create_openai_tools_agent(llm, tools_final, prompt)
370
+
371
+ agent_executor = AgentExecutor(agent=agent, tools=tools_final, verbose=True)
372
+
373
+ agent_executor.invoke({"input": "can you give me some bad reviews for Avant company.?"})
374
+
375
+ agent_executor.invoke({"input": "find the average rating for Avant company based on BBB.?"})
376
+
377
+ #!pip install reportlab
378
+
379
+ #from reportlab.lib.pagesizes import letter
380
+ #from reportlab.pdfgen import canvas
381
+ #from reportlab.lib.styles import getSampleStyleSheet
382
+ #from reportlab.platypus import Paragraph
383
+ #from reportlab.lib.units import inch
384
+
385
+ #def json_to_pdf(data, filename):
386
+ # c = canvas.Canvas(filename, pagesize=letter)
387
+ # styles = getSampleStyleSheet()
388
+ # width, height = letter
389
+ # margin = inch * 0.5
390
+ # y_position = height - margin # Start position on the page
391
+
392
+ # def add_page():
393
+ # """Adds a new page and resets y_position."""
394
+ # nonlocal y_position
395
+ # c.showPage() # Add a new page
396
+ # y_position = height - margin # Reset y_position for the new page
397
+
398
+ # for item in data:
399
+ # for field in ['companyName', 'reviewTitle', 'reviewDescription']:
400
+ # # Each Paragraph represents a section of text
401
+ # text = f"{field.replace('companyName', 'Company Name').replace('reviewTitle', 'Review Title').replace('reviewDescription', 'Review Description')}: {item[field]}"
402
+ # p = Paragraph(text, styles['Normal'])
403
+
404
+ # Wrap the text according to the width of the page
405
+ # w, h = p.wrap(width - 2*margin, y_position)
406
+
407
+ # Check if the text block fits in the remaining page space
408
+ # if y_position - h < margin: # If not enough space, add a new page
409
+ # add_page()
410
+
411
+ # p.drawOn(c, margin, y_position - h)
412
+ # y_position -= (h + 0.1 * inch) # Move to the next block position
413
+
414
+ # Check space after drawing each field, add page if next block might not fit
415
+ # if y_position < margin + inch: # Assume next block needs at least 1 inch
416
+ # add_page()
417
+
418
+ # c.save()
419
+
420
+ # Load your JSON data
421
+ #import json
422
+
423
+ #json_file_path = '/content/drive/My Drive/database/combined_extracted.json'
424
+ #with open(json_file_path, 'r') as file:
425
+ # data = json.load(file)
426
+
427
+ # Generate PDF - Ensure the path is where you want to save on Google Drive
428
+ #output_pdf_path = '/content/drive/My Drive/database/output.pdf'
429
+ #json_to_pdf(data, output_pdf_path)
430
+
431
+ #from google.colab import files
432
+ #files.download('output.pdf')