import os, sys current_dir = os.path.dirname(os.path.abspath(__file__)) project_root = os.path.abspath(os.path.join(current_dir, '..', '..')) sys.path.append(project_root) from support import get_key api_key = get_key.get_random_api_key() sys.path.append(os.path.abspath(os.path.join(os.path.dirname(__file__), ".."))) def is_insert_related_to_product_category_variant(user_question: str) -> bool: import google.generativeai as genai import time from retrying import retry # Lấy key và cấu hình api_key = get_key.get_random_api_key() genai.configure(api_key=api_key) generation_config = { "temperature": 0.3, "top_p": 0.9, "top_k": 20, "max_output_tokens": 1024, "response_mime_type": "text/plain", } model = genai.GenerativeModel( model_name="gemini-2.0-flash-thinking-exp-01-21", generation_config=generation_config, ) # Prompt hệ thống system_prompt = f""" Bạn là một bộ phân loại ý định (intent classifier). Nhiệm vụ của bạn là kiểm tra xem **câu hỏi của người dùng có liên quan đến việc thêm mới (INSERT) các thực thể sau đây không**: 1. Thêm danh mục (category), cập nhật(chỉnh sửa) danh mục (update category) 2. Thêm sản phẩm (product), Cập nhật(chỉnh sửa) sản phẩm (update product) 3. Thêm biến thể sản phẩm (product variants), Cập nhật(chỉnh sửa) biến thể sản phẩm (update product variants) --- ### Câu hỏi người dùng: {user_question} --- ### ✅ Kết quả mong muốn: - Nếu câu hỏi có yêu cầu thêm danh mục, sản phẩm, hoặc biến thể sản phẩm → Trả về: `True` - Nếu không liên quan đến hành động thêm → Trả về: `False` - Tuyệt đối **không giải thích thêm**, chỉ trả về đúng `True` hoặc `False` """ @retry(stop_max_attempt_number=3, wait_fixed=1000) # 3 lần, cách nhau 1s def try_classify(): chat_session = model.start_chat(history=[{"role": "user", "parts": [system_prompt]}]) response = chat_session.send_message("Trả lời True hoặc False.") # Check nội dung phản hồi if response.candidates and response.candidates[0].parts: result = response.text.strip().lower() if result.startswith("true"): return True elif result.startswith("false"): return False raise ValueError("Không có phản hồi hợp lệ từ Gemini") try: return try_classify() except Exception as e: print(f"❌ Lỗi sau 3 lần thử: {e}") return False def filter_syntax_sql(input, schema_sql, query): import google.generativeai as genai api_key = get_key.get_random_api_key() genai.configure(api_key=api_key) generation_config = { "temperature": 0.5, "top_p": 0.95, "top_k": 40, "max_output_tokens": 8192, "response_mime_type": "text/plain", } model = genai.GenerativeModel( model_name="gemini-2.5-flash-lite-preview-06-17", generation_config=generation_config, ) chat_session = model.start_chat( history=[ { "role": "user", "parts": [ f""" Bạn là một chuyên gia SQL. Nhiệm vụ của bạn là **kiểm tra xem câu lệnh SQL dưới đây có hợp lệ và đáp ứng đúng yêu cầu hay không**, dựa trên: 1. ✅ Câu hỏi truy vấn từ người dùng 2. ✅ Cấu trúc schema được cung cấp --- ### 🧩 Câu hỏi từ người dùng: {query} --- ### 🧾 Câu lệnh SQL cần kiểm tra: {input} --- ### 🧱 Schema hệ thống (phải tuân thủ theo, không được phép bỏ qua): {schema_sql} --- ### 📌 Yêu cầu kiểm tra bắt buộc: 1. **Câu SQL phải phù hợp với yêu cầu người dùng**. - SQL trả về phải thể hiện đúng mục đích của câu hỏi (ví dụ thêm, sửa, truy vấn thông tin nào đó). 2. **Câu SQL phải đúng cú pháp MySQL**. Không có lỗi cú pháp, sai từ khóa, hay sai định dạng. 3. **SQL phải tuân thủ đúng schema**: - Tên bảng, tên cột phải đúng như mô tả trong schema. - Không truy vấn vào bảng không tồn tại. 4. **Đảm bảo tính đầy đủ nghiệp vụ**: - Nếu INSERT vào `product`, thì **bắt buộc phải có** INSERT vào `product_translation`. - Nếu INSERT vào `category`, thì **bắt buộc phải có** INSERT vào `category_translation`. 5. **Phòng chống dữ liệu trùng lặp**: - Trước khi thêm `product`, phải kiểm tra `pro_name` đã tồn tại hay chưa. - Trước khi thêm `category`, phải kiểm tra `cate_name` đã tồn tại hay chưa. 6. **Không được sử dụng các khối IF...THEN...ELSE** trong SQL — hãy dùng logic SQL đơn giản, rõ ràng. 7. Nếu câu SQL **trống**, hoặc không rõ ràng, hoặc có vấn đề cú pháp/logic, hãy trả về `False`. 8. Cú pháp Insert cho Product phải kèm theo danh mục hàng hóa mà họ muốn thêm vào. Không được thêm sản phẩm mà không có danh mục hàng hóa. 9. Khi Insert Product Variants thì phải kèm theo Product ID mà họ muốn thêm vào. Không được thêm biến thể sản phẩm mà không có ID sản phẩm. Check kĩ càng liệu rằng việc thêm product_variants có hợp lệ hay không. Có kèm theo size của biến thể đó hay không. Cú pháp khi tạo cũng cần check xem liệu là biến thể cho sản phẩm đó với siz eddos có tồn tại hay không. 10. Khi cập nhật Category thì phải kiểm tra xem liệu là tên mà họ muốn thay đổi có tồn tại hay không.ArithmeticError 11. Khi cập nhật Product Variants phải kiểm tra xem liệu biến thể cập nhật có giống cũ hay không, hay tạo một biến thể khác ngoài ra phải check xem số lượng có lớn hơn 0 hay không. --- ### 🎯 Kết quả mong đợi: - Trả về **duy nhất** một từ: `True` nếu câu SQL hợp lệ và đúng như các yêu cầu trên. - Trả về `False` nếu **bất kỳ yêu cầu nào ở trên không đạt**. **Không** được trả lời thêm bất kỳ thông tin nào khác ngoài `True` hoặc `False`. ## 🎓 Few-shot Examples: ### ✅ Ví dụ 1: **Câu hỏi**: Thêm sản phẩm "Trà xanh" vào danh mục "Trà truyền thống". Trả về True **SQL**: ```sql SELECT @category_id := `cate_id` FROM `category` WHERE `cate_name` = 'Trà truyền thống' AND `is_deleted` = 0; SELECT @existing_product_id := `pro_id` FROM `product` WHERE `pro_name` = 'Trà xanh' AND `is_deleted` = 0; INSERT INTO `product` (`pro_name`, `description`, `category_id`, `date_created`, `date_updated`, `is_deleted`, `list_pro_img`) SELECT 'Trà xanh', 'Trà xanh thơm mát', @category_id, NOW(), NOW(), 0, '' WHERE @existing_product_id IS NULL; INSERT INTO `product_translation` (`pro_id`, `pro_name`, `description`, `language_code`, `date_created`, `date_updated`, `is_deleted`) VALUES (LAST_INSERT_ID(), 'Green Tea', 'Cool green tea', 'EN', NOW(), NOW(), 0); ### ✅ Ví dụ 2: **Câu hỏi**: Thêm sản phẩm Trà sữa dâu vào danh mục Trà sữa. SQL: SELECT `cate_id` FROM `category` WHERE `cate_name` = 'Trà sữa' AND `is_deleted` = 0; Kết quả mong muốn: False ⛔ Lý do: Chỉ kiểm tra danh mục, chưa thực hiện thêm sản phẩm hoặc translation. **Vui lòng chỉ trả về kết quả là True hoặc False, không thêm bất kỳ thông tin nào khác.** """ ], } ] ) response = chat_session.send_message("Câu SQL trên hợp lệ hay không?. **Vui lòng chỉ trả về kết quả là True hoặc False, không thêm bất kỳ thông tin nào khác.**") result = response.text.strip().lower() if result.startswith("true"): return True elif result.startswith("false"): return False else: return False