−25%

sur Windows en paiement annuel, jusqu'au 31/10. Voir les offres

EQVPS
Commencer

Votre première tâche d'agent dans une sandbox : un LLM écrit le code, une microVM l'exécute

Construisez la plus petite boucle utile d'exécution de code par IA : un modèle écrit un script Python, une sandbox Firecracker l'exécute, les erreurs repartent vers le modèle jusqu'à ce que le script marche. Une quarantaine de lignes, plus la même tâche via MCP sans aucun code.

Un agent qui écrit du code n'est utile que si quelque chose exécute ce code en toute sécurité et rend compte du résultat. Ce guide construit cette boucle de bout en bout : un modèle écrit un script Python, une sandbox l'exécute, et s'il échoue, l'erreur retourne au modèle. Puis la même tâche sans écrire une ligne de code, via MCP.

Il vous faut Python 3.8+, un token de compte EQVPS (voir connecter votre compte) et une clé d'API pour un modèle.

1. Fixer d'abord un plafond de dépenses

Un agent crée des sandboxes de lui-même, donnez-lui donc un plafond avant qu'il commence. Deux dollars par jour et vingt par mois suffisent largement pour expérimenter :

curl -X PUT https://api.eqvps.com/api/v1/eqvps/sandboxes/budget \
  -H "Authorization: Bearer $EQVPS_API_KEY" -H "Content-Type: application/json" \
  -d '{"daily_usd": 2, "monthly_usd": 20}'

Quand un plafond est atteint, les nouvelles sandboxes reçoivent 429 budget_exceeded et les éphémères en cours sont supprimées. Les détails sont dans limites et facturation des sandboxes.

2. Installer les deux bibliothèques

pip install eqvps anthropic
export EQVPS_API_KEY="your-eqvps-token"
export ANTHROPIC_API_KEY="your-model-key"

L'exemple utilise un fournisseur de modèles, mais rien n'en dépend. Seule la fonction ask() parle au modèle.

3. La boucle écrire, exécuter, corriger

Enregistrez ceci sous agent.py :

import re
import anthropic
from eqvps import Sandbox

TASK = "Count the prime numbers below 1,000,000 and print only the number."
client = anthropic.Anthropic()

def ask(messages):
    msg = client.messages.create(model="claude-sonnet-5", max_tokens=2000, messages=messages)
    return msg.content[0].text

def extract_code(text):
    m = re.search(r"`{3}(?:python)?\n(.*?)`{3}", text, re.S)
    return m.group(1) if m else text

messages = [{"role": "user", "content": "Write a Python 3 script for this task. "
             "Reply with a single code block and nothing else.\n\nTask: " + TASK}]

with Sandbox.create(tariff="small", idle_timeout=120) as sb:
    for attempt in range(1, 4):
        reply = ask(messages)
        r = sb.run(extract_code(reply), timeout=55)
        print(f"attempt {attempt}: exit code {r.exit_code}")
        if r.ok:
            print(r.stdout.strip())
            break
        messages += [
            {"role": "assistant", "content": reply},
            {"role": "user", "content": f"The script failed with exit code {r.exit_code}.\n"
             f"stderr:\n{r.stderr[-3000:]}\nFix it. Reply with a single code block."},
        ]

Lancez-le :

python3 agent.py

Une exécution typique affiche attempt 1: exit code 0 puis 78498. Si le premier script échoue, vous verrez le deuxième essai avec l'erreur corrigée.

Ce que fait chaque partie :

  • Sandbox.create(..., idle_timeout=120) démarre une microVM en une seconde environ. Si votre script meurt en route, la sandbox se supprime de toute façon après 2 minutes d'inactivité.
  • sb.run(code, timeout=55) exécute le code et renvoie le code de sortie, stdout et stderr. Un plantage du code est un résultat normal, pas une exception, la boucle peut donc le montrer au modèle.
  • r.stderr[-3000:] n'envoie que la fin de l'erreur. Une trace complète d'un gros script peut gaspiller beaucoup de contexte du modèle.
  • Trois essais, c'est une limite volontaire. Un modèle qui n'a pas corrigé un script en trois essais a généralement besoin d'une meilleure description de la tâche, pas d'un quatrième essai.

4. Quand la tâche dépasse 55 secondes

Un appel synchrone dure au maximum 55 secondes. Pour un travail plus long, lancez-le en arrière-plan et attendez :

task = sb.run(code, background=True)
result = task.wait(timeout=1800)

La tâche continue même si votre wait expire, et vous pouvez la reprendre avec sb.task(task_id).

5. La même tâche via MCP, sans code

Si vous utilisez un client MCP comme Claude Desktop ou Cursor avec le serveur MCP d'EQVPS, l'agent dispose déjà des outils sandbox : create_sandbox, run_code, exec_command, upload_file, download_file et kill_sandbox. Un prompt suffit :

Crée une petite sandbox éphémère. Écris un script Python qui compte les nombres premiers inférieurs à 1 000 000, exécute-le dedans, corrige-le s'il échoue, donne-moi le résultat et supprime la sandbox.

L'agent fait les mêmes appels que le script ci-dessus. Quels outils autoriser sans confirmation, c'est expliqué dans garde-fous MCP.

Ce que ça a coûté

La sandbox a vécu bien moins d'une minute et a été facturée au minimum de 60 secondes : 0,00055 $ sur small. L'appel au modèle coûte plus cher que la sandbox. Le crédit d'essai de 1 $ d'un nouveau compte couvre environ 1 800 exécutions comme celle-ci.

Et ensuite

FAQ

Pourquoi ne pas exécuter simplement le code du modèle sur ma machine ?

Parce que vous ne savez pas ce qu'il va faire. Du code généré peut supprimer des fichiers, lire vos clés ou boucler sans fin. Dans une sandbox, il tourne dans une microVM séparée avec son propre noyau, et la sandbox est supprimée ensuite.

Est-ce que ça marche avec d'autres modèles que celui de l'exemple ?

Oui. La boucle a seulement besoin d'une fonction qui prend des messages et renvoie du texte. Remplacez ask() par n'importe quelle API de chat, y compris un modèle local.

Qu'est-ce qui empêche un agent de créer des sandboxes à l'infini ?

Fixez un plafond de dépenses quotidien et mensuel avant de commencer. Une fois atteint, les nouvelles sandboxes sont refusées avec 429 budget_exceeded. De plus, seules deux commandes tournent en même temps par compte, une boucle emballée ne peut donc pas se démultiplier.

Le code généré peut-il accéder à Internet ?

Oui, les sandboxes ont un accès Internet sortant pour que le code puisse installer des paquets et récupérer des données. Elles n'ont aucun port entrant. Ne mettez pas de secrets dans le prompt ou le code ; passez ceux dont un script a vraiment besoin en variables d'environnement.

Commentaires

Pas encore de commentaires. Soyez le premier.

Laisser un commentaire

Les commentaires sont modérés avant leur publication.