Vous êtes enfin arrivé aux parties les plus difficiles du cours, où l'objectif est d'automatiser les connexions des bots sur tous les bots disponibles.

Les sujets abordés dans cette section sont les suivants :

  1. Comment tout s'articule
  2. Connexion automatisée et contournement du captcha
  3. Modèles de base de données pour les profils de bots
  4. Routes backend
  5. Modèle frontend
  6. Tests

Comment tout s'articule

Voici un aperçu général de la manière dont tous les composants de tornet_scraper s'intègrent :

  1. Dans la section 3.1, vous avez configuré votre environnement de développement pour commencer.
  2. Dans la section 3.2, vous avez appris à générer des proxys pour sécuriser les connexions.
  3. Dans la section 3.3, vous avez découvert comment créer des API pour contourner les CAPTCHA, identifier les Initial Access Brokers (IAB) et traduire les données.

Ce sont des compétences impressionnantes. Nous allons maintenant voir comment ces éléments s'associent pour gérer les profils de bots. Voici comment les fonctionnalités fonctionnent ensemble :

  1. Génération de proxys : vous utiliserez le générateur de proxys pour créer des proxys Tor, dont les profils de bots ont besoin pour accéder au site Tor en toute sécurité.
  2. Gestion des API : vous tirerez parti de la gestion des API pour ajouter une API CAPTCHA, permettant aux bots de contourner les CAPTCHA et de se connecter avec succès.
  3. Gestion des bots :
    1. Utilisez l'interface pour créer des bots en saisissant leur nom d'utilisateur, leur mot de passe, leur objectif et le proxy qui leur est attribué.
    2. Spécifiez l'URL de connexion des bots.
    3. Cliquez sur « Effectuer la connexion du bot » pour connecter tous les comptes de bots et contourner automatiquement les CAPTCHA.
    4. Après la connexion, le système met à jour un tableau pour indiquer les comptes qui ont des sessions actives.

Si vous exécutez « Effectuer la connexion du bot » deux fois pour tous les comptes, le backend récupérera les nouvelles sessions. Le fait qu'une session soit marquée comme active ne garantit pas qu'elle soit valide. Il est fortement recommandé d'effectuer la connexion du bot à chaque fois que vous lancez l'application afin de garantir que les sessions sont actives et fonctionnelles.


Connexion automatisée et contournement des CAPTCHA

Ce sujet ne doit intimider personne, ce n'est pas de la magie. Dans les sections précédentes, nous avons exploré le contournement des CAPTCHA à l'aide du modèle ChatGPT o3, mais comme l'API OpenAI pour o3 ne prend pas en charge les images, nous allons maintenant utiliser le modèle « gpt-4.1 », qui s'est avéré efficace pour contourner les CAPTCHA d'après mon expérience.

N'oubliez jamais que de nombreux modèles d'IA interdisent le contournement des CAPTCHA à des fins malveillantes, car cela enfreint leurs conditions d'utilisation et peut être illégal. Dans ce cours, nous utilisons ces modèles dans un environnement contrôlé à des fins éducatives, en veillant au respect des normes légales. Je n'approuve ni ne tolère les activités illégales avec des modèles d'IA.

Sur la plateforme OpenAI, le Playground vous permet d'expérimenter différents modèles. Je vous recommande de l'essayer avant de continuer, car de nouveaux modèles pourraient être disponibles au moment où vous lirez ces lignes. Les modèles d'IA évoluant chaque mois, il se peut qu'un modèle plus avancé pour l'OCR existe lorsque vous aborderez cette section.

Le processus de contournement du CAPTCHA est simple :

  1. Ouvrez la page de connexion
  2. Téléchargez l'image CAPTCHA
  3. Redimensionnez-la pour améliorer sa lisibilité
  4. Encodez l'image en base64 et envoyez-la au modèle d'IA avec une invite
  5. Récupérez le texte CAPTCHA extrait
  6. Utilisez le texte CAPTCHA, le nom d'utilisateur et le mot de passe pour vous connecter
  7. Obtenez la session après une connexion réussie
  8. Utilisez la session pour scraper les places de marché, les publications et les profils

Bien que cela puisse sembler complexe, le fait de le décomposer en fonctions individuelles permet de comprendre facilement comment tout est lié.

Le code permettant de se connecter en contournant le CAPTCHA se trouve dans app/services/tornet_forum_login.py.

