'Non autorisé']); exit; } $user = SessionManager::getUser(); $action = $_GET['action'] ?? $_POST['action'] ?? null; try { switch ($action) { case 'save': // Sauvegarder une clé API $provider = $_POST['provider'] ?? null; $api_key = $_POST['api_key'] ?? null; $model_default = $_POST['model_default'] ?? null; $quota_max = !empty($_POST['quota_max']) ? (int)$_POST['quota_max'] : null; if (!$provider || !$api_key || !$model_default) { throw new Exception('Paramètres manquants'); } // Valider le provider $valid_providers = ['gemini', 'mistral', 'openai', 'ollama']; if (!in_array($provider, $valid_providers)) { throw new Exception('Provider invalide'); } // Sauvegarder $result = APIKeyManager::saveKey( $user['id_utilisateur'], $provider, $api_key, $model_default ); if (!$result) { throw new Exception('Erreur lors de la sauvegarde'); } // Mettre à jour le quota si défini if ($quota_max !== null) { $db = Database::getInstance(); $db->query( "UPDATE api_keys SET quota_max = ? WHERE id_enseignant = ? AND provider = ?", [$quota_max, $user['id_utilisateur'], $provider] ); } echo json_encode([ 'success' => true, 'message' => 'Clé API enregistrée avec succès' ]); break; case 'test': // Tester une connexion API $provider = $_POST['provider'] ?? null; $api_key = $_POST['api_key'] ?? null; $model = $_POST['model'] ?? null; if (!$provider) { throw new Exception('Provider manquant'); } // Si pas de clé fournie, récupérer celle enregistrée if (!$api_key) { $key_data = APIKeyManager::getKey($user['id_utilisateur'], $provider); if (!$key_data) { throw new Exception('Aucune clé enregistrée pour ce provider'); } $api_key = $key_data['api_key']; $model = $model ?? $key_data['model_default']; } // Tester la connexion $result = APIKeyManager::testConnection($provider, $api_key, $model); echo json_encode($result); break; case 'delete': // Supprimer une clé API $provider = $_POST['provider'] ?? null; if (!$provider) { throw new Exception('Provider manquant'); } $result = APIKeyManager::deleteKey($user['id_utilisateur'], $provider); if (!$result) { throw new Exception('Erreur lors de la suppression'); } echo json_encode([ 'success' => true, 'message' => 'Clé API supprimée' ]); break; case 'get': // Récupérer une clé API (pour édition) $provider = $_GET['provider'] ?? null; if (!$provider) { throw new Exception('Provider manquant'); } $db = Database::getInstance(); $key_data = $db->fetchOne( "SELECT provider, model_default, quota_max, is_active FROM api_keys WHERE id_enseignant = ? AND provider = ?", [$user['id_utilisateur'], $provider] ); if (!$key_data) { throw new Exception('Clé non trouvée'); } // Ne pas retourner la clé API elle-même echo json_encode([ 'success' => true, 'data' => $key_data ]); break; case 'toggle': // Activer/désactiver une clé $provider = $_POST['provider'] ?? null; $active = isset($_POST['active']) ? (bool)$_POST['active'] : null; if (!$provider || $active === null) { throw new Exception('Paramètres manquants'); } $db = Database::getInstance(); $result = $db->query( "UPDATE api_keys SET is_active = ? WHERE id_enseignant = ? AND provider = ?", [$active, $user['id_utilisateur'], $provider] ); echo json_encode([ 'success' => true, 'message' => $active ? 'Clé activée' : 'Clé désactivée' ]); break; case 'stats': // Récupérer les statistiques d'utilisation $db = Database::getInstance(); $stats = $db->fetchAll( "SELECT provider, model_used, SUM(total_conversations) as conversations, SUM(total_messages) as messages, AVG(avg_response_time_ms) as avg_latency, month FROM v_chatbot_usage_stats WHERE id_enseignant = ? GROUP BY provider, model_used, month ORDER BY month DESC, conversations DESC LIMIT 50", [$user['id_utilisateur']] ); echo json_encode([ 'success' => true, 'stats' => $stats ]); break; default: throw new Exception('Action inconnue'); } } catch (Exception $e) { http_response_code(400); echo json_encode([ 'success' => false, 'error' => $e->getMessage() ]); }