Spaces:
Sleeping
Sleeping
Update app.py
Browse files
app.py
CHANGED
@@ -43,6 +43,7 @@ import httpx
|
|
43 |
import langdetect
|
44 |
from langdetect import detect
|
45 |
import threading
|
|
|
46 |
|
47 |
# Configure advanced logging
|
48 |
logging.basicConfig(
|
@@ -2018,7 +2019,7 @@ async def handle_all_products_selection(from_number: str, selection: str, user_c
|
|
2018 |
send_helpful_guidance(from_number, 'all_products_menu')
|
2019 |
|
2020 |
async def handle_intelligent_product_inquiry(from_number: str, query: str, user_context: dict, reply_language: str = 'en'):
|
2021 |
-
"""Handle product inquiry with OpenAI intelligence"""
|
2022 |
try:
|
2023 |
# First try direct product search
|
2024 |
products = get_veterinary_product_matches(query)
|
@@ -2141,7 +2142,7 @@ Format your response professionally with emojis and clear structure. Keep it con
|
|
2141 |
context_manager.add_to_history(from_number, query, message)
|
2142 |
|
2143 |
else:
|
2144 |
-
# Single product found - show detailed information
|
2145 |
selected_product = products[0]
|
2146 |
context_manager.update_context(
|
2147 |
from_number,
|
@@ -2153,21 +2154,15 @@ Format your response professionally with emojis and clear structure. Keep it con
|
|
2153 |
|
2154 |
# Get updated context with last message
|
2155 |
context = context_manager.get_context(from_number)
|
2156 |
-
response = generate_veterinary_product_response(selected_product, context)
|
2157 |
|
2158 |
-
#
|
2159 |
-
|
2160 |
-
|
2161 |
-
|
2162 |
-
|
2163 |
-
except Exception as e:
|
2164 |
-
logger.error(f"[AI] Translation error: {e}")
|
2165 |
-
send_whatsjet_message(from_number, response)
|
2166 |
-
else:
|
2167 |
-
send_whatsjet_message(from_number, response)
|
2168 |
|
2169 |
# Add to conversation history
|
2170 |
-
context_manager.add_to_history(from_number, query,
|
2171 |
|
2172 |
else:
|
2173 |
# Enhanced "not found" response with veterinary suggestions
|
@@ -3564,6 +3559,107 @@ def generate_veterinary_product_response_with_media(product_info: Dict[str, Any]
|
|
3564 |
'product_name': product_name
|
3565 |
}
|
3566 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3567 |
if __name__ == "__main__":
|
3568 |
# Launch FastAPI app
|
3569 |
import uvicorn
|
|
|
43 |
import langdetect
|
44 |
from langdetect import detect
|
45 |
import threading
|
46 |
+
import shutil
|
47 |
|
48 |
# Configure advanced logging
|
49 |
logging.basicConfig(
|
|
|
2019 |
send_helpful_guidance(from_number, 'all_products_menu')
|
2020 |
|
2021 |
async def handle_intelligent_product_inquiry(from_number: str, query: str, user_context: dict, reply_language: str = 'en'):
|
2022 |
+
"""Handle product inquiry with OpenAI intelligence and media support"""
|
2023 |
try:
|
2024 |
# First try direct product search
|
2025 |
products = get_veterinary_product_matches(query)
|
|
|
2142 |
context_manager.add_to_history(from_number, query, message)
|
2143 |
|
2144 |
else:
|
2145 |
+
# Single product found - show detailed information with media support
|
2146 |
selected_product = products[0]
|
2147 |
context_manager.update_context(
|
2148 |
from_number,
|
|
|
2154 |
|
2155 |
# Get updated context with last message
|
2156 |
context = context_manager.get_context(from_number)
|
|
|
2157 |
|
2158 |
+
# Use enhanced response with media support
|
2159 |
+
response_with_media = generate_veterinary_product_response_with_media(selected_product, context)
|
2160 |
+
|
2161 |
+
# Send the response
|
2162 |
+
send_whatsjet_message(from_number, response_with_media['text'])
|
|
|
|
|
|
|
|
|
|
|
2163 |
|
2164 |
# Add to conversation history
|
2165 |
+
context_manager.add_to_history(from_number, query, response_with_media['text'])
|
2166 |
|
2167 |
else:
|
2168 |
# Enhanced "not found" response with veterinary suggestions
|
|
|
3559 |
'product_name': product_name
|
3560 |
}
|
3561 |
|
3562 |
+
# Ensure static/images directory exists for product images
|
3563 |
+
def ensure_images_dir():
|
3564 |
+
images_dir = os.path.join('static', 'images')
|
3565 |
+
os.makedirs(images_dir, exist_ok=True)
|
3566 |
+
return images_dir
|
3567 |
+
|
3568 |
+
# New feature: Send product image with caption (product details)
|
3569 |
+
async def send_product_image_with_caption(from_number: str, product: Dict[str, Any], user_context: Dict[str, Any]):
|
3570 |
+
"""
|
3571 |
+
Send product image (if available) with product details as caption in a single WhatsApp message.
|
3572 |
+
If image is not available, send only the product details as text.
|
3573 |
+
Now supports 'Images' column in CSV (Google Drive or direct links).
|
3574 |
+
"""
|
3575 |
+
ensure_images_dir()
|
3576 |
+
product_name = product.get('Product Name', 'Unknown Product')
|
3577 |
+
details = generate_veterinary_product_response(product, user_context)
|
3578 |
+
image_url = product.get('Images', '').strip() if 'Images' in product else ''
|
3579 |
+
temp_file_path = None
|
3580 |
+
try:
|
3581 |
+
if image_url:
|
3582 |
+
# Convert Google Drive link to direct download if needed
|
3583 |
+
if 'drive.google.com' in image_url:
|
3584 |
+
if '/d/' in image_url:
|
3585 |
+
file_id = image_url.split('/d/')[1].split('/')[0]
|
3586 |
+
elif 'id=' in image_url:
|
3587 |
+
file_id = image_url.split('id=')[1].split('&')[0]
|
3588 |
+
else:
|
3589 |
+
file_id = ''
|
3590 |
+
if file_id:
|
3591 |
+
image_url = f"https://drive.google.com/uc?export=download&id={file_id}"
|
3592 |
+
# Download the image to a temp file
|
3593 |
+
response = requests.get(image_url, stream=True, timeout=10)
|
3594 |
+
if response.status_code == 200:
|
3595 |
+
with tempfile.NamedTemporaryFile(delete=False, suffix='.jpg') as tmp:
|
3596 |
+
for chunk in response.iter_content(1024):
|
3597 |
+
tmp.write(chunk)
|
3598 |
+
temp_file_path = tmp.name
|
3599 |
+
media_type = 'image/jpeg'
|
3600 |
+
filename = f"{product_name.replace(' ', '_')}.jpg"
|
3601 |
+
success = send_whatsjet_message(
|
3602 |
+
from_number,
|
3603 |
+
details,
|
3604 |
+
media_type=media_type,
|
3605 |
+
media_path=temp_file_path,
|
3606 |
+
filename=filename
|
3607 |
+
)
|
3608 |
+
if success:
|
3609 |
+
logger.info(f"[Product] Sent image from CSV link with caption for product: {product_name}")
|
3610 |
+
return
|
3611 |
+
else:
|
3612 |
+
logger.warning(f"[Product] Failed to send image from CSV link, sending text only: {product_name}")
|
3613 |
+
else:
|
3614 |
+
logger.warning(f"[Product] Could not download image from CSV link: {image_url}")
|
3615 |
+
# Fallback to local static/images
|
3616 |
+
image_path = get_product_image_path(product_name)
|
3617 |
+
if image_path and os.path.exists(image_path):
|
3618 |
+
media_type = get_product_image_media_type(image_path)
|
3619 |
+
filename = f"{product_name.replace(' ', '_')}.jpg"
|
3620 |
+
success = send_whatsjet_message(
|
3621 |
+
from_number,
|
3622 |
+
details,
|
3623 |
+
media_type=media_type,
|
3624 |
+
media_path=image_path,
|
3625 |
+
filename=filename
|
3626 |
+
)
|
3627 |
+
if success:
|
3628 |
+
logger.info(f"[Product] Sent image with caption for product: {product_name}")
|
3629 |
+
else:
|
3630 |
+
logger.warning(f"[Product] Failed to send image, sending text only: {product_name}")
|
3631 |
+
send_whatsjet_message(from_number, details)
|
3632 |
+
else:
|
3633 |
+
send_whatsjet_message(from_number, details)
|
3634 |
+
logger.info(f"[Product] Sent product info without image: {product_name}")
|
3635 |
+
except Exception as e:
|
3636 |
+
logger.error(f"[Product] Error sending product image with caption: {e}")
|
3637 |
+
send_whatsjet_message(from_number, details)
|
3638 |
+
finally:
|
3639 |
+
if temp_file_path and os.path.exists(temp_file_path):
|
3640 |
+
try:
|
3641 |
+
os.remove(temp_file_path)
|
3642 |
+
except Exception:
|
3643 |
+
pass
|
3644 |
+
|
3645 |
+
@app.get("/test-product-image-with-caption")
|
3646 |
+
async def test_product_image_with_caption(phone: str):
|
3647 |
+
"""
|
3648 |
+
Test endpoint to send Heposel product image and details as caption to the given phone number.
|
3649 |
+
"""
|
3650 |
+
# Load Heposel product from CSV
|
3651 |
+
try:
|
3652 |
+
df = pd.read_csv('Veterinary.csv')
|
3653 |
+
row = df[df['Product Name'].str.lower() == 'heposel']
|
3654 |
+
if row.empty:
|
3655 |
+
return {"error": "Heposel not found in CSV"}
|
3656 |
+
product = row.iloc[0].to_dict()
|
3657 |
+
user_context = context_manager.get_context(phone)
|
3658 |
+
await send_product_image_with_caption(phone, product, user_context)
|
3659 |
+
return {"status": "sent", "phone": phone}
|
3660 |
+
except Exception as e:
|
3661 |
+
return {"error": str(e)}
|
3662 |
+
|
3663 |
if __name__ == "__main__":
|
3664 |
# Launch FastAPI app
|
3665 |
import uvicorn
|