Fonctions

  1. image_to_base64 :

    • Objectif : convertit un fichier image en une chaîne codée en base64 pour la soumission à l'API.
    • Paramètres clés :
      • image_path : chemin d'accès au fichier image.
    • Retourne : chaîne de caractères base64 ou None en cas d'erreur.
    • Détails : lit le fichier image en mode binaire, l'encode en base64 et consigne le processus dans le journal. Renvoie None si l'accès au fichier ou l'encodage échoue.
  2. resize_image :

    • Objectif : redimensionne une image aux dimensions spécifiées pour un traitement CAPTCHA cohérent.
    • Paramètres clés :
      • image_path : chemin d'accès à l'image d'entrée.
      • output_path : chemin d'accès pour enregistrer l'image redimensionnée.
      • size : tuple des dimensions cibles (par défaut : 354x112).
    • Retourne : True en cas de succès, False en cas d'erreur.
    • Détails : utilise PIL pour redimensionner l'image avec le rééchantillonnage LANCZOS, l'enregistre au format PNG et consigne l'opération dans le journal. Renvoie False si le redimensionnement ou l'enregistrement échoue.
  3. clean_captcha_text :

    • Objectif : extrait un code CAPTCHA à 6 caractères (lettres majuscules et chiffres) à partir d'un texte brut.
    • Paramètres clés :
      • captcha_text : texte généré par l'API OpenAI.
    • Retourne : code à 6 caractères ou None si l'extraction échoue.
    • Détails : utilise une expression régulière ([A-Z0-9]{6}) pour trouver le code, enregistre le résultat nettoyé et renvoie None si aucune correspondance n'est trouvée ou si une erreur se produit.
  4. solve_captcha :

    • Objectif : résout une image CAPTCHA à l'aide de l'API OpenAI.
    • Paramètres clés :
      • image_path : chemin d'accès à l'image CAPTCHA.
      • api_key : clé API OpenAI.
      • model_name : modèle OpenAI (par exemple, GPT-4).
      • max_tokens : nombre maximal de tokens pour la réponse API.
      • prompt : texte d'instruction pour l'API.
    • Retourne : Code CAPTCHA de 6 caractères nettoyé ou None en cas d'erreur.
    • Détails :
      • Redimensionne l'image CAPTCHA à une taille fixe à l'aide de resize_image.
      • Convertit l'image redimensionnée en base64 à l'aide de image_to_base64.
      • Envoie l'image base64 et l'invite à l'API OpenAI via client.chat.completions.create, en demandant le texte du CAPTCHA.
      • Nettoie la réponse de l'API à l'aide de clean_captcha_text et renvoie le résultat. Enregistre les erreurs et renvoie None en cas d'échec.
  5. login_to_tor_website :

    • Objectif : se connecte à un site web Tor en résolvant des CAPTCHA et en soumettant des identifiants de connexion, puis renvoie une session avec des cookies.
    • Paramètres clés :
      • api_key : clé API OpenAI pour la résolution des CAPTCHA.
      • max_tokens : nombre maximal de jetons pour l'API OpenAI.
      • model_name : nom du modèle OpenAI.
      • login_url : URL de la page de connexion.
      • username : nom d'utilisateur de connexion.
      • password : mot de passe de connexion.
      • tor_proxy : URL du proxy Tor (par exemple, socks5h://127.0.0.1:9050).
      • prompt : invite pour la résolution du CAPTCHA OpenAI.
      • timeout : délai d'expiration de la requête (par défaut : 20 secondes).
    • Renvoie : requests.Session avec les cookies en cas de succès, None en cas d'échec.
    • Détails :
      • Crée une requests.Session avec le proxy Tor et un agent utilisateur aléatoire (provenant de gen_desktop_ua).
      • Tente la connexion jusqu'à 9 fois, avec un délai de 5 minutes après le nombre maximal de tentatives.
      • Récupère la page de connexion, extrait l'URL de l'image CAPTCHA à l'aide de BeautifulSoup et la télécharge.
      • Résout le CAPTCHA à l'aide de solve_captcha.
      • Envoie les données de connexion (nom d'utilisateur, mot de passe, code CAPTCHA et tous les champs de formulaire cachés tels que les jetons CSRF) via POST.
      • Vérifie la réponse pour s'assurer que l'opération a réussi (« profile » et « logout » dans le texte), les informations d'identification non valides ou le CAPTCHA non valide. Réessayer en cas d'échec, nettoyer les fichiers temporaires (images CAPTCHA) et renvoyer la session avec les cookies en cas de succès.

Le script tente la connexion jusqu'à 9 fois avant de faire une pause de 5 minutes et de réessayer. La résolution du CAPTCHA peut être imprévisible, certains CAPTCHA étant plus faciles à résoudre que d'autres. La stratégie consiste à persévérer jusqu'à ce que la connexion soit établie. D'après mon expérience, la connexion aboutit généralement après 5 tentatives.


Modèles de base de données pour les profils de bot

Les modèles de base de données pour les profils de bot comprennent toutes les informations nécessaires, telles que l'objectif du bot, l'URL « tornet_forum » et les comptes du bot, mais celles-ci sont organisées dans des modèles distincts pour une meilleure gestion et plus de clarté.

Vos modèles se trouvent dans « app/database/models.py ». Les voici :

class BotPurpose(enum.Enum):
    SCRAPE_MARKETPLACE = "scrape_marketplace"
    SCRAPE_POST = "scrape_post"
    SCRAPE_PROFILE = "scrape_profile"


class BotProfile(Base):
    __tablename__ = "bot_profiles"

    id = Column(Integer, primary_key=True, index=True)
    username = Column(String, unique=True, nullable=False)
    password = Column(String, nullable=False)
    purpose = Column(Enum(BotPurpose), nullable=False)
    tor_proxy = Column(String, nullable=True)
    user_agent = Column(String, nullable=True)
    session = Column(Text)
    timestamp = Column(DateTime, default=datetime.utcnow)

BotPurpose définit la tâche principale d'un bot et prend en charge trois types de scraping :

  1. Scraping des liens vers des publications sur le marché (à l'exclusion du contenu).
  2. Scraping des publications avec leurs liens.
  3. Récupération des liens des publications à partir des profils des utilisateurs.

Cela nécessite des types de bots distincts pour chaque objectif.


Routes backend

Le module tornet_forum_login.py gère les fonctionnalités de connexion de base, aucune interaction unique n'est donc nécessaire pour celui-ci. L'interface du profil du bot nécessite les fonctionnalités clés suivantes :

  1. Liste des bots existants.
  2. Créer de nouveaux bots.
  3. Mettre à jour les détails des bots.
  4. Supprimer des bots.
  5. Créer et modifier des URL onion.
  6. Se connecter.

Ces fonctionnalités correspondent aux opérations CRUD évoquées précédemment. La fonctionnalité de connexion repose sur la fonction login_to_tor_website, donc aucun nouveau concept n'est introduit au-delà du CRUD standard.

Votre code se trouve dans app/routes/bot_profile.py.

Fonctions

  1. get_bot_profiles :

    • Objectif : récupère tous les profils de bot de la base de données.
    • Paramètres clés :
      • db : SQLAlchemy Session (via Depends(get_db)).
    • Retourne : liste de dictionnaires contenant les détails du profil (ID, nom d'utilisateur, mot de passe masqué, objectif, proxy Tor, statut de la session, agent utilisateur, horodatage).
    • Détails : interroge la table BotProfile, masque le mot de passe pour des raisons de sécurité et renvoie les données du profil. Lève une exception HTTPException (500) en cas d'erreur.
  2. create_bot_profile :

    • Objectif : crée un nouveau profil de bot.
    • Paramètres clés :
      • profile : BotProfileCreate avec les données du profil.
      • request : FastAPI Request pour les messages flash basés sur la session.
      • db : SQLAlchemy Session.
    • Renvoie : Dictionnaire avec message de réussite et message flash.
    • Détails : Vérifie s'il existe des noms d'utilisateur en double, crée une instance BotProfile avec un agent utilisateur aléatoire (à partir de gen_desktop_ua), l'enregistre dans la base de données et ajoute un message flash de réussite à la session. Lève une exception HTTPException (400 pour les doublons, 500 pour les erreurs) avec retour en arrière en cas d'échec.
  3. update_bot_profile :

    • Objectif : met à jour un profil de bot existant.
    • Paramètres clés :
      • profile_id : ID entier du profil.
      • profile : BotProfileUpdate avec les champs mis à jour.
      • request : FastAPI Request pour les messages flash.
      • db : SQLAlchemy Session.
    • Retourne : Dictionnaire avec message de réussite et message flash.
    • Détails : Vérifie que le profil existe, recherche les noms d'utilisateur en double (s'ils ont été modifiés), met à jour les champs non None (y compris l'énumération BotPurpose) et valide les modifications. Ajoute un message flash de réussite. Lève une exception HTTPException (404 si introuvable, 400 pour les doublons, 500 pour les erreurs) avec retour en arrière en cas d'échec.
  4. delete_bot_profile :

    • Objectif : Supprime un profil de bot.
    • Paramètres clés :
      • profile_id : ID entier du profil.
      • request : FastAPI Request pour les messages flash.
      • db : SQLAlchemy Session.
    • Retourne : Dictionnaire avec message de réussite et message flash.
    • Détails : Vérifie que le profil existe, le supprime de la table BotProfile et ajoute un message flash de réussite. Lève une exception HTTPException (404 si introuvable, 500 en cas d'erreur) avec retour en arrière en cas d'échec.
  5. get_onion_url :

    • Objectif : Récupère la dernière URL onion.
    • Paramètres clés :
      • db : SQLAlchemy Session.
    • Retourne : Dictionnaire contenant la dernière OnionUrl.url ou None.
    • Détails : Interroge la table OnionUrl, triée par horodatage (décroissant), et renvoie l'URL la plus récente. Lève une exception HTTPException (500) en cas d'erreur.
  6. set_onion_url :

    • Objectif : crée une nouvelle entrée d'URL onion.
    • Paramètres clés :
      • onion : OnionUrlCreate avec l'URL.
      • request : FastAPI Request pour les messages flash.
      • db : SQLAlchemy Session.
    • Retourne : dictionnaire avec message de réussite et message flash.
    • Détails : Crée une instance OnionUrl, l'enregistre dans la base de données et ajoute un message flash de réussite. Lève une exception HTTPException (500) avec retour en arrière en cas d'échec.
  7. perform_bot_login :

    • Objectif : automatise la connexion pour tous les profils de bot à l'aide d'une API CAPTCHA.
    • Paramètres clés :
      • request : FastAPI Request pour les messages flash.
      • db : SQLAlchemy Session.
    • Retourne : Dictionnaire avec les résultats de connexion et un message flash.
    • Détails :
      • Récupère la dernière OnionUrl et la captcha_api active dans la table APIs.
      • Interroge toutes les entrées BotProfile et tente la connexion pour chacune d'entre elles à l'aide de login_to_tor_website (à partir de tornet_forum_login.py) avec les paramètres de l'API CAPTCHA.
      • Si un cookie de session est reçu, le formate sous la forme session=<valeur>, met à jour le champ session du profil et incrémente le nombre de connexions réussies. Les échecs de connexion sont consignés et collectés.
      • Renvoie un message récapitulatif avec le nombre de connexions réussies et échouées, en ajoutant un message flash (succès si une connexion a réussi, erreur dans le cas contraire). Lève une exception HTTPException (400 pour les URL/API/profils manquants, 500 pour les erreurs) avec retour en arrière en cas d'échec.

Modèle frontal

Votre code de modèle se trouve dans app/templates/bot_profile.html.

Le modèle bot_profile.html fournit une interface utilisateur pour gérer les profils de bot et les URL onion dans l'application tornet_scraper, en interagissant avec le backend via des appels API pour effectuer des opérations CRUD sur les profils de bot, définir des URL onion et automatiser les connexions. Vous trouverez ci-dessous une explication concise de ses fonctionnalités principales et de ses interactions avec le backend.

  1. Gestion des URL onion :

    • Objectif : permet aux utilisateurs de définir et d'afficher l'URL .onion pour accéder au site web Tor.
    • Interaction avec le backend :
      • Un champ de saisie et un bouton « Mettre à jour l'URL .onion » déclenchent la fonction setOnionUrl(), qui envoie une requête AJAX POST à /api/bot-profile/onion-url (gérée par bot_profile.py::set_onion_url) avec l'URL saisie.
      • Le backend enregistre l'URL dans la table « OnionUrl », ajoute un message flash de réussite à la session et renvoie une réponse de réussite. En cas de réussite, la page se recharge et « loadOnionUrl() » récupère la dernière URL via une requête GET vers « /api/bot-profile/onion-url », mettant à jour l'affichage. Les erreurs déclenchent un message flash d'erreur.
  2. Création d'un profil de bot :

    • Objectif : permet d'ajouter de nouveaux profils de bot.
    • Interaction avec le backend :
      • Le bouton « Ajouter un bot » ouvre une fenêtre modale avec des champs pour le nom d'utilisateur, le mot de passe, l'objectif (liste déroulante : scrape_marketplace, scrape_post, scrape_profile), proxy Tor et session (facultatif).
      • La fonction createBotProfile() envoie une requête AJAX POST à /api/bot-profile/create (gérée par bot_profile.py::create_bot_profile) avec les données du formulaire.
      • Le backend valide le nom d'utilisateur, crée un BotProfile avec un agent utilisateur aléatoire, l'enregistre dans la base de données et ajoute un message flash de réussite. En cas de succès, la fenêtre modale se ferme et la page se recharge. Les erreurs (par exemple, un nom d'utilisateur déjà utilisé) déclenchent un message flash d'erreur.
  3. Liste et mises à jour des profils de bots :

    • Objectif : affiche et actualise un tableau des profils des bots.
    • Interaction avec le backend :
      • La fonction loadBotProfiles(), déclenchée lors du chargement de la page et par le bouton « Actualiser », envoie une requête AJAX GET à /api/bot-profile/list (gérée par bot_profile.py::get_bot_profiles).
      • Le backend renvoie une liste de profils (ID, nom d'utilisateur, mot de passe masqué, objectif, proxy Tor, statut de session, agent utilisateur, horodatage), qui remplit le tableau. Les erreurs déclenchent un message d'erreur flash.
      • Le tableau se met à jour automatiquement après les actions de création, de mise à jour ou de suppression.
  4. Modification du profil du bot :

    • Objectif : permet de mettre à jour les profils de bots existants.
    • Interaction avec le backend :
      • Le bouton « Modifier » de chaque ligne du tableau appelle openEditModal(), qui remplit une fenêtre modale avec les données du profil.
      • La fonction updateBotProfile() envoie une requête AJAX PUT à /api/bot-profile/{profile_id} (gérée par bot_profile.py::update_bot_profile) avec les champs mis à jour (nom d'utilisateur, mot de passe, objectif, proxy Tor, agent utilisateur, session ; les champs facultatifs peuvent rester inchangés).
      • Le backend valide et met à jour le BotProfile, en ajoutant un message flash de réussite. En cas de succès, la fenêtre modale se ferme et la page se recharge. Les erreurs (par exemple, un nom d'utilisateur en double) déclenchent un message flash d'erreur.
  5. Suppression d'un profil de bot :

    • Objectif : Supprime un profil de bot.
    • Interaction avec le backend :
      • Le bouton « Supprimer » de chaque ligne du tableau ouvre une fenêtre modale de confirmation via openDeleteModal(), qui stocke l'ID du profil.
      • La fonction deleteBotProfile() envoie une requête AJAX DELETE à /api/bot-profile/{profile_id} (gérée par bot_profile.py::delete_bot_profile).
      • Le backend supprime le profil de la table BotProfile et ajoute un message flash indiquant que l'opération a réussi. En cas de succès, la fenêtre modale se ferme et la page se recharge. Les erreurs déclenchent un message flash d'erreur.
  6. Connexion automatisée du bot :

    • Objectif : déclenche la connexion de tous les profils de bot à l'aide d'un CAPTCHA.
    • Interaction avec le backend :
      • Le bouton « Perform Bot Login » appelle performBotLogin(), envoyant une requête AJAX POST à /api/bot-profile/perform-login.
      • Le backend récupère la dernière URL onion, l'API CAPTCHA active et tous les profils, puis utilise login_to_tor_website pour authentifier chaque profil, stockant les cookies de session dans la table BotProfile. Il renvoie un résumé des connexions réussies et échouées avec un message flash (succès si une connexion a réussi, erreur dans le cas contraire).
      • En cas de succès ou d'erreur, la page se recharge et des messages flash affichent le résultat.

Test

Pour tester cette fonctionnalité, vous devez d'abord ajouter une API Captcha. Je vous recommande d'obtenir une clé API gpt-4.1 et de l'ajouter via la page API Management.

Pour l'invite, vous pouvez utiliser ceci :

The attached image is 6 characters, it contains letters and numbers. The letters are all uppercase. I want you to analyze the image and extract the characters for me, send the combined characters as answer.

Une fois que tout est fait, vous devriez pouvoir vous connecter à un ou plusieurs comptes et leurs sessions seront mises à jour. Si la session est définie sur « true », cela signifie qu'elle a probablement été remplie.

Interface utilisateur de gestion des profils de bot