From 270741e2640579a7905eb2a87ca0fb8a4a7347e0 Mon Sep 17 00:00:00 2001 From: Renato Date: Sun, 15 Feb 2026 22:33:34 +0100 Subject: [PATCH] Agrega skill y funcionalidad para vender kits completos MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Nueva skill armar_kits.md con lógica completa de kits - Nueva tool confirmar_venta_kit para vender múltiples productos - Función db_confirmar_venta_kit() para procesar ventas en batch - Procesa ventas de kits y actualiza stock de todos los productos - Maneja errores parciales (si falta stock de algún producto) - Presenta resumen completo de venta del kit --- pymesbot/backend/main.py | 125 ++++++++++++++++++++++++++++++++++++++- 1 file changed, 124 insertions(+), 1 deletion(-) diff --git a/pymesbot/backend/main.py b/pymesbot/backend/main.py index 6adacf4..6eeb502 100644 --- a/pymesbot/backend/main.py +++ b/pymesbot/backend/main.py @@ -244,6 +244,91 @@ def db_confirmar_venta(producto_nombre: str, cantidad: int) -> dict: } +def db_confirmar_venta_kit(items: list) -> dict: + """Registra la venta de múltiples productos (un kit completo)""" + conn = sqlite3.connect(DB_PATH) + conn.row_factory = sqlite3.Row + cursor = conn.cursor() + + resultados = [] + total_venta = 0 + errores = [] + + for item in items: + producto_nombre = item.get("producto_nombre", "") + cantidad = item.get("cantidad", 1) + + query_normalized = normalize_text(producto_nombre.lower()) + search_term = f"%{query_normalized}%" + + cursor.execute( + """ + SELECT * FROM productos + WHERE activo = 1 AND ( + REPLACE(REPLACE(REPLACE(REPLACE(REPLACE(LOWER(nombre), 'á', 'a'), 'é', 'e'), 'í', 'i'), 'ó', 'o'), 'ú', 'u') LIKE ? + ) + LIMIT 1 + """, + (search_term,), + ) + + producto = cursor.fetchone() + + if not producto: + errores.append(f"Producto no encontrado: {producto_nombre}") + continue + + if producto["stock"] < cantidad: + errores.append( + f"Stock insuficiente para {producto['nombre']}: tenemos {producto['stock']}, pidió {cantidad}" + ) + continue + + # Registrar venta + cursor.execute( + """ + INSERT INTO ventas (producto_id, cantidad, precio_vendido, vendedor) + VALUES (?, ?, ?, ?) + """, + (producto["id"], cantidad, producto["precio"], "AI Bot"), + ) + + # Actualizar stock + cursor.execute( + """ + UPDATE productos SET stock = stock - ?, updated_at = datetime('now') + WHERE id = ? + """, + (cantidad, producto["id"]), + ) + + subtotal = cantidad * producto["precio"] + total_venta += subtotal + + resultados.append( + { + "producto": producto["nombre"], + "cantidad": cantidad, + "precio_unitario": producto["precio"], + "subtotal": subtotal, + } + ) + + conn.commit() + conn.close() + + if errores and not resultados: + return {"error": "No se pudo completar la venta", "detalles": errores} + + return { + "success": True, + "items_vendidos": len(resultados), + "total": total_venta, + "productos": resultados, + "errores": errores if errores else None, + } + + async def chat_with_ai(message: str, session_id: str = "pymesbot") -> Optional[str]: """Send message to Anthropic API with tools""" @@ -273,7 +358,7 @@ async def chat_with_ai(message: str, session_id: str = "pymesbot") -> Optional[s }, { "name": "confirmar_venta", - "description": "Registra una venta y descuenta el stock del inventario. Usar SOLO cuando el usuario confirme explícitamente que se vendió algo.", + "description": "Registra la venta de UN solo producto. Usar cuando el usuario confirme que vendió un producto específico.", "input_schema": { "type": "object", "properties": { @@ -289,6 +374,34 @@ async def chat_with_ai(message: str, session_id: str = "pymesbot") -> Optional[s "required": ["producto_nombre", "cantidad"], }, }, + { + "name": "confirmar_venta_kit", + "description": "Registra la venta de MÚLTIPLES productos a la vez (un kit completo). Usar cuando el usuario confirme que vendió un kit o varios productos juntos.", + "input_schema": { + "type": "object", + "properties": { + "items": { + "type": "array", + "description": "Lista de productos vendidos con sus cantidades", + "items": { + "type": "object", + "properties": { + "producto_nombre": { + "type": "string", + "description": "Nombre del producto", + }, + "cantidad": { + "type": "integer", + "description": "Cantidad vendida", + }, + }, + "required": ["producto_nombre", "cantidad"], + }, + }, + }, + "required": ["items"], + }, + }, ] messages = [{"role": "user", "content": message}] @@ -374,6 +487,16 @@ async def chat_with_ai(message: str, session_id: str = "pymesbot") -> Optional[s "content": json.dumps(resultado), } ) + elif tool_name == "confirmar_venta_kit": + items = tool_input.get("items", []) + resultado = db_confirmar_venta_kit(items) + tool_results.append( + { + "type": "tool_result", + "tool_use_id": tool_call.get("id"), + "content": json.dumps(resultado), + } + ) # Agregar el tool use y los resultados a los mensajes messages.append({"role": "assistant", "content": json.dumps(content)})