Spaces:
Runtime error
Runtime error
Update flask_app.py
Browse files- flask_app.py +47 -24
flask_app.py
CHANGED
|
@@ -109,28 +109,56 @@ import re
|
|
| 109 |
# return "I don't know."
|
| 110 |
|
| 111 |
# Function to perform model inference
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 112 |
def model_inference(retriever, question, llm):
|
|
|
|
|
|
|
|
|
|
|
|
|
| 113 |
# Retrieve relevant documents
|
| 114 |
-
retrieved_docs = retriever.invoke(question)
|
| 115 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 116 |
|
| 117 |
# Define prompt template
|
| 118 |
prompt = PromptTemplate(
|
| 119 |
input_variables=["context", "question"],
|
| 120 |
template="""\
|
| 121 |
-
You are a
|
| 122 |
-
|
| 123 |
-
|
| 124 |
-
|
| 125 |
-
|
| 126 |
-
|
|
|
|
| 127 |
|
| 128 |
Context:
|
| 129 |
{context}
|
| 130 |
-
|
| 131 |
Query:
|
| 132 |
{question}
|
| 133 |
-
|
| 134 |
Answer:
|
| 135 |
"""
|
| 136 |
)
|
|
@@ -140,26 +168,21 @@ def model_inference(retriever, question, llm):
|
|
| 140 |
RunnablePassthrough.assign(context=lambda _: context, question=lambda _: question)
|
| 141 |
| prompt
|
| 142 |
| llm
|
| 143 |
-
|
| 144 |
)
|
| 145 |
|
| 146 |
-
# Invoke the chain and
|
| 147 |
-
response = rag_chain.invoke({})
|
| 148 |
|
| 149 |
-
# Extract the
|
| 150 |
match = re.findall(r"Answer:\s*(.*)", response, re.DOTALL)
|
| 151 |
-
if match:
|
| 152 |
-
final_answer = "Answer:\n " + match[-1].strip() # Taking the last match
|
| 153 |
-
else:
|
| 154 |
-
final_answer = "Answer:\n No valid answer found."
|
| 155 |
|
| 156 |
-
#
|
| 157 |
-
references =
|
| 158 |
-
f"Source: {
|
| 159 |
-
|
| 160 |
-
|
| 161 |
|
| 162 |
-
# Return final structured output
|
| 163 |
return f"{final_answer}\nReferences: {references}"
|
| 164 |
|
| 165 |
# # Example usage:
|
|
|
|
| 109 |
# return "I don't know."
|
| 110 |
|
| 111 |
# Function to perform model inference
|
| 112 |
+
import re
|
| 113 |
+
from fuzzywuzzy import fuzz # For relevance matching
|
| 114 |
+
|
| 115 |
+
def is_context_relevant(context, question, threshold=40):
|
| 116 |
+
"""
|
| 117 |
+
Checks if the retrieved context is relevant to the question using fuzzy matching.
|
| 118 |
+
Returns True if relevant, False otherwise.
|
| 119 |
+
"""
|
| 120 |
+
context_snippet = " ".join(context.split()[:100]) # Use only first 100 words for efficiency
|
| 121 |
+
relevance_score = fuzz.partial_ratio(context_snippet.lower(), question.lower())
|
| 122 |
+
|
| 123 |
+
return relevance_score >= threshold # Only accept if score is above threshold
|
| 124 |
+
|
| 125 |
def model_inference(retriever, question, llm):
|
| 126 |
+
# Validate question: Reject if too short or empty
|
| 127 |
+
if not question.strip() or len(question.strip()) < 5:
|
| 128 |
+
return "Answer:\n The question is invalid or lacks sufficient detail."
|
| 129 |
+
|
| 130 |
# Retrieve relevant documents
|
| 131 |
+
retrieved_docs = retriever.invoke(question)
|
| 132 |
+
|
| 133 |
+
# If no relevant documents are found, reject the query
|
| 134 |
+
if not retrieved_docs:
|
| 135 |
+
return "Answer:\n The answer is not found in the context provided.\nReferences: No references found."
|
| 136 |
+
|
| 137 |
+
# Extract context
|
| 138 |
+
context = "\n\n".join([doc.page_content for doc in retrieved_docs]).strip()
|
| 139 |
+
|
| 140 |
+
# **New: Check if the retrieved context is relevant to the question**
|
| 141 |
+
if not is_context_relevant(context, question):
|
| 142 |
+
return "Answer:\n The answer is not found in the context provided.\nReferences: No references found."
|
| 143 |
|
| 144 |
# Define prompt template
|
| 145 |
prompt = PromptTemplate(
|
| 146 |
input_variables=["context", "question"],
|
| 147 |
template="""\
|
| 148 |
+
You are a highly accurate and reliable assistant. Follow these strict rules:
|
| 149 |
+
|
| 150 |
+
1. **Use Only the Provided Context** – Base your answer strictly on the given context. Do not infer or generate extra details.
|
| 151 |
+
2. **Reject Invalid or Unrelated Questions** – If the question does not relate to the context, respond with: "The answer is not found in the context provided."
|
| 152 |
+
3. **Ensure Context Relevance** – Answer only if the exact information exists in the context.
|
| 153 |
+
4. **No Hallucination** – Do not assume, summarize, or infer beyond what is explicitly stated.
|
| 154 |
+
5. **Concise and Relevant Answers** – Avoid redundancy. Provide only the most accurate response.
|
| 155 |
|
| 156 |
Context:
|
| 157 |
{context}
|
| 158 |
+
|
| 159 |
Query:
|
| 160 |
{question}
|
| 161 |
+
|
| 162 |
Answer:
|
| 163 |
"""
|
| 164 |
)
|
|
|
|
| 168 |
RunnablePassthrough.assign(context=lambda _: context, question=lambda _: question)
|
| 169 |
| prompt
|
| 170 |
| llm
|
|
|
|
| 171 |
)
|
| 172 |
|
| 173 |
+
# Invoke the chain and get the response
|
| 174 |
+
response = rag_chain.invoke({}).strip()
|
| 175 |
|
| 176 |
+
# Extract only the final "Answer:" section
|
| 177 |
match = re.findall(r"Answer:\s*(.*)", response, re.DOTALL)
|
| 178 |
+
final_answer = "Answer:\n " + match[-1].strip() if match else "Answer:\n The answer is not found in the context provided."
|
|
|
|
|
|
|
|
|
|
| 179 |
|
| 180 |
+
# Extract only the first relevant reference
|
| 181 |
+
references = (
|
| 182 |
+
f"Source: {retrieved_docs[0].metadata['source']}, Page: {retrieved_docs[0].metadata.get('page_label', 'Unknown')}"
|
| 183 |
+
if retrieved_docs else "No references found."
|
| 184 |
+
)
|
| 185 |
|
|
|
|
| 186 |
return f"{final_answer}\nReferences: {references}"
|
| 187 |
|
| 188 |
# # Example usage:
|