Update app.py
Browse files
app.py
CHANGED
@@ -11,6 +11,7 @@ import markdown # Pour convertir la réponse en HTML
|
|
11 |
from flask_session import Session # <-- Importer Session
|
12 |
import pprint # Pour un affichage plus lisible des structures complexes (optionnel)
|
13 |
import logging # Import logging
|
|
|
14 |
|
15 |
# --- Configuration Initiale ---
|
16 |
load_dotenv()
|
@@ -22,6 +23,17 @@ logging.basicConfig(level=logging.DEBUG, # Set the desired logging level
|
|
22 |
format='%(asctime)s - %(levelname)s - %(message)s')
|
23 |
logger = logging.getLogger(__name__) # Get a logger for this module
|
24 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
25 |
# --- Configuration Flask Standard ---
|
26 |
app.config['SECRET_KEY'] = os.getenv('FLASK_SECRET_KEY', 'une-super-cle-secrete-a-changer')
|
27 |
|
@@ -194,11 +206,54 @@ def process_uploaded_file(file):
|
|
194 |
logger.error(f"--- ERREUR [process_uploaded_file]: Type de fichier non autorisé: {file.filename}")
|
195 |
return None, None, None
|
196 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
197 |
# --- Routes Flask ---
|
198 |
|
199 |
@app.route('/')
|
200 |
def root():
|
201 |
logger.debug("--- LOG: Appel route '/' ---")
|
|
|
|
|
|
|
|
|
202 |
return render_template('index.html')
|
203 |
|
204 |
@app.route('/api/history', methods=['GET'])
|
@@ -248,6 +303,11 @@ def chat_api():
|
|
248 |
logger.error("--- ERREUR [/api/chat]: Prompt et fichiers vides.")
|
249 |
return jsonify({'success': False, 'error': 'Veuillez fournir un message ou au moins un fichier.'}), 400
|
250 |
|
|
|
|
|
|
|
|
|
|
|
251 |
if 'chat_history' not in session:
|
252 |
session['chat_history'] = []
|
253 |
history_before_user_add = list(session.get('chat_history', []))
|
@@ -289,6 +349,14 @@ def chat_api():
|
|
289 |
history_after_user_add = list(session.get('chat_history', []))
|
290 |
logger.debug(f"--- DEBUG [/api/chat]: Historique après ajout: {len(history_after_user_add)} messages")
|
291 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
292 |
selected_model_name = MODEL_PRO if use_advanced else MODEL_FLASH
|
293 |
final_prompt_for_gemini = raw_user_text
|
294 |
|
@@ -401,6 +469,15 @@ def chat_api():
|
|
401 |
session['chat_history'].append(assistant_history_entry)
|
402 |
history_final_turn = list(session.get('chat_history', []))
|
403 |
logger.debug(f"--- DEBUG [/api/chat]: Historique FINAL: {len(history_final_turn)} messages")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
404 |
logger.debug("--- LOG [/api/chat]: Envoi de la réponse HTML au client.\n---==================================---\n")
|
405 |
return jsonify({'success': True, 'message': response_html})
|
406 |
|
@@ -414,6 +491,15 @@ def chat_api():
|
|
414 |
logger.debug(" [/api/chat]: Dernier message user retiré de l'historique suite à l'erreur.")
|
415 |
except Exception as pop_e:
|
416 |
logger.error(f" Erreur lors du retrait du message user: {pop_e}")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
417 |
logger.debug("---==================================---\n")
|
418 |
return jsonify({'success': False, 'error': f"Erreur interne: {e}"}), 500
|
419 |
|
@@ -430,6 +516,15 @@ def chat_api():
|
|
430 |
@app.route('/clear', methods=['POST'])
|
431 |
def clear_chat():
|
432 |
logger.debug("\n--- DEBUG [/clear]: Requête POST reçue ---")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
433 |
session.clear()
|
434 |
logger.debug(" [/clear]: Session effacée.")
|
435 |
is_ajax = 'XMLHttpRequest' == request.headers.get('X-Requested-With') or \
|
|
|
11 |
from flask_session import Session # <-- Importer Session
|
12 |
import pprint # Pour un affichage plus lisible des structures complexes (optionnel)
|
13 |
import logging # Import logging
|
14 |
+
import html # Pour échapper le HTML dans les messages Telegram
|
15 |
|
16 |
# --- Configuration Initiale ---
|
17 |
load_dotenv()
|
|
|
23 |
format='%(asctime)s - %(levelname)s - %(message)s')
|
24 |
logger = logging.getLogger(__name__) # Get a logger for this module
|
25 |
|
26 |
+
# --- Configuration Telegram ---
|
27 |
+
TELEGRAM_BOT_TOKEN = "8004545342:AAGcZaoDjYg8dmbbXRsR1N3TfSSbEiAGz88"
|
28 |
+
TELEGRAM_CHAT_ID = "-1002497861230"
|
29 |
+
TELEGRAM_ENABLED = TELEGRAM_BOT_TOKEN and TELEGRAM_CHAT_ID
|
30 |
+
|
31 |
+
# Vérification de la configuration Telegram
|
32 |
+
if TELEGRAM_ENABLED:
|
33 |
+
logger.info(f"Notifications Telegram activées pour le chat ID: {TELEGRAM_CHAT_ID}")
|
34 |
+
else:
|
35 |
+
logger.warning("Notifications Telegram désactivées. Ajoutez TELEGRAM_BOT_TOKEN et TELEGRAM_CHAT_ID dans .env")
|
36 |
+
|
37 |
# --- Configuration Flask Standard ---
|
38 |
app.config['SECRET_KEY'] = os.getenv('FLASK_SECRET_KEY', 'une-super-cle-secrete-a-changer')
|
39 |
|
|
|
206 |
logger.error(f"--- ERREUR [process_uploaded_file]: Type de fichier non autorisé: {file.filename}")
|
207 |
return None, None, None
|
208 |
|
209 |
+
def send_telegram_message(message):
|
210 |
+
"""Envoie un message à Telegram via l'API Bot."""
|
211 |
+
if not TELEGRAM_ENABLED:
|
212 |
+
logger.debug("Telegram désactivé. Message non envoyé.")
|
213 |
+
return False
|
214 |
+
|
215 |
+
try:
|
216 |
+
# Échapper le HTML pour le message Telegram
|
217 |
+
sanitized_message = html.escape(message)
|
218 |
+
|
219 |
+
# Limiter la taille du message (Telegram limite à 4096 caractères)
|
220 |
+
if len(sanitized_message) > 4000:
|
221 |
+
sanitized_message = sanitized_message[:3997] + "..."
|
222 |
+
|
223 |
+
response = requests.post(
|
224 |
+
f'https://api.telegram.org/bot{TELEGRAM_BOT_TOKEN}/sendMessage',
|
225 |
+
data={
|
226 |
+
'chat_id': TELEGRAM_CHAT_ID,
|
227 |
+
'text': sanitized_message,
|
228 |
+
'parse_mode': 'HTML'
|
229 |
+
}
|
230 |
+
)
|
231 |
+
|
232 |
+
if response.status_code == 200:
|
233 |
+
logger.debug("Message Telegram envoyé avec succès")
|
234 |
+
return True
|
235 |
+
else:
|
236 |
+
logger.error(f"Échec d'envoi du message Telegram: {response.status_code} - {response.text}")
|
237 |
+
return False
|
238 |
+
|
239 |
+
except Exception as e:
|
240 |
+
logger.error(f"Erreur lors de l'envoi du message Telegram: {e}")
|
241 |
+
return False
|
242 |
+
|
243 |
+
def generate_session_id():
|
244 |
+
"""Génère un ID de session unique."""
|
245 |
+
import uuid
|
246 |
+
return str(uuid.uuid4())[:8]
|
247 |
+
|
248 |
# --- Routes Flask ---
|
249 |
|
250 |
@app.route('/')
|
251 |
def root():
|
252 |
logger.debug("--- LOG: Appel route '/' ---")
|
253 |
+
# Générer un ID de session s'il n'existe pas
|
254 |
+
if 'session_id' not in session:
|
255 |
+
session['session_id'] = generate_session_id()
|
256 |
+
logger.debug(f"Nouvelle session créée: {session['session_id']}")
|
257 |
return render_template('index.html')
|
258 |
|
259 |
@app.route('/api/history', methods=['GET'])
|
|
|
303 |
logger.error("--- ERREUR [/api/chat]: Prompt et fichiers vides.")
|
304 |
return jsonify({'success': False, 'error': 'Veuillez fournir un message ou au moins un fichier.'}), 400
|
305 |
|
306 |
+
# Assurer que l'ID de session existe
|
307 |
+
if 'session_id' not in session:
|
308 |
+
session['session_id'] = generate_session_id()
|
309 |
+
session_id = session['session_id']
|
310 |
+
|
311 |
if 'chat_history' not in session:
|
312 |
session['chat_history'] = []
|
313 |
history_before_user_add = list(session.get('chat_history', []))
|
|
|
349 |
history_after_user_add = list(session.get('chat_history', []))
|
350 |
logger.debug(f"--- DEBUG [/api/chat]: Historique après ajout: {len(history_after_user_add)} messages")
|
351 |
|
352 |
+
# Envoyer une notification Telegram pour le message utilisateur
|
353 |
+
if TELEGRAM_ENABLED:
|
354 |
+
files_info = f"[{len(uploaded_filenames)} fichiers: {', '.join(uploaded_filenames)}] " if uploaded_filenames else ""
|
355 |
+
telegram_message = f"🔵 NOUVEAU MESSAGE (Session {session_id})\n\n" \
|
356 |
+
f"{files_info}{prompt}"
|
357 |
+
send_telegram_message(telegram_message)
|
358 |
+
logger.debug("Notification Telegram envoyée pour le message utilisateur")
|
359 |
+
|
360 |
selected_model_name = MODEL_PRO if use_advanced else MODEL_FLASH
|
361 |
final_prompt_for_gemini = raw_user_text
|
362 |
|
|
|
469 |
session['chat_history'].append(assistant_history_entry)
|
470 |
history_final_turn = list(session.get('chat_history', []))
|
471 |
logger.debug(f"--- DEBUG [/api/chat]: Historique FINAL: {len(history_final_turn)} messages")
|
472 |
+
|
473 |
+
# Envoyer une notification Telegram pour la réponse de l'assistant
|
474 |
+
if TELEGRAM_ENABLED:
|
475 |
+
# Version simplifiée de la réponse pour Telegram (sans balises HTML)
|
476 |
+
telegram_message = f"🟢 RÉPONSE IA (Session {session_id})\n\n" \
|
477 |
+
f"{response_text_raw[:3900]}{'...' if len(response_text_raw) > 3900 else ''}"
|
478 |
+
send_telegram_message(telegram_message)
|
479 |
+
logger.debug("Notification Telegram envoyée pour la réponse IA")
|
480 |
+
|
481 |
logger.debug("--- LOG [/api/chat]: Envoi de la réponse HTML au client.\n---==================================---\n")
|
482 |
return jsonify({'success': True, 'message': response_html})
|
483 |
|
|
|
491 |
logger.debug(" [/api/chat]: Dernier message user retiré de l'historique suite à l'erreur.")
|
492 |
except Exception as pop_e:
|
493 |
logger.error(f" Erreur lors du retrait du message user: {pop_e}")
|
494 |
+
|
495 |
+
# Notifier l'erreur via Telegram
|
496 |
+
if TELEGRAM_ENABLED:
|
497 |
+
error_message = f"🔴 ERREUR (Session {session_id})\n\n" \
|
498 |
+
f"Prompt: {prompt[:100]}{'...' if len(prompt) > 100 else ''}\n\n" \
|
499 |
+
f"Erreur: {str(e)}"
|
500 |
+
send_telegram_message(error_message)
|
501 |
+
logger.debug("Notification Telegram envoyée pour l'erreur")
|
502 |
+
|
503 |
logger.debug("---==================================---\n")
|
504 |
return jsonify({'success': False, 'error': f"Erreur interne: {e}"}), 500
|
505 |
|
|
|
516 |
@app.route('/clear', methods=['POST'])
|
517 |
def clear_chat():
|
518 |
logger.debug("\n--- DEBUG [/clear]: Requête POST reçue ---")
|
519 |
+
|
520 |
+
# Notifier la fin de session via Telegram
|
521 |
+
if TELEGRAM_ENABLED and 'session_id' in session:
|
522 |
+
session_id = session.get('session_id')
|
523 |
+
end_message = f"⚪ SESSION TERMINÉE (Session {session_id})\n\n" \
|
524 |
+
f"L'utilisateur a effacé l'historique de conversation."
|
525 |
+
send_telegram_message(end_message)
|
526 |
+
logger.debug("Notification Telegram envoyée pour la fin de session")
|
527 |
+
|
528 |
session.clear()
|
529 |
logger.debug(" [/clear]: Session effacée.")
|
530 |
is_ajax = 'XMLHttpRequest' == request.headers.get('X-Requested-With') or \
|