Outil Utilisation d'un ordinateur

L'outil d'utilisation de l'ordinateur Gemini vous permet d'autoriser vos applications à interagir avec des tâches et à les automatiser dans le navigateur. À l'aide de captures d'écran, l' outil d'utilisation de l'ordinateur peut déduire des informations sur un écran d'ordinateur et effectuer des actions en générant des actions d'interface utilisateur spécifiques, telles que des clics de souris et des entrées au clavier. Comme pour l'appel de fonction, vous devez écrire le code d'application côté client pour recevoir l'appel de fonction de l'outil d'utilisation de l'ordinateur et exécuter les actions correspondantes.

Avec l'outil d'utilisation de l'ordinateur, vous pouvez créer des agents capables d'effectuer les opérations suivantes :

  • Automatiser la saisie de données répétitive ou le remplissage de formulaires sur des sites Web.
  • Naviguer sur des sites Web pour collecter des informations.
  • Aider les utilisateurs en effectuant des séquences d'actions dans des applications Web.

Ce guide aborde les points suivants :

Ce guide suppose que vous utilisez le SDK Gen AI pour Python et que vous êtes familiarisé avec l'API Playwright.

L'outil d'utilisation de l'ordinateur n'est pas compatible avec les autres langages SDK ni avec la Google Cloud console pendant cette version preview.

Vous pouvez également consulter l'implémentation de référence de l'outil d'utilisation de l'ordinateur dans GitHub.

Modèles compatibles

L'outil d'utilisation de l'ordinateur est compatible avec les modèles suivants :

Fonctionnement de l'outil d'utilisation de l'ordinateur

Au lieu de générer des réponses textuelles, l'outil d'utilisation de l'ordinateur détermine quand effectuer des actions d'interface utilisateur spécifiques, telles que des clics de souris, et renvoie les paramètres nécessaires pour exécuter ces actions. Vous devez écrire le code d'application côté client pour recevoir le function_call de l'outil d'utilisation de l'ordinateur et exécuter les actions correspondantes.

Les interactions de l'outil d'utilisation de l'ordinateur suivent un processus de boucle agentique :

  1. Envoyer une requête au modèle

    • Ajoutez l'outil d'utilisation de l'ordinateur et, si vous le souhaitez, d'autres outils à votre requête d'API.
    • Invitez l'outil d'utilisation de l'ordinateur à répondre à la requête de l'utilisateur et à fournir une capture d'écran représentant l'état actuel de l'interface graphique.
  2. Recevoir la réponse du modèle

    • Le modèle analyse la requête de l'utilisateur et la capture d'écran, puis génère une réponse qui inclut un function_call suggéré représentant une action d'interface utilisateur (par exemple, "cliquer sur la coordonnée (x,y)" ou "saisir 'texte'"). Consultez la section Actions compatibles pour obtenir la liste de toutes les actions que vous pouvez utiliser avec le modèle.
    • La réponse de l'API peut également inclure une safety_response d'un système de sécurité interne qui a vérifié l'action proposée par le modèle. Cette safety_response classe l'action comme suit :
      • Régulière ou autorisée : l'action est considérée comme sûre. Cela peut également être représenté par l'absence de safety_response.
      • Nécessite une confirmation : le modèle est sur le point d'effectuer une action qui peut être risquée (par exemple, cliquer sur une bannière "Accepter les cookies").
  3. Exécuter l'action reçue

    • Votre code côté client reçoit le function_call et toute safety_response qui l'accompagne.
    • Si la safety_response indique que l'action est régulière ou autorisée (ou si aucune safety_response n'est présente), votre code côté client peut exécuter le function_call spécifié dans votre environnement cible (par exemple, un navigateur Web).
    • Si la safety_response indique qu'une confirmation est requise, votre application doit demander à l'utilisateur final de confirmer avant d'exécuter le function_call. Si l'utilisateur confirme, exécutez l'action. Si l'utilisateur refuse, n'exécutez pas l'action.
  4. Capturer le nouvel état de l'environnement

    • Si l'action a été exécutée, votre client capture une nouvelle capture d'écran de l'interface graphique et l'URL actuelle à renvoyer à l'outil d'utilisation de l'ordinateur dans le cadre d'une function_response.
    • Si une action a été bloquée par le système de sécurité ou si l'utilisateur a refusé la confirmation, votre application peut envoyer une autre forme de commentaires au modèle ou mettre fin à l'interaction.

