File size: 4,986 Bytes
0821095
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
c9ccedb
 
 
 
 
 
 
 
 
0821095
c9ccedb
 
 
0821095
 
 
 
 
 
c9ccedb
 
 
 
0821095
 
 
 
 
 
 
 
 
 
 
 
3d6332d
0821095
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
"""
Browser management for the leaderboard agent.
"""
import os
import gc
import logging
from io import BytesIO
from time import sleep

import helium
from PIL import Image
from selenium import webdriver
from smolagents import CodeAgent
from smolagents.agents import ActionStep

# Configuration du logger
logger = logging.getLogger("leaderboard-parser")

# Global driver variable
driver = None


def save_screenshot(memory_step: ActionStep, agent: CodeAgent) -> None:
    """
    Save a screenshot of the current browser state in memory for the agent.
    This is used as a callback for the agent to visualize the page.
    The screenshot is only kept in memory and not saved to disk.
    """
    sleep(2.0)  # Increased to allow time for JavaScript animations
    current_step = memory_step.step_number
    if driver is not None:
        for previous_memory_step in agent.memory.steps:  # Remove previous screenshots from logs for lean processing
            if isinstance(previous_memory_step, ActionStep) and previous_memory_step.step_number <= current_step - 2:
                previous_memory_step.observations_images = None
        
        # Capture screenshot for agent visualization only (not saved to disk)
        png_bytes = driver.get_screenshot_as_png()
        image = Image.open(BytesIO(png_bytes))
        print(f"Captured a browser screenshot for agent: {image.size} pixels")
        memory_step.observations_images = [image.copy()]  # Create a copy to ensure it persists, important!

    # Update observations with current URL
    url_info = f"Current url: {driver.current_url}"
    memory_step.observations = (
        url_info if memory_step.observations is None else memory_step.observations + "\n" + url_info
    )
    return


def initialize_driver():
    """
    Initialize the Selenium WebDriver.
    Returns a configured Chrome WebDriver instance.
    """
    global driver
    
    # Si le driver existe déjà, on le nettoie d'abord pour éviter les fuites mémoire
    if driver is not None:
        close_driver()
    
    print("Démarrage de l'initialisation du navigateur Chrome...")
    
    # Configuration minimale mais suffisante pour éviter les timeouts
    chrome_options = webdriver.ChromeOptions()
    # Options essentielles pour l'environnement conteneurisé
    chrome_options.add_argument("--no-sandbox")
    chrome_options.add_argument("--disable-dev-shm-usage")
    # Options pour améliorer les performances
    chrome_options.add_argument("--disable-gpu")
    chrome_options.add_argument("--disable-extensions")
    
    try:
        print("Tentative de démarrage de Chrome avec Helium...")
        # Utiliser les options minimales mais avec le mode headless
        driver = helium.start_chrome(headless=True, options=chrome_options)
        print("Chrome démarré avec succès!")
        
        # Informations sur le navigateur
        print(f"Version de Chrome: {driver.capabilities.get('browserVersion', 'Inconnue')}")
        print(f"Plateforme: {driver.capabilities.get('platformName', 'Inconnue')}")
        
        # Augmenter le délai d'attente pour le chargement des pages
        driver.set_page_load_timeout(60)  # Augmenté à 60 secondes
        # Augmenter le délai d'attente pour les scripts
        driver.set_script_timeout(60)  # Augmenté à 60 secondes
        
        return driver
    except Exception as e:
        print(f"ERREUR lors du démarrage de Chrome: {str(e)}")
        # Capturer la trace complète pour diagnostic
        import traceback
        print("Trace d'erreur complète:")
        traceback.print_exc()
        
        # Vérifier si Chrome est disponible
        try:
            import subprocess
            chrome_path = os.environ.get("CHROME_PATH", "/usr/bin/google-chrome-stable")
            chrome_version_cmd = f"{chrome_path} --version"
            version_output = subprocess.check_output(chrome_version_cmd, shell=True, stderr=subprocess.STDOUT).decode()
            print(f"Version de Chrome installée: {version_output.strip()}")
        except Exception as chrome_check_error:
            print(f"Impossible de vérifier la version de Chrome: {str(chrome_check_error)}")
        
        raise


def close_driver():
    """
    Close the browser and clean up resources.
    """
    global driver
    
    try:
        print("Fermeture du navigateur et nettoyage des ressources...")
        
        # Utiliser helium.kill_browser() pour fermer proprement le navigateur
        helium.kill_browser()
        
        # Libérer la référence
        driver = None
        
        # Forcer le garbage collector
        gc.collect()
        
        print("Navigateur fermé avec succès")
    except Exception as e:
        print(f"Error closing browser: {e}")


# Alias de close_driver pour compatibilité avec browser_utils.cleanup_browser
def cleanup_browser():
    """
    Alias de close_driver pour compatibilité avec l'API existante.
    """
    close_driver()