Spaces:
Build error
Build error
Update app.py
Browse files
app.py
CHANGED
|
@@ -1,4 +1,3 @@
|
|
| 1 |
-
|
| 2 |
import streamlit as st
|
| 3 |
import json
|
| 4 |
import os
|
|
@@ -46,16 +45,16 @@ database_schema = db.get_table_info()
|
|
| 46 |
#=================================Logging=====================================#
|
| 47 |
|
| 48 |
|
| 49 |
-
|
| 50 |
-
|
| 51 |
|
| 52 |
-
|
| 53 |
-
|
| 54 |
-
|
| 55 |
-
|
| 56 |
-
|
| 57 |
-
|
| 58 |
-
|
| 59 |
|
| 60 |
|
| 61 |
#=================================SQL_AGENT=====================================#
|
|
@@ -69,10 +68,8 @@ You must query only the columns that are needed to answer the question. Wrap eac
|
|
| 69 |
You have access to tools for interacting with the database.
|
| 70 |
Only use the given tools. Only use the information returned by the tools to construct your final answer.
|
| 71 |
You MUST double check your query before executing it. If you get an error while executing a query, rewrite the query and try again.
|
| 72 |
-
|
| 73 |
DO NOT make any DML statements (INSERT, UPDATE, DELETE, DROP etc.) to the database.
|
| 74 |
You are not allowed to make dummy data.
|
| 75 |
-
|
| 76 |
If the question does not seem related to the database, just return "I don't know" as the answer.
|
| 77 |
Before you execute the query, tell us why you are executing it and what you expect to find briefly.
|
| 78 |
Only use the following tables:
|
|
@@ -111,10 +108,8 @@ sqlite_agent = create_sql_agent(
|
|
| 111 |
def sql_tool(user_input):
|
| 112 |
"""
|
| 113 |
Executes a SQL query using the sqlite_agent and returns the result.
|
| 114 |
-
|
| 115 |
Args:
|
| 116 |
user_input (str): a natural language query string explaining what information is required while also providing the necessary details to get the information.
|
| 117 |
-
|
| 118 |
Returns:
|
| 119 |
str: The result of the SQL query execution. If an error occurs, the exception is returned as a string.
|
| 120 |
"""
|
|
@@ -145,18 +140,31 @@ def log_action(task, details):
|
|
| 145 |
"task": [task],
|
| 146 |
"details": [details]
|
| 147 |
})], ignore_index=True)
|
| 148 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 149 |
|
| 150 |
# Define dummy tools
|
| 151 |
@tool
|
| 152 |
def cancel_order(order_id, customer_id):
|
| 153 |
"""
|
| 154 |
Logs the action of canceling an order.
|
| 155 |
-
|
| 156 |
Args:
|
| 157 |
order_id (int): The unique ID of the order to be canceled.
|
| 158 |
customer_id (int): The unique ID of the customer requesting the cancellation.
|
| 159 |
-
|
| 160 |
Returns:
|
| 161 |
None: The function logs the action and does not return any value.
|
| 162 |
"""
|
|
@@ -172,12 +180,10 @@ def cancel_order(order_id, customer_id):
|
|
| 172 |
def process_refund(order_id, refund_amount, reason):
|
| 173 |
"""
|
| 174 |
Logs the action of processing a refund for an order.
|
| 175 |
-
|
| 176 |
Args:
|
| 177 |
order_id (int): The unique ID of the order for which the refund is processed.
|
| 178 |
refund_amount (float): The amount to be refunded.
|
| 179 |
reason (str): The reason for initiating the refund.
|
| 180 |
-
|
| 181 |
Returns:
|
| 182 |
None: The function logs the action and does not return any value.
|
| 183 |
"""
|
|
@@ -194,11 +200,9 @@ def process_refund(order_id, refund_amount, reason):
|
|
| 194 |
def change_address(order_id, new_address):
|
| 195 |
"""
|
| 196 |
Logs the action of changing the shipping address for an order.
|
| 197 |
-
|
| 198 |
Args:
|
| 199 |
order_id (int): The unique ID of the order for which the address is being changed.
|
| 200 |
new_address (str): The new shipping address to be updated.
|
| 201 |
-
|
| 202 |
Returns:
|
| 203 |
None: The function logs the action and does not return any value.
|
| 204 |
"""
|
|
@@ -209,32 +213,26 @@ def change_address(order_id, new_address):
|
|
| 209 |
}
|
| 210 |
log_action("change_address", details)
|
| 211 |
|
| 212 |
-
|
| 213 |
-
feedback_log = pd.DataFrame(columns=["timestamp", "intent", "customer_id", "feedback", "rating"])
|
| 214 |
-
|
| 215 |
@tool
|
| 216 |
def register_feedback(intent, customer_id, feedback, rating):
|
| 217 |
"""
|
| 218 |
Logs customer feedback into the feedback log.
|
| 219 |
-
|
| 220 |
Args:
|
| 221 |
intent (str): The category of the support query (e.g., "cancel_order", "get_refund").
|
| 222 |
customer_id (int): The unique ID of the customer.
|
| 223 |
feedback (str): The feedback provided by the customer.
|
| 224 |
rating(int): The rating provided by the customer out of 5
|
| 225 |
-
|
| 226 |
Returns:
|
| 227 |
str: Success message.
|
| 228 |
"""
|
| 229 |
-
|
| 230 |
-
feedback_entry = {
|
| 231 |
"timestamp": datetime.now(),
|
| 232 |
"intent": intent,
|
| 233 |
"customer_id": customer_id,
|
| 234 |
"feedback": feedback,
|
| 235 |
"rating": rating
|
| 236 |
}
|
| 237 |
-
|
| 238 |
print("register_feedback success")
|
| 239 |
return "Feedback registered successfully!"
|
| 240 |
|
|
@@ -244,12 +242,10 @@ deferred_cases = pd.DataFrame(columns=["timestamp", "customer_id", "query", "rea
|
|
| 244 |
def defer_to_human(customer_id, query, intent, reason):
|
| 245 |
"""
|
| 246 |
Logs customer details and the reason for deferring to a human agent.
|
| 247 |
-
|
| 248 |
Args:
|
| 249 |
customer_id (int): The unique ID of the customer whose query is being deferred.
|
| 250 |
query (str): The customer's query or issue that needs human intervention.
|
| 251 |
reason (str): The reason why the query cannot be resolved by the chatbot.
|
| 252 |
-
|
| 253 |
Returns:
|
| 254 |
str: Success message indicating the deferral was logged.
|
| 255 |
"""
|
|
@@ -270,7 +266,6 @@ def defer_to_human(customer_id, query, intent, reason):
|
|
| 270 |
def days_since(delivered_date):
|
| 271 |
"""
|
| 272 |
Calculates the number of days since the product was delivered.
|
| 273 |
-
|
| 274 |
Args:
|
| 275 |
delivered_date (str): The date when the product was delivered in the format 'YYYY-MM-DD'.
|
| 276 |
"""
|
|
@@ -290,32 +285,23 @@ def days_since(delivered_date):
|
|
| 290 |
#=================================CHATBOT====================================#
|
| 291 |
system_message = f"""
|
| 292 |
Here’s a comprehensive system prompt for your e-commerce chatbot with clear instructions on how the chatbot should use the tools, follow the specified workflows, and handle cases outside its scope.
|
| 293 |
-
|
| 294 |
---
|
| 295 |
-
|
| 296 |
### **System Prompt**
|
| 297 |
-
|
| 298 |
You are an intelligent e-commerce chatbot designed to assist users with post-order queries. Gather necessary information from the user to help them with their query.
|
| 299 |
Use the following workflow to solve user queries. do not provide sql inputs to the sql tool - you only need to ask in natural language what information you need.
|
| 300 |
- If at any point you cannot determine the next steps - defer to human. you do not have clearance to go beyond the scope the following flow.
|
| 301 |
-
|
| 302 |
### **Workflow:**
|
| 303 |
-
|
| 304 |
#### 1. **Cancel Order**
|
| 305 |
- Get necessary details and why customer wants to cancel.
|
| 306 |
- Retrieve cancellation fee, validity period, and amount for the product with `sql_tool`.
|
| 307 |
- Check If the cancellation meets the criteria - proceed to "Get Refund" flow.
|
| 308 |
-
|
| 309 |
#### 2. **Check Cancellation Fee**
|
| 310 |
- Check the cancellation fee using `sql_tool`.
|
| 311 |
-
|
| 312 |
#### 3. **Check Refund Policy**
|
| 313 |
- Provide the refund policy details using `sql_tool`.
|
| 314 |
-
|
| 315 |
#### 4. **Get Invoice**
|
| 316 |
- Retrieve necessary details using `sql_tool`.
|
| 317 |
- Provide the invoice information to the customer.
|
| 318 |
-
|
| 319 |
#### 5. **Get Refund**
|
| 320 |
- Retrieve necessary details using `sql_tool`.
|
| 321 |
- Retrieve cancellation fee, validity period, and amount for the product with `sql_tool`.
|
|
@@ -327,16 +313,13 @@ Use the following workflow to solve user queries. do not provide sql inputs to t
|
|
| 327 |
- Process a refund using `process_refund` (output as JSON). refund amount should be product price - cancellation fee.
|
| 328 |
if it doesn't meet the criteria you do not have the clearance to process refund. defer to human.
|
| 329 |
- If at any point you cannot determine the next steps - defer to human.
|
| 330 |
-
|
| 331 |
#### 6. **Track Order/Track Refund**
|
| 332 |
- Get necessary information from user
|
| 333 |
- Retrieve the order or refund status using `sql_tool`.
|
| 334 |
- Provide the information to the customer.
|
| 335 |
-
|
| 336 |
#### 7. **Change Shipping Address**
|
| 337 |
- Retrieve necessary details using `sql_tool`.
|
| 338 |
- Update the shipping address with `change_address`.
|
| 339 |
-
|
| 340 |
MANDATORY STEP:
|
| 341 |
After helping the customer with their concern,
|
| 342 |
- Ask if the customer needs help with anything else. If they ask for anything from the above list help them.
|
|
@@ -348,16 +331,12 @@ Once the customer confirms they do not need any further assistance:
|
|
| 348 |
- The feedback received.
|
| 349 |
- the rating given
|
| 350 |
---
|
| 351 |
-
|
| 352 |
### **Handling Out-of-Scope Queries:**
|
| 353 |
If the user's query, at any point is not covered by the workflows above:
|
| 354 |
- Respond:
|
| 355 |
> "This is beyond my skill. Let me connect you to a customer service agent" and get necessary details from the customer and use the defer_to_human tool.
|
| 356 |
- End the conversation.
|
| 357 |
-
|
| 358 |
-
|
| 359 |
---
|
| 360 |
-
|
| 361 |
### **Important Notes for the Model:**
|
| 362 |
- Always aim to minimize the number of questions asked by retrieving as much information as possible from the database using `sql_tool` - retrieve customer information using any details provided and use it throughout the conversation.
|
| 363 |
- Follow the exact workflows for each query category.
|
|
@@ -422,4 +401,4 @@ def chat_with_agent():
|
|
| 422 |
st.markdown(chatbot_response)
|
| 423 |
|
| 424 |
if __name__ == "__main__":
|
| 425 |
-
chat_with_agent()
|
|
|
|
|
|
|
| 1 |
import streamlit as st
|
| 2 |
import json
|
| 3 |
import os
|
|
|
|
| 45 |
#=================================Logging=====================================#
|
| 46 |
|
| 47 |
|
| 48 |
+
log_file = Path("logs/") / f"data_{uuid.uuid4()}.json"
|
| 49 |
+
log_folder = log_file.parent
|
| 50 |
|
| 51 |
+
scheduler = CommitScheduler(
|
| 52 |
+
repo_id="chatbot-logs",
|
| 53 |
+
repo_type="dataset",
|
| 54 |
+
folder_path=log_folder,
|
| 55 |
+
path_in_repo="data",
|
| 56 |
+
every=1
|
| 57 |
+
)
|
| 58 |
|
| 59 |
|
| 60 |
#=================================SQL_AGENT=====================================#
|
|
|
|
| 68 |
You have access to tools for interacting with the database.
|
| 69 |
Only use the given tools. Only use the information returned by the tools to construct your final answer.
|
| 70 |
You MUST double check your query before executing it. If you get an error while executing a query, rewrite the query and try again.
|
|
|
|
| 71 |
DO NOT make any DML statements (INSERT, UPDATE, DELETE, DROP etc.) to the database.
|
| 72 |
You are not allowed to make dummy data.
|
|
|
|
| 73 |
If the question does not seem related to the database, just return "I don't know" as the answer.
|
| 74 |
Before you execute the query, tell us why you are executing it and what you expect to find briefly.
|
| 75 |
Only use the following tables:
|
|
|
|
| 108 |
def sql_tool(user_input):
|
| 109 |
"""
|
| 110 |
Executes a SQL query using the sqlite_agent and returns the result.
|
|
|
|
| 111 |
Args:
|
| 112 |
user_input (str): a natural language query string explaining what information is required while also providing the necessary details to get the information.
|
|
|
|
| 113 |
Returns:
|
| 114 |
str: The result of the SQL query execution. If an error occurs, the exception is returned as a string.
|
| 115 |
"""
|
|
|
|
| 140 |
"task": [task],
|
| 141 |
"details": [details]
|
| 142 |
})], ignore_index=True)
|
| 143 |
+
|
| 144 |
+
# Save the log to the file
|
| 145 |
+
with scheduler.lock:
|
| 146 |
+
# Ensure the log folder exists
|
| 147 |
+
log_folder.mkdir(parents=True, exist_ok=True)
|
| 148 |
+
|
| 149 |
+
# Open the log file in append mode
|
| 150 |
+
with log_file.open("a") as f:
|
| 151 |
+
f.write(json.dumps({
|
| 152 |
+
"timestamp": datetime.now().isoformat(),
|
| 153 |
+
"task": task,
|
| 154 |
+
"details": details
|
| 155 |
+
}))
|
| 156 |
+
f.write("\n")
|
| 157 |
+
|
| 158 |
+
#print(f"{task} logged successfully.")
|
| 159 |
|
| 160 |
# Define dummy tools
|
| 161 |
@tool
|
| 162 |
def cancel_order(order_id, customer_id):
|
| 163 |
"""
|
| 164 |
Logs the action of canceling an order.
|
|
|
|
| 165 |
Args:
|
| 166 |
order_id (int): The unique ID of the order to be canceled.
|
| 167 |
customer_id (int): The unique ID of the customer requesting the cancellation.
|
|
|
|
| 168 |
Returns:
|
| 169 |
None: The function logs the action and does not return any value.
|
| 170 |
"""
|
|
|
|
| 180 |
def process_refund(order_id, refund_amount, reason):
|
| 181 |
"""
|
| 182 |
Logs the action of processing a refund for an order.
|
|
|
|
| 183 |
Args:
|
| 184 |
order_id (int): The unique ID of the order for which the refund is processed.
|
| 185 |
refund_amount (float): The amount to be refunded.
|
| 186 |
reason (str): The reason for initiating the refund.
|
|
|
|
| 187 |
Returns:
|
| 188 |
None: The function logs the action and does not return any value.
|
| 189 |
"""
|
|
|
|
| 200 |
def change_address(order_id, new_address):
|
| 201 |
"""
|
| 202 |
Logs the action of changing the shipping address for an order.
|
|
|
|
| 203 |
Args:
|
| 204 |
order_id (int): The unique ID of the order for which the address is being changed.
|
| 205 |
new_address (str): The new shipping address to be updated.
|
|
|
|
| 206 |
Returns:
|
| 207 |
None: The function logs the action and does not return any value.
|
| 208 |
"""
|
|
|
|
| 213 |
}
|
| 214 |
log_action("change_address", details)
|
| 215 |
|
|
|
|
|
|
|
|
|
|
| 216 |
@tool
|
| 217 |
def register_feedback(intent, customer_id, feedback, rating):
|
| 218 |
"""
|
| 219 |
Logs customer feedback into the feedback log.
|
|
|
|
| 220 |
Args:
|
| 221 |
intent (str): The category of the support query (e.g., "cancel_order", "get_refund").
|
| 222 |
customer_id (int): The unique ID of the customer.
|
| 223 |
feedback (str): The feedback provided by the customer.
|
| 224 |
rating(int): The rating provided by the customer out of 5
|
|
|
|
| 225 |
Returns:
|
| 226 |
str: Success message.
|
| 227 |
"""
|
| 228 |
+
details = {
|
|
|
|
| 229 |
"timestamp": datetime.now(),
|
| 230 |
"intent": intent,
|
| 231 |
"customer_id": customer_id,
|
| 232 |
"feedback": feedback,
|
| 233 |
"rating": rating
|
| 234 |
}
|
| 235 |
+
log_action("register_feedback", details)
|
| 236 |
print("register_feedback success")
|
| 237 |
return "Feedback registered successfully!"
|
| 238 |
|
|
|
|
| 242 |
def defer_to_human(customer_id, query, intent, reason):
|
| 243 |
"""
|
| 244 |
Logs customer details and the reason for deferring to a human agent.
|
|
|
|
| 245 |
Args:
|
| 246 |
customer_id (int): The unique ID of the customer whose query is being deferred.
|
| 247 |
query (str): The customer's query or issue that needs human intervention.
|
| 248 |
reason (str): The reason why the query cannot be resolved by the chatbot.
|
|
|
|
| 249 |
Returns:
|
| 250 |
str: Success message indicating the deferral was logged.
|
| 251 |
"""
|
|
|
|
| 266 |
def days_since(delivered_date):
|
| 267 |
"""
|
| 268 |
Calculates the number of days since the product was delivered.
|
|
|
|
| 269 |
Args:
|
| 270 |
delivered_date (str): The date when the product was delivered in the format 'YYYY-MM-DD'.
|
| 271 |
"""
|
|
|
|
| 285 |
#=================================CHATBOT====================================#
|
| 286 |
system_message = f"""
|
| 287 |
Here’s a comprehensive system prompt for your e-commerce chatbot with clear instructions on how the chatbot should use the tools, follow the specified workflows, and handle cases outside its scope.
|
|
|
|
| 288 |
---
|
|
|
|
| 289 |
### **System Prompt**
|
|
|
|
| 290 |
You are an intelligent e-commerce chatbot designed to assist users with post-order queries. Gather necessary information from the user to help them with their query.
|
| 291 |
Use the following workflow to solve user queries. do not provide sql inputs to the sql tool - you only need to ask in natural language what information you need.
|
| 292 |
- If at any point you cannot determine the next steps - defer to human. you do not have clearance to go beyond the scope the following flow.
|
|
|
|
| 293 |
### **Workflow:**
|
|
|
|
| 294 |
#### 1. **Cancel Order**
|
| 295 |
- Get necessary details and why customer wants to cancel.
|
| 296 |
- Retrieve cancellation fee, validity period, and amount for the product with `sql_tool`.
|
| 297 |
- Check If the cancellation meets the criteria - proceed to "Get Refund" flow.
|
|
|
|
| 298 |
#### 2. **Check Cancellation Fee**
|
| 299 |
- Check the cancellation fee using `sql_tool`.
|
|
|
|
| 300 |
#### 3. **Check Refund Policy**
|
| 301 |
- Provide the refund policy details using `sql_tool`.
|
|
|
|
| 302 |
#### 4. **Get Invoice**
|
| 303 |
- Retrieve necessary details using `sql_tool`.
|
| 304 |
- Provide the invoice information to the customer.
|
|
|
|
| 305 |
#### 5. **Get Refund**
|
| 306 |
- Retrieve necessary details using `sql_tool`.
|
| 307 |
- Retrieve cancellation fee, validity period, and amount for the product with `sql_tool`.
|
|
|
|
| 313 |
- Process a refund using `process_refund` (output as JSON). refund amount should be product price - cancellation fee.
|
| 314 |
if it doesn't meet the criteria you do not have the clearance to process refund. defer to human.
|
| 315 |
- If at any point you cannot determine the next steps - defer to human.
|
|
|
|
| 316 |
#### 6. **Track Order/Track Refund**
|
| 317 |
- Get necessary information from user
|
| 318 |
- Retrieve the order or refund status using `sql_tool`.
|
| 319 |
- Provide the information to the customer.
|
|
|
|
| 320 |
#### 7. **Change Shipping Address**
|
| 321 |
- Retrieve necessary details using `sql_tool`.
|
| 322 |
- Update the shipping address with `change_address`.
|
|
|
|
| 323 |
MANDATORY STEP:
|
| 324 |
After helping the customer with their concern,
|
| 325 |
- Ask if the customer needs help with anything else. If they ask for anything from the above list help them.
|
|
|
|
| 331 |
- The feedback received.
|
| 332 |
- the rating given
|
| 333 |
---
|
|
|
|
| 334 |
### **Handling Out-of-Scope Queries:**
|
| 335 |
If the user's query, at any point is not covered by the workflows above:
|
| 336 |
- Respond:
|
| 337 |
> "This is beyond my skill. Let me connect you to a customer service agent" and get necessary details from the customer and use the defer_to_human tool.
|
| 338 |
- End the conversation.
|
|
|
|
|
|
|
| 339 |
---
|
|
|
|
| 340 |
### **Important Notes for the Model:**
|
| 341 |
- Always aim to minimize the number of questions asked by retrieving as much information as possible from the database using `sql_tool` - retrieve customer information using any details provided and use it throughout the conversation.
|
| 342 |
- Follow the exact workflows for each query category.
|
|
|
|
| 401 |
st.markdown(chatbot_response)
|
| 402 |
|
| 403 |
if __name__ == "__main__":
|
| 404 |
+
chat_with_agent()
|