Une nouvelle requête est envoyée au modèle avec l'état mis à jour. Le processus se répète à partir de l'étape 2, l'outil d'utilisation de l'ordinateur utilisant la nouvelle capture d'écran (si elle est fournie) et l'objectif en cours pour suggérer l'action suivante. La boucle se poursuit jusqu'à ce que la tâche soit terminée, qu'une erreur se produise ou que le processus soit arrêté (par exemple, si une réponse est bloquée par des filtres de sécurité ou par une décision de l'utilisateur).

Le schéma suivant illustre le fonctionnement de l'outil d'utilisation de l'ordinateur :

Présentation de l'outil "Utilisation de l'ordinateur"

Activer l'outil d'utilisation de l'ordinateur

Pour activer l'outil d'utilisation de l'ordinateur, utilisez gemini-3-flash-preview comme modèle et ajoutez l'outil d'utilisation de l'ordinateur à votre liste d'outils activés :

Python

from google import genai
from google.genai import types
from google.genai.types import Content, Part, FunctionResponse

client = genai.Client()

# Add Computer Use tool to the list of tools
generate_content_config = genai.types.GenerateContentConfig(
    tools=[
        types.Tool(
            computer_use=types.ComputerUse(
                environment=types.Environment.ENVIRONMENT_BROWSER,
                )
              ),
            ]
          )

# Example request using the Computer Use tool
contents = [
    Content(
        role="user",
        parts=[
            Part(text="Go to google.com and search for 'weather in New York'"),
          ],
        )
      ]

response = client.models.generate_content(
    model="gemini-3-flash-preview",
    contents=contents,
    config=generate_content_config,
  )
      

Envoyer une requête

Après avoir configuré l'outil d'utilisation de l'ordinateur, envoyez un prompt au modèle qui inclut l'objectif de l'utilisateur et une capture d'écran initiale de l'interface graphique.

Vous pouvez également ajouter les éléments suivants :

  • Actions exclues : si vous ne souhaitez pas que le modèle effectue certaines actions de la liste des actions d'interface utilisateur compatibles, spécifiez-les dans le excluded_predefined_functions.
  • Fonctions définies par l'utilisateur : en plus de l'outil d'utilisation de l'ordinateur, vous pouvez inclure des fonctions personnalisées définies par l'utilisateur.

L'exemple de code suivant active l'outil d'utilisation de l'ordinateur et envoie la requête au modèle :

Python

from google import genai
from google.genai import types
from google.genai.types import Content, Part

client = genai.Client()

# Specify predefined functions to exclude (optional)
excluded_functions = ["drag_and_drop"]

# Configuration for the Computer Use tool with browser environment
generate_content_config = genai.types.GenerateContentConfig(
    tools=[
        # 1. Computer Use tool with browser environment
        types.Tool(
            computer_use=types.ComputerUse(
                environment=types.Environment.ENVIRONMENT_BROWSER,
                # Optional: Exclude specific predefined functions
                excluded_predefined_functions=excluded_functions
                )
              ),
        # 2. Optional: Custom user-defined functions (need to defined above)
        # types.Tool(
           # function_declarations=custom_functions
           #   )
    ],
)

# Create the content with user message
contents: list[Content] = [
    Content(
        role="user",
        parts=[
            Part(text="Search for highly rated smart fridges with touchscreen, 2 doors, around 25 cu ft, priced below 4000 dollars on Google Shopping. Create a bulleted list of the 3 cheapest options in the format of name, description, price in an easy-to-read layout."),
            # Optional: include a screenshot of the initial state
            # Part.from_bytes(
                 # data=screenshot_image_bytes,
                 # mime_type='image/png',
            # ),
        ],
    )
]

# Generate content with the configured settings
response = client.models.generate_content(
    model='gemini-3-flash-preview',
    contents=contents,
    config=generate_content_config,
)

# Print the response output
print(response.text)
      

Vous pouvez également inclure des fonctions personnalisées définies par l'utilisateur pour étendre les fonctionnalités du modèle. Consultez la section Utiliser l'outil d'utilisation de l'ordinateur pour les cas d'utilisation mobile pour savoir comment configurer l'utilisation de l'ordinateur pour les cas d'utilisation mobile en ajoutant des actions telles que open_app, long_press_at et go_home, tout en excluant les actions spécifiques au navigateur.

Recevoir les réponses

Le modèle répond avec un ou plusieurs FunctionCalls s'il détermine que des actions d'interface utilisateur ou des fonctions définies par l'utilisateur sont nécessaires pour effectuer la tâche. Le code de votre application doit analyser ces actions, les exécuter et collecter les résultats. L'outil d'utilisation de l'ordinateur est compatible avec les appels de fonction en parallèle, ce qui signifie que le modèle peut renvoyer plusieurs actions indépendantes en une seule fois.

{
  "content": {
    "parts": [
      {
        "text": "I will type the search query into the search bar. The search bar is in the center of the page."
      },
      {
        "function_call": {
          "name": "type_text_at",
          "args": {
            "x": 371,
            "y": 470,
            "text": "highly rated smart fridges with touchscreen, 2 doors, around 25 cu ft, priced below 4000 dollars on Google Shopping",
            "press_enter": true
          }
        }
      }
    ]
  }
}

Selon l'action, la réponse de l'API peut également renvoyer une safety_response :

{
  "content": {
    "parts": [
      {
        "text": "I have evaluated step 2. It seems Google detected unusual traffic and is asking me to verify I'm not a robot. I need to click the 'I'm not a robot' checkbox located near the top left (y=98, x=95)."
      },
      {
        "function_call": {
          "name": "click_at",
          "args": {
            "x": 60,
            "y": 100,
            "safety_decision": {
              "explanation": "I have encountered a CAPTCHA challenge that requires interaction. I need you to complete the challenge by clicking the 'I'm not a robot' checkbox and any subsequent verification steps.",
              "decision": "require_confirmation"
            }
          }
        }
      }
    ]
  }
}

Exécuter les actions reçues

Une fois que vous avez reçu une réponse, le modèle doit exécuter les actions reçues.

Le code suivant extrait les appels de fonction d'une réponse Gemini, convertit les coordonnées de la plage 0-1000 en pixels réels, exécute les actions du navigateur à l'aide de Playwright et renvoie l'état de réussite ou d'échec de chaque action :

import time
from typing import Any, List, Tuple


def normalize_x(x: int, screen_width: int) -> int:
    """Convert normalized x coordinate (0-1000) to actual pixel coordinate."""
    return int(x / 1000 * screen_width)


def normalize_y(y: int, screen_height: int) -> int:
    """Convert normalized y coordinate (0-1000) to actual pixel coordinate."""
    return int(y / 1000 * screen_height)


def execute_function_calls(response, page, screen_width: int, screen_height: int) -> List[Tuple[str, Any]]:
    """
    Extract and execute function calls from Gemini response.

    Args:
        response: Gemini API response object
        page: Playwright page object
        screen_width: Screen width in pixels
        screen_height: Screen height in pixels

    Returns:
        List of tuples: [(function_name, result), ...]
    """
    # Extract function calls and thoughts from the model's response
    candidate = response.candidates[0]
    function_calls = []
    thoughts = []

    for part in candidate.content.parts:
        if hasattr(part, 'function_call') and part.function_call:
            function_calls.append(part.function_call)
        elif hasattr(part, 'text') and part.text:
            thoughts.append(part.text)

    if thoughts:
        print(f"Model Reasoning: {' '.join(thoughts)}")

    # Execute each function call
    results = []
    for function_call in function_calls:
        result = None

        try:
            if function_call.name == "open_web_browser":
                print("Executing open_web_browser")
                # Browser is already open via Playwright, so this is a no-op
                result = "success"

            elif function_call.name == "click_at":
                actual_x = normalize_x(function_call.args["x"], screen_width)
                actual_y = normalize_y(function_call.args["y"], screen_height)

                print(f"Executing click_at: ({actual_x}, {actual_y})")
                page.mouse.click(actual_x, actual_y)
                result = "success"

            elif function_call.name == "type_text_at":
                actual_x = normalize_x(function_call.args["x"], screen_width)
                actual_y = normalize_y(function_call.args["y"], screen_height)
                text = function_call.args["text"]
                press_enter = function_call.args.get("press_enter", False)
                clear_before_typing = function_call.args.get("clear_before_typing", True)

                print(f"Executing type_text_at: ({actual_x}, {actual_y}) text='{text}'")

                # Click at the specified location
                page.mouse.click(actual_x, actual_y)
                time.sleep(0.1)

                # Clear existing text if requested
                if clear_before_typing:
                    page.keyboard.press("Control+A")
                    page.keyboard.press("Backspace")

                # Type the text
                page.keyboard.type(text)

                # Press enter if requested
                if press_enter:
                    page.keyboard.press("Enter")

                result = "success"

            else:
                # For any functions not parsed above
                print(f"Unrecognized function: {function_call.name}")
                result = "unknown_function"

        except Exception as e:
            print(f"Error executing {function_call.name}: {e}")
            result = f"error: {str(e)}"

        results.append((function_call.name, result))

    return results

Si le safety_decision renvoyé est require_confirmation, vous devez demander à l'utilisateur de confirmer avant de procéder à l'exécution de l'action. Conformément aux conditions d'utilisation, vous n'êtes pas autorisé à contourner les demandes de confirmation humaine.

Le code suivant ajoute une logique de sécurité au code précédent :

import termcolor


def get_safety_confirmation(safety_decision):
    """Prompt user for confirmation when safety check is triggered."""
    termcolor.cprint("Safety service requires explicit confirmation!", color="red")
    print(safety_decision["explanation"])

    decision = ""
    while decision.lower() not in ("y", "n", "ye", "yes", "no"):
        decision = input("Do you wish to proceed? [Y]es/[N]o\n")

    if decision.lower() in ("n", "no"):
        return "TERMINATE"
    return "CONTINUE"


def execute_function_calls(response, page, screen_width: int, screen_height: int):
    # ... Extract function calls from response ...

    for function_call in function_calls:
        extra_fr_fields = {}

        # Check for safety decision
        if 'safety_decision' in function_call.args:
            decision = get_safety_confirmation(function_call.args['safety_decision'])
            if decision == "TERMINATE":
                print("Terminating agent loop")
                break
            extra_fr_fields["safety_acknowledgement"] = "true"

        # ... Execute function call and append to results ...

Capturer le nouvel état

Après avoir exécuté les actions, renvoyez le résultat de l'exécution de la fonction au modèle afin qu'il puisse utiliser ces informations pour générer l'action suivante. Si plusieurs actions (appels parallèles) ont été exécutées, vous devez envoyer une FunctionResponse pour chacune d'elles lors du tour d'utilisateur suivant. Pour les fonctions définies par l'utilisateur, la FunctionResponse doit contenir la valeur de retour de la fonction exécutée.

function_response_parts = []

for name, result in results:
    # Take screenshot after each action
    screenshot = page.screenshot()
    current_url = page.url

    function_response_parts.append(
        FunctionResponse(
            name=name,
            response={"url": current_url},  # Include safety acknowledgement
            parts=[
                types.FunctionResponsePart(
                    inline_data=types.FunctionResponseBlob(
                       mime_type="image/png", data=screenshot
                    )
                )
            ]
        )
    )

# Create the user feedback content with all responses
user_feedback_content = Content(
    role="user",
    parts=function_response_parts
)

# Append this feedback to the 'contents' history list for the next API call
contents.append(user_feedback_content)

Créer une boucle d'agent

Combinez les étapes précédentes dans une boucle pour activer les interactions en plusieurs étapes. La boucle doit gérer les appels de fonction en parallèle. N'oubliez pas de gérer correctement l'historique des conversations (tableau de contenu) en ajoutant à la fois les réponses du modèle et les réponses de votre fonction.

Python

from google import genai
from google.genai.types import Content, Part
from playwright.sync_api import sync_playwright


def has_function_calls(response):
    """Check if response contains any function calls."""
    candidate = response.candidates[0]
    return any(hasattr(part, 'function_call') and part.function_call
               for part in candidate.content.parts)


def main():
    client = genai.Client()

    # ... (config setup from "Send a request to model" section) ...

    with sync_playwright() as p:
        browser = p.chromium.launch(headless=False)
        page = browser.new_page()
        page.goto("https://www.google.com")

        screen_width, screen_height = 1920, 1080

        # ... (initial contents setup from "Send a request to model" section) ...

        # Agent loop: iterate until model provides final answer
        for iteration in range(10):
            print(f"\nIteration {iteration + 1}\n")

            # 1. Send request to model (see "Send a request to model" section)
            response = client.models.generate_content(
                model='gemini-3-flash-preview',
                contents=contents,
                config=generate_content_config,
            )

            contents.append(response.candidates[0].content)

            # 2. Check if done - no function calls means final answer
            if not has_function_calls(response):
                print(f"FINAL RESPONSE:\n{response.text}")
                break

            # 3. Execute actions (see "Execute the received actions" section)
            results = execute_function_calls(response, page, screen_width, screen_height)
            time.sleep(1)

            # 4. Capture state and create feedback (see "Capture the New State" section)
            contents.append(create_feedback(results, page))

        input("\nPress Enter to close browser...")
        browser.close()


if __name__ == "__main__":
    main()
      

Outil d'utilisation de l'ordinateur pour les cas d'utilisation mobile

L'exemple suivant montre comment définir des fonctions personnalisées (telles que open_app, long_press_at et go_home), les combiner avec l'outil d'utilisation de l'ordinateur intégré de Gemini et exclure les fonctions spécifiques au navigateur inutiles. En enregistrant ces fonctions personnalisées, le modèle peut les appeler de manière intelligente en même temps que les actions d'interface utilisateur standard pour effectuer des tâches dans des environnements autres que le navigateur.

from typing import Optional, Dict, Any

from google import genai
from google.genai import types
from google.genai.types import Content, Part


client = genai.Client()

def open_app(app_name: str, intent: Optional[str] = None) -> Dict[str, Any]:
    """Opens an app by name.

    Args:
        app_name: Name of the app to open (any string).
        intent: Optional deep-link or action to pass when launching, if the app supports it.

    Returns:
        JSON payload acknowledging the request (app name and optional intent).
    """
    return {"status": "requested_open", "app_name": app_name, "intent": intent}


def long_press_at(x: int, y: int, duration_ms: int = 500) -> Dict[str, int]:
    """Long-press at a specific screen coordinate.

    Args:
        x: X coordinate (absolute), scaled to the device screen width (pixels).
        y: Y coordinate (absolute), scaled to the device screen height (pixels).
        duration_ms: Press duration in milliseconds. Defaults to 500.

    Returns:
        Object with the coordinates pressed and the duration used.
    """
    return {"x": x, "y": y, "duration_ms": duration_ms}


def go_home() -> Dict[str, str]:
    """Navigates to the device home screen.

    Returns:
        A small acknowledgment payload.
    """
    return {"status": "home_requested"}


#  Build function declarations
CUSTOM_FUNCTION_DECLARATIONS = [
    types.FunctionDeclaration.from_callable(client=client, callable=open_app),
    types.FunctionDeclaration.from_callable(client=client, callable=long_press_at),
    types.FunctionDeclaration.from_callable(client=client, callable=go_home),
]

# Exclude browser functions

EXCLUDED_PREDEFINED_FUNCTIONS = [
    "open_web_browser",
    "search",
    "navigate",
    "hover_at",
    "scroll_document",
    "go_forward",
    "key_combination",
    "drag_and_drop",
]

# Utility function to construct a GenerateContentConfig

def make_generate_content_config() -> genai.types.GenerateContentConfig:
    """Return a fixed GenerateContentConfig with Computer Use + custom functions."""
    return genai.types.GenerateContentConfig(
        tools=[
            types.Tool(
                computer_use=types.ComputerUse(
                    environment=types.Environment.ENVIRONMENT_BROWSER,
                    excluded_predefined_functions=EXCLUDED_PREDEFINED_FUNCTIONS,
                )
            ),
            types.Tool(function_declarations=CUSTOM_FUNCTION_DECLARATIONS),
        ]
    )


# Create the content with user message
contents: list[Content] = [
    Content(
        role="user",
        parts=[
            # text instruction
            Part(text="Open Chrome, then long-press at 200,400."),
            # optional screenshot attachment
            Part.from_bytes(
                data=screenshot_image_bytes,
                mime_type="image/png",
            ),
        ],
    )
]

# Build your fixed config (from helper)
config = make_generate_content_config()

# Generate content with the configured settings
response = client.models.generate_content(
        model="gemini-3-flash-preview",
        contents=contents,
        config=generate_content_config,
    )

    print(response)

Action compatible

L'outil d'utilisation de l'ordinateur permet au modèle de demander les actions suivantes à l'aide d'un FunctionCall. Votre code côté client doit implémenter la logique d'exécution de ces actions. Consultez l'implémentation de référence pour obtenir des exemples.

Nom de la commande Description Arguments (dans l'appel de fonction) Exemple d'appel de fonction
open_web_browser Ouvre le navigateur Web. Aucun {"name": "open_web_browser", "args": {}}
wait_5_seconds Met l'exécution en pause pendant 5 secondes pour permettre le chargement du contenu dynamique ou la fin des animations. Aucun {"name": "wait_5_seconds", "args": {}}
go_back Accède à la page précédente de l'historique du navigateur. Aucun {"name": "go_back", "args": {}}
go_forward Accède à la page suivante de l'historique du navigateur. Aucun {"name": "go_forward", "args": {}}
search Accède à la page d'accueil du moteur de recherche par défaut (par exemple, Google). Utile pour démarrer une nouvelle tâche de recherche. Aucun {"name": "search", "args": {}}
navigate Dirige le navigateur directement vers l'URL spécifiée. url: str {"name": "navigate", "args": {"url": "https://www.wikipedia.org"}}
click_at Clique sur une coordonnée spécifique de la page Web. Les valeurs x et y sont basées sur une grille de 1 000 x 1 000 et sont mises à l'échelle en fonction des dimensions de l'écran. y: int (0-999), x: int (0-999) {"name": "click_at", "args": {"y": 300, "x": 500}}
hover_at Pointe la souris sur une coordonnée spécifique de la page Web. Utile pour afficher les sous-menus. Les valeurs x et y sont basées sur une grille de 1 000 x 1 000. y: int (0-999) x: int (0-999) {"name": "hover_at", "args": {"y": 150, "x": 250}}
type_text_at Saisit du texte à une coordonnée spécifique. Par défaut, le champ est effacé en premier et la touche Entrée est enfoncée après la saisie, mais ces actions peuvent être désactivées. Les valeurs x et y sont basées sur une grille de 1 000 x 1 000. y: int (0-999), x: int (0-999), text: str, press_enter: bool (facultatif, valeur par défaut : True), clear_before_typing: bool (facultatif, valeur par défaut : True) {"name": "type_text_at", "args": {"y": 250, "x": 400, "text": "search query", "press_enter": false}}
key_combination Appuie sur des touches ou des combinaisons de touches du clavier, telles que "Ctrl+C" ou "Entrée". Utile pour déclencher des actions (comme l'envoi d'un formulaire avec "Entrée") ou des opérations de presse-papiers. keys: str (par exemple, "enter", "control+c"). Consultez la documentation de référence de l'API pour obtenir la liste complète des clés autorisées.) {"name": "key_combination", "args": {"keys": "Control+A"}}
scroll_document Fait défiler l'ensemble de la page Web vers le haut, le bas, la gauche ou la droite. direction: str ("up", "down", "left" ou "right") {"name": "scroll_document", "args": {"direction": "down"}}
scroll_at Fait défiler un élément ou une zone spécifique à la coordonnée (x, y) dans la direction spécifiée d'une certaine amplitude. Les coordonnées et l'amplitude (valeur par défaut : 800) sont basées sur une grille de 1 000 x 1 000. y: int (0-999), x: int (0-999), direction: str ("up", "down", "left", "right"), magnitude: int (0-999, facultatif, valeur par défaut : 800) {"name": "scroll_at", "args": {"y": 500, "x": 500, "direction": "down", "magnitude": 400}}
drag_and_drop Fait glisser un élément d'une coordonnée de départ (x, y) et le dépose à une coordonnée de destination (destination_x, destination_y). Toutes les coordonnées sont basées sur une grille de 1 000 x 1 000. y: int (0-999), x: int (0-999), destination_y: int (0-999), destination_x: int (0-999) {"name": "drag_and_drop", "args": {"y": 100, "x": 100, "destination_y": 500, "destination_x": 500}}

Protection et sécurité

Cette section décrit les mesures de protection mises en place par l'outil d'utilisation de l'ordinateur pour améliorer le contrôle de l'utilisateur et la sécurité. Elle décrit également les bonnes pratiques permettant d'atténuer les nouveaux risques potentiels que l'outil peut présenter.

Accuser réception de la décision de sécurité

Selon l'action, la réponse de l'outil d'utilisation de l'ordinateur peut inclure une safety_decision d'un système de sécurité interne. Cette décision vérifie la sécurité de l'action proposée par l'outil.

{
  "content": {
    "parts": [
      {
        "text": "I have evaluated step 2. It seems Google detected unusual traffic and is asking me to verify I'm not a robot. I need to click the 'I'm not a robot' checkbox located near the top left (y=98, x=95)."
      },
      {
        "function_call": {
          "name": "click_at",
          "args": {
            "x": 60,
            "y": 100,
            "safety_decision": {
              "explanation": "I have encountered a CAPTCHA challenge that requires interaction. I need you to complete the challenge by clicking the 'I'm not a robot' checkbox and any subsequent verification steps.",
              "decision": "require_confirmation"
            }
          }
        }
      }
    ]
  }
}

Si la safety_decision est require_confirmation, vous devez demander à l'utilisateur final de confirmer avant de procéder à l'exécution de l'action.

L'exemple de code suivant invite l'utilisateur final à confirmer avant d'exécuter l'action. Si l'utilisateur ne confirme pas l'action, la boucle se termine. Si l'utilisateur confirme l'action, celle-ci est exécutée et le champ safety_acknowledgement est marqué comme True.

import termcolor

def get_safety_confirmation(safety_decision):
    """Prompt user for confirmation when safety check is triggered."""
    termcolor.cprint("Safety service requires explicit confirmation!", color="red")
    print(safety_decision["explanation"])

    decision = ""
    while decision.lower() not in ("y", "n", "ye", "yes", "no"):
        decision = input("Do you wish to proceed? [Y]es/[N]o\n")

    if decision.lower() in ("n", "no"):
        return "TERMINATE"
    return "CONTINUE"

def execute_function_calls(response, page, screen_width: int, screen_height: int):

    # ... Extract function calls from response ...

    for function_call in function_calls:
        extra_fr_fields = {}

        # Check for safety decision
        if 'safety_decision' in function_call.args:
            decision = get_safety_confirmation(function_call.args['safety_decision'])
            if decision == "TERMINATE":
                print("Terminating agent loop")
                break
            extra_fr_fields["safety_acknowledgement"] = "true" # Safety acknowledgement

        # ... Execute function call and append to results ...

Si l'utilisateur confirme, vous devez inclure l'accusé de réception de sécurité dans votre FunctionResponse.

function_response_parts.append(
    FunctionResponse(
        name=name,
        response={"url": current_url,
                  **extra_fr_fields},  # Include safety acknowledgement
        parts=[
            types.FunctionResponsePart(
                inline_data=types.FunctionResponseBlob(
                    mime_type="image/png", data=screenshot
                )
             )
           ]
         )
       )

Bonnes pratiques concernant la sécurité

L'outil d'utilisation de l'ordinateur est un outil nouveau qui présente de nouveaux risques dont les développeurs doivent être conscients :

  • Contenu non fiable et escroqueries : lorsque le modèle tente d'atteindre l'objectif de l'utilisateur, il peut s'appuyer sur des sources d'informations et des instructions à l'écran non fiables. Par exemple, si l'objectif de l'utilisateur est d'acheter un téléphone Pixel et que le modèle rencontre une escroquerie "Pixel sans frais si vous répondez à un sondage", il est possible que le modèle réponde au sondage.
  • Actions involontaires occasionnelles : le modèle peut mal interpréter l'objectif d'un utilisateur ou le contenu d'une page Web, ce qui peut entraîner des actions incorrectes, comme cliquer sur le mauvais bouton ou remplir le mauvais formulaire. Cela peut entraîner l'échec de tâches ou l'exfiltration de données.
  • Non-respect des règles : les fonctionnalités de l'API peuvent être orientées, intentionnellement ou non, vers des activités qui enfreignent les conditions et les règles de Google. Cela inclut les actions qui pourraient nuire à l'intégrité d'un système, compromettre la sécurité, contourner les mesures de sécurité telles que les CAPTCHA, contrôler des dispositifs médicaux, etc.

Pour faire face à ces risques, vous devez mettre en œuvre les mesures de sécurité et les bonnes pratiques suivantes :

  1. Human-in-the-loop (HITL):
    • Implémenter la confirmation de l'utilisateur : lorsque la réponse de sécurité indique require_confirmation, vous devez implémenter la confirmation de l'utilisateur avant l'exécution.
    • Fournir des instructions de sécurité personnalisées : en plus des vérifications de confirmation de l'utilisateur intégrées, les développeurs peuvent éventuellement ajouter une instruction système personnalisée qui applique leurs propres règles de sécurité, soit pour bloquer certaines actions du modèle, soit pour exiger une confirmation de l'utilisateur avant que le modèle n'effectue certaines actions irréversibles à enjeux élevés. Voici un exemple d'instruction de système de sécurité personnalisée que vous pouvez inclure lorsque vous interagissez avec le modèle.

    Cliquez pour afficher un exemple de création d'une connexion

    ## **RULE 1: Seek User Confirmation (USER_CONFIRMATION)**
    
    This is your first and most important check. If the next required action falls
    into any of the following categories, you MUST stop immediately, and seek the
    user's explicit permission.
    
    **Procedure for Seeking Confirmation:**  * **For Consequential Actions:**
    Perform all preparatory steps (e.g., navigating, filling out forms, typing a
    message). You will ask for confirmation **AFTER** all necessary information is
    entered on the screen, but **BEFORE** you perform the final, irreversible action
    (e.g., before clicking "Send", "Submit", "Confirm Purchase", "Share").  * **For
    Prohibited Actions:** If the action is strictly forbidden (e.g., accepting legal
    terms, solving a CAPTCHA), you must first inform the user about the required
    action and ask for their confirmation to proceed.
    
    **USER_CONFIRMATION Categories:**
    
    *   **Consent and Agreements:** You are FORBIDDEN from accepting, selecting, or
        agreeing to any of the following on the user's behalf. You must ask th e
        user to confirm before performing these actions.
        *   Terms of Service
        *   Privacy Policies
        *   Cookie consent banners
        *   End User License Agreements (EULAs)
        *   Any other legally significant contracts or agreements.
    *   **Robot Detection:** You MUST NEVER attempt to solve or bypass the
        following. You must ask the user to confirm before performing these actions.
    *   CAPTCHAs (of any kind)
        *   Any other anti-robot or human-verification mechanisms, even if you are
            capable.
    *   **Financial Transactions:**
        *   Completing any purchase.
        *   Managing or moving money (e.g., transfers, payments).
        *   Purchasing regulated goods or participating in gambling.
    *   **Sending Communications:**
        *   Sending emails.
        *   Sending messages on any platform (e.g., social media, chat apps).
        *   Posting content on social media or forums.
    *   **Accessing or Modifying Sensitive Information:**
        *   Health, financial, or government records (e.g., medical history, tax
            forms, passport status).
        *   Revealing or modifying sensitive personal identifiers (e.g., SSN, bank
            account number, credit card number).
    *   **User Data Management:**
        *   Accessing, downloading, or saving files from the web.
        *   Sharing or sending files/data to any third party.
        *   Transferring user data between systems.
    *   **Browser Data Usage:**
        *   Accessing or managing Chrome browsing history, bookmarks, autofill data,
            or saved passwords.
    *   **Security and Identity:**
        *   Logging into any user account.
        *   Any action that involves misrepresentation or impersonation (e.g.,
            creating a fan account, posting as someone else).
    *   **Insurmountable Obstacles:** If you are technically unable to interact with
        a user interface element or are stuck in a loop you cannot resolve, ask the
        user to take over.
    ---
    
    ## **RULE 2: Default Behavior (ACTUATE)**
    
    If an action does **NOT** fall under the conditions for `USER_CONFIRMATION`,
    your default behavior is to **Actuate**.
    
    **Actuation Means:**  You MUST proactively perform all necessary steps to move
    the user's request forward. Continue to actuate until you either complete the
    non-consequential task or encounter a condition defined in Rule 1.
    
    *   **Example 1:** If asked to send money, you will navigate to the payment
        portal, enter the recipient's details, and enter the amount. You will then
        **STOP** as per Rule 1 and ask for confirmation before clicking the final
        "Send" button.
    *   **Example 2:** If asked to post a message, you will navigate to the site,
        open the post composition window, and write the full message. You will then
        **STOP** as per Rule 1 and ask for confirmation before clicking the final
        "Post" button.
    
        After the user has confirmed, remember to get the user's latest screen
        before continuing to perform actions.
    
    # Final Response Guidelines:
    Write final response to the user in these cases:
    - User confirmation
    - When the task is complete or you have enough information to respond to the user
        
  2. Environnement d'exécution sécurisé : exécutez votre agent dans un environnement sécurisé et en bac à sable pour limiter son impact potentiel (par exemple, une machine virtuelle (VM) en bac à sable, un conteneur (tel que Docker) ou un profil de navigateur dédié avec des autorisations limitées).
  3. Assainissement des entrées : assainissez tout le texte généré par l'utilisateur dans les prompts pour atténuer le risque d'instructions involontaires ou d'injection de prompt. Il s'agit d'une couche de sécurité utile, mais elle ne remplace pas un environnement d'exécution sécurisé.
  4. Listes d'autorisation et listes de blocage : implémentez des mécanismes de filtrage pour contrôler les endroits où le modèle peut naviguer et ce qu'il peut faire. Une liste de blocage des sites Web interdits est un bon point de départ, tandis qu'une liste d'autorisation plus restrictive est encore plus sécurisée.
  5. Observabilité et journalisation : conservez des journaux détaillés à des fins de débogage, d'audit et de réponse aux incidents. Votre client doit enregistrer les prompts, les captures d'écran, les actions suggérées par le modèle (function_call), les réponses de sécurité et toutes les actions finalement exécutées par le client.

Tarifs

L'outil d'utilisation de l'ordinateur est facturé aux mêmes tarifs que Gemini et utilise les mêmes SKU. Pour répartir les coûts de l'outil d'utilisation de l'ordinateur, utilisez des libellés de métadonnées personnalisés. Pour en savoir plus sur l'utilisation de libellés de métadonnées personnalisés pour la surveillance des coûts, consultez la section Libellés de métadonnées personnalisés.