Aller au contenu principal

Sécurité et sandboxing

Donner le contrôle à une IA : les risques

Computer Use donne à un modèle d’IA la capacité d’agir sur un ordinateur. C’est puissant mais potentiellement dangereux. Un agent mal configuré pourrait naviguer vers des sites malveillants, exécuter du code arbitraire, ou exposer des données sensibles. La sécurité n’est pas optionnelle — c’est le fondement de toute mise en production.

Le principe du moindre privilège

Votre agent ne devrait avoir accès qu’au strict minimum nécessaire pour accomplir sa tâche :

  • Navigateur isolé : Jamais le navigateur principal de l’utilisateur
  • Pas d’accès au système de fichiers (sauf dossier dédié)
  • Pas d’accès au réseau interne (sauf si explicitement requis)
  • Pas de droits administrateur
  • Session éphémère : Les données sont supprimées après chaque exécution

Sandboxing avec Docker

La méthode recommandée est d’exécuter l’agent dans un conteneur Docker isolé :

FROM mcr.microsoft.com/playwright:v1.49.0-noble

WORKDIR /app

# Installer les dépendances Python
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# Copier le code de l'agent
COPY src/ ./src/

# Utilisateur non-root
RUN useradd -m agent
USER agent

# Pas d'accès réseau par défaut (configuré au lancement)
CMD ["python", "src/main.py"]

Lancez avec des restrictions réseau :

docker run --rm \
  --network=none \
  --memory=2g \
  --cpus=1.5 \
  --read-only \
  --tmpfs /tmp \
  -e ANTHROPIC_API_KEY="$ANTHROPIC_API_KEY" \
  computer-use-agent

Restrictions réseau ciblées

Si l’agent doit accéder à certains sites, utilisez un réseau dédié avec un proxy :

# Créer un réseau isolé
docker network create --internal agent-net

# Lancer un proxy qui n'autorise que certains domaines
docker run -d --network agent-net \
  --name agent-proxy \
  -e ALLOWED_DOMAINS="example.com,api.anthropic.com" \
  squid-proxy

# Lancer l'agent avec le proxy
docker run --rm --network agent-net \
  -e HTTP_PROXY="http://agent-proxy:3128" \
  -e HTTPS_PROXY="http://agent-proxy:3128" \
  computer-use-agent

Filtrage des URLs

Implémentez un filtre côté Playwright pour bloquer les domaines non autorisés :

def setup_url_filter(page, allowed_domains: list[str]):
    """Bloque la navigation vers des domaines non autorisés."""

    def check_navigation(route):
        from urllib.parse import urlparse
        domain = urlparse(route.request.url).hostname

        if any(domain.endswith(d) for d in allowed_domains):
            route.continue_()
        else:
            print(f"  BLOQUÉ : {route.request.url}")
            route.abort()

    page.route("**/*", check_navigation)


# Utilisation
allowed = ["example.com", "api.anthropic.com"]
setup_url_filter(page, allowed)

Protection des données sensibles

Masquer les informations dans les screenshots

Si l’écran contient des données sensibles (mots de passe, numéros de carte), masquez-les avant d’envoyer le screenshot au modèle :

from PIL import Image, ImageDraw

def mask_sensitive_areas(screenshot_bytes: bytes, regions: list) -> bytes:
    """Masque des zones sensibles dans un screenshot."""
    img = Image.open(io.BytesIO(screenshot_bytes))
    draw = ImageDraw.Draw(img)

    for x, y, w, h in regions:
        draw.rectangle([x, y, x + w, y + h], fill="black")

    buffer = io.BytesIO()
    img.save(buffer, format="PNG")
    return buffer.getvalue()

Ne jamais logger les données sensibles

import logging
import re

class SensitiveFilter(logging.Filter):
    """Filtre les données sensibles des logs."""

    PATTERNS = [
        (re.compile(r"password['\"]?\s*[:=]\s*['\"]?[^\s,}]+"), "password=***"),
        (re.compile(r"sk-ant-[a-zA-Z0-9-]+"), "sk-ant-***"),
        (re.compile(r"\b\d{16}\b"), "****-****-****-****"),
    ]

    def filter(self, record):
        msg = record.getMessage()
        for pattern, replacement in self.PATTERNS:
            msg = pattern.sub(replacement, msg)
        record.msg = msg
        return True

Limites d’exécution

Protégez-vous contre les agents qui déraillent :

import signal

class ExecutionLimits:
    """Impose des limites d'exécution à l'agent."""

    def __init__(
        self,
        max_iterations: int = 50,
        max_duration_seconds: int = 300,
        max_api_calls: int = 100,
        max_cost_usd: float = 5.0,
    ):
        self.max_iterations = max_iterations
        self.max_duration = max_duration_seconds
        self.max_api_calls = max_api_calls
        self.max_cost = max_cost_usd
        self.api_calls = 0
        self.total_tokens = 0

    def check(self, iteration: int, elapsed: float):
        """Vérifie que les limites ne sont pas dépassées."""
        if iteration >= self.max_iterations:
            raise RuntimeError(
                f"Limite d'itérations atteinte ({self.max_iterations})"
            )
        if elapsed >= self.max_duration:
            raise RuntimeError(
                f"Timeout ({self.max_duration}s)"
            )
        if self.api_calls >= self.max_api_calls:
            raise RuntimeError(
                f"Limite d'appels API atteinte ({self.max_api_calls})"
            )

    def track_usage(self, response):
        """Compte les tokens consommés."""
        self.api_calls += 1
        self.total_tokens += response.usage.input_tokens
        self.total_tokens += response.usage.output_tokens
        cost = self.total_tokens / 1_000_000 * 3  # Estimation
        if cost >= self.max_cost:
            raise RuntimeError(f"Budget dépassé (${cost:.2f})")

Checklist sécurité production

Avant de déployer un agent Computer Use en production, vérifiez :

  • Navigateur dans un conteneur Docker isolé
  • Réseau filtré (domaines autorisés uniquement)
  • Utilisateur non-root dans le conteneur
  • Limites de temps, d’itérations et de coût
  • Logs filtrés (pas de données sensibles)
  • Screenshots non persistés (ou chiffrés)
  • Pas d’accès au système de fichiers hôte
  • Clés API en variables d’environnement (pas dans le code)
  • Mécanisme d’arrêt d’urgence (kill switch)

Points clés à retenir

  • Exécutez toujours l’agent dans un environnement sandboxé (Docker recommandé)
  • Filtrez les URLs pour limiter l’accès aux domaines autorisés
  • Masquez les données sensibles dans les screenshots avant de les envoyer au modèle
  • Imposez des limites strictes : itérations, durée, coût, appels API
  • Les logs ne doivent jamais contenir de données sensibles