I am using langchain to create a chroma database to store pdf files through a Flask frontend. I am able to query the database and successfully retrieve data when the python file is ran from the command line.
I am however trying to use the the feature through Flask, and so far I can't get it to work. This is the class I am using to query the database:
from langchain.embeddings import OpenAIEmbeddings
from langchain.chains import RetrievalQA
from langchain.llms import OpenAI
from langchain.vectorstores import Chroma
class Chat_db:
def __init__(self):
persist_directory = 'chromadb'
embedding = OpenAIEmbeddings()
vectordb = Chroma(persist_directory=persist_directory, embedding_function=embedding)
retriever = vectordb.as_retriever(search_kwargs={"k": 2})
self.qa = RetrievalQA.from_chain_type(llm=OpenAI(), chain_type="stuff",
retriever= retriever)
def chat_over_documents(self, query):
result = self.qa({"query": query})
return result['result']
#if __name__ == "__main__":
# query = "Where was the US declaration of independence signed?"
# vector_db = Chat_db()
# result= vector_db.chat_over_documents(query)
# print(result)
If I uncomment the "main" section, I get the result I expect. If I run the query through 'app.py', I get the canned langchain result 'I'm sorry, don't know'. This is how I am calling it from 'app.py'
## app.py
...
chat_db = Chat_db()
@app.route('/message', methods=['POST'])
def message():
user_message = request.json['message']
if "document" in user_message.lower():
response = chat_db.chat_over_documents(user_message)
return jsonify({"message": response})
else:
response = assistant.chat_with_gpt(user_message)
return jsonify({"message": response})
I am not sure what I am doing incorrectly; any help is highly appreciated.
I have tried tracing data using the browser's developer tool and debugging in terminal. From the logs, my suspicion is that langchain is making two openai api calls even before Chroma db completes initializing.
Ultimately I went with a pure python and Chroma db solution, removing Langchain (Only from this part as I still use langchain in other parts of the project.)
The solution that worked:
import chromadb
from chromadb.config import Settings
class Chat_db:
def __init__(self, persist_directory="../data/Chromadb"):
self.persist_directory = persist_directory
self.client_settings = Settings(is_persistent= True, persist_directory= persist_directory, anonymized_telemetry=False)
self.persistent_client = chromadb.Client(settings= self.client_settings)
self.doc_collection = self.persistent_client.get_or_create_collection(name = "books")
#I thought I could just use self.persistent_client for querying but it did not work.
# had to create a PersistentClient to use for querying.
self.queryclient = chromadb.PersistentClient(path= persist_directory, settings= self.client_settings)
def chat_over_documents(self, collection_name, query, k = 5):
collection = self.queryclient.get_collection(name=collection_name)
results = collection.query(query_texts= query, n_results= k)
flat_results = [item for sublist in results['documents'] for item in sublist]
return flat_results
...
#Other methods for preprocessing and adding docs to the Chroma collection omitted
In app.py
...
document_handler = Chat_db()
...
@app.route('/message', methods=['POST'])
def message():
user_message = request.json['message']
if "/document" in user_message.lower():
keywords = assistant.preprocess_keywords(user_message)
vector_mgs = document_handler.chat_over_documents("books", keywords)
response = assistant.query_stored_documents(user_message, vector_mgs)
return jsonify({"message": response})
else:
response = assistant.chat_with_gpt(user_message)
return jsonify({"message": response})
Note: The assistant class uses langchain for chatting and other features. However, its query_stored_documents() method builds a prompt using system and user messages and query openai chat completion endpoint to get the desired result.