Aller au contenu
astorlm
Langue: Français
← Carte

Niveau 1

Qu'est-ce qu'un agent ?

On appelle « agent » presque tout ce qui contient un modèle de langage. La définition utile est bien plus étroite, et elle tient en une question : qui décide de l'étape suivante ? Dans un agent, c'est le modèle.
1/16 Plis du bandonéon :
  • user
  • assistant
  • tool_result
Un villageois a perdu la clé du coffre du village. Astor, la boucle de l'agent, porte la question à l'Oracle, avec deux outils : ask_villager et search_area. La plus grande partie de la carte est encore dans le noir.

EventBus

Le problème

Un chatbot, un script qui appelle deux fois un modèle et un système qui corrige des bugs tout seul : on les appelle tous des agents. Difficile alors de savoir ce que vous construisez, et encore plus de choisir le bon outil pour le travail.

L'animation est un petit jeu d'aventure. Un villageois demande : « J'ai perdu la clé du coffre du village. Où est-elle ? ». Le jeu a deux fonctions qui peuvent aider : ask_villager demande à quelqu'un ce qu'il a vu, et search_area fouille un endroit de la carte. Regardez qui décide laquelle s'exécute, et quand.

Ce qui en fait un agent

Un agent, ce n'est pas « un LLM avec des outils », ni « un workflow malin ». C'est un système où le modèle choisit le flux de contrôle : quel outil appeler, dans quel ordre et quand s'arrêter. Votre code ne dit jamais « interroge le pêcheur, puis fouille le chêne ». Le modèle lit chaque résultat et décide de l'étape suivante.

La boucle qui rend cela possible, c'est le niveau suivant.

Dans l'animation

Le villageois votre app
La question part d'une maison du village, et la réponse y revient.
Astor la boucle
La boucle de l'agent, avec le bandonéon des messages sur le dos. Il va là où les notes de l'Oracle l'envoient, et nulle part ailleurs.
L'Oracle LLM
Le modèle, dans une grotte entre deux feux. Il ne sort jamais : il ne sait que ce qu'il y a dans le bandonéon. Sans outils, il ne peut que parler, comme Petrus l'Inerte.
Le quai et les bois outils
ask_villager et search_area : vos propres fonctions. Un écran reste dans le noir jusqu'à ce qu'un chemin y mène.
Les écrans éclairés flux de contrôle
Tout le pattern en une image, aussi sur la mini-carte. Chaque chemin n'apparaît que quand l'Oracle demande cet outil, après avoir lu le dernier résultat. Dans un workflow, votre code les aurait tous tracés avant même que quelqu'un pose la question. La montagne reste dans le noir : le modèle n'en a jamais eu besoin.
Rubis et cœurs tokens, maxTurns
Chaque visite à l'Oracle coûte des rubis, parce que tout le bandonéon est relu, et un cœur du budget de tours. Les chiffres sont illustratifs.

Le code

Avec astorlm : Enveloppez vos propres fonctions avec tool() et donnez-les à l'agent. La boucle est intégrée : le modèle choisit quels outils appeler, dans quel ordre, et quand il en sait assez pour répondre.

À partir de zéro : Les fonctions de votre jeu, données au modèle comme outils. La boucle elle-même est celle du niveau 2 ; la seule nouveauté, ce sont les outils qu'il reçoit.

import { OpenAIProvider, createLocalAgent, tool } from 'astorlm'
import { z } from 'zod'

// Any OpenAI-compatible endpoint: OpenAI, Ollama, LM Studio, vLLM, a proxy…
const provider = new OpenAIProvider({
  baseURL: 'http://localhost:11434/v1', // e.g. Ollama's default address
  model: 'your-model', // e.g. 'llama3.1', 'gpt-4o-mini'
  apiKey: 'YOUR_API_KEY', // local servers usually ignore it
})

// Your own game functions, wrapped as tools: a name, a description and an input schema.
const askVillager = tool({
  name: 'ask_villager',
  description: 'Ask someone in the village what they saw. Returns what they say.',
  schema: z.object({ name: z.string().describe('Who to ask, e.g. "fisher" or "baker"') }),
  execute: async ({ name }) => world.villager(name).say(),
})

const searchArea = tool({
  name: 'search_area',
  description: 'Search one spot on the map. Returns what is found there, if anything.',
  schema: z.object({ area: z.string().describe('A named spot, e.g. "old oak" or "bridge"') }),
  execute: async ({ area }) => world.search(area),
})

// The model decides which tools to call, in what order, and when to stop.
const agent = await createLocalAgent({
  provider,
  tools: [askVillager, searchArea],
  maxTurns: 5, // a cap on the laps, in case it never settles
})

await agent.run('I lost the key to the village chest. Where is it?') // "In the crow's nest on the old oak"

Quand en utiliser un, et ce que ça coûte

  • Utilisez-en un quand vous ne pouvez pas écrire les étapes à l'avance. La clé pourrait être dans un nid, sous un pont ou déjà vendue à la boutique : dans du code, chaque nouveau cas est une branche de plus. L'agent les gère avec la même boucle, tant qu'il a les outils.
  • Chaque étape est un appel au modèle. Deux outils ont signifié trois appels ici. Plus d'étapes, c'est plus de latence et plus de tokens : plafonnez les tours avec maxTurns.
  • La même question peut prendre un autre chemin. Journalisez le chemin choisi par le modèle, pour comprendre pourquoi une réponse est sortie comme elle est sortie.
  • Les outils sont la frontière. Le modèle ne peut faire que ce que vos outils permettent. Ce que vous lui donnez, c'est ce qu'il peut casser.