Un jeton MCP, c'est le mot de passe de votre compte avec une API branchée dessus. Confiez-le à un agent et vous obtenez un utilisateur qui ne se fatigue jamais, lit toutes les pages qu'on lui indique et fait exactement ce que dit la dernière consigne de son contexte. La plupart du temps, c'est ce que vous voulez. Cette page parle du reste du temps.
Tout ce qui suit a été vérifié sur le serveur en production à la date indiquée en haut : la liste des outils vient de tools/list sur https://mcp.eqvps.com/mcp, les limites de l'API elle-même. Si vous découvrez le serveur, commencez par connecter un client MCP et les jetons API, puis revenez ici.
Modèle de menace : ce qui tourne mal en pratique
Trois choses, dans l'ordre où nous les voyons :
- L'agent comprend de travers. « Nettoie la machine de test » devient la réinstallation du mauvais serveur. Aucune malveillance, juste un modèle qui comble un trou dans la consigne.
- L'injection de prompt. L'agent lit un texte que vous n'avez pas écrit (un README, une réponse du support, une page récupérée sur le web) et ce texte lui dit de faire quelque chose. Si l'agent détient un jeton avec tous les droits, la consigne injectée les a aussi.
- Le jeton fuite. Il atterrit dans un historique shell, un dépôt public, une config MCP partagée ou une ligne de log.
Le serveur MCP vérifie que le jeton est valide et que le serveur appartient à ce compte (ou lui est délégué). Il ne sait pas ce que vous vouliez dire. Chaque garde-fou ci-dessous répond à une seule question : quels dégâts sont possibles quand la consigne est fausse ?
Tous les outils MCP, par niveau de risque
Un jeton client voit 45 outils (serveur MCP 1.6.0). Un jeton revendeur (rk_…) voit un ensemble distinct de 30 outils revendeur et aucun de ceux-ci, l'endpoint en compte donc 75 au total. Votre client ne reçoit que son propre ensemble via tools/list.
Cette page classe les outils par niveau de risque. Les paramètres et exemples d'appels de chaque outil sont dans la référence des paramètres ; tous les outils en une ligne, y compris les 30 outils revendeur, sont dans la liste complète.
Nous ne publions pas encore d'annotations d'outils MCP (readOnlyHint, destructiveHint), votre client ne peut donc pas les trier seul. Réglez les validations à la main d'après les niveaux ci-dessous.
Niveau 0 — public, sans jeton (5)
| Outil | Ce qu'il fait |
|---|---|
get_started | Tout le parcours en une réponse : quels outils appeler, dans quel ordre |
list_plans | Offres, prix, images d'OS |
sandbox_pricing | Tarifs des sandboxes |
register_account | Crée un nouveau compte et renvoie son jeton |
login | E-mail + mot de passe → jeton |
Niveau 1 — lecture du compte, sans effet de bord (15)
| Outil | Ce qu'il fait | Attention |
|---|---|---|
whoami | Identifiant, nom, e-mail du compte | |
get_balance | Solde prépayé | |
list_vps | Serveurs actifs, en création et suspendus | |
get_vps_status | État, caractéristiques, informations d'accès | Avec reveal: true, renvoie le mot de passe root |
get_vps_metrics | CPU, mémoire, réseau, disque dans le temps | |
get_upgrade_options | Offres vers lesquelles le serveur peut passer sans réinstallation | |
list_delegations | À qui vous avez donné accès | |
list_delegated_to_me | Serveurs que d'autres vous ont délégués | |
list_tickets | Vos tickets de support | |
get_ticket | Un ticket et son fil | Le texte du ticket est une entrée non fiable pour l'agent |
list_sandboxes | Vos sandboxes | |
get_sandbox | Une sandbox et sa consommation | |
get_task | Sortie d'une tâche en arrière-plan | |
download_file | Lit un petit fichier dans une sandbox | |
get_download_url | Lien temporaire vers un fichier de sandbox | Quiconque a le lien peut télécharger jusqu'à son expiration |
Niveau 2 — modifie l'état, ne dépense rien (17)
| Outil | Ce qu'il fait | Attention |
|---|---|---|
power_vps | start / stop / reboot | Un stop est un stop : les services tombent |
set_hostname | Renomme le serveur | Modifie la valeur que confirm vérifie |
undo_cancel | Retire une résiliation programmée en fin de période | |
refresh_token | Nouveau jeton, l'ancien est révoqué aussitôt | Mettez à jour toute config statique ensuite |
set_password | Définit le mot de passe du compte s'il n'en a pas | Le détenteur du jeton peut le définir avant vous |
topup_balance | Facture de recharge + lien de paiement crypto | Le régler exige un portefeuille |
pay_invoice | Lien de paiement pour une facture impayée | Idem |
accept_delegation | Accepte une invitation | |
revoke_delegation | Met fin à une délégation | |
create_ticket / reply_ticket / close_ticket | Tickets de support | L'agent écrit au support en votre nom |
run_code / exec_command | Exécute du code dans une sandbox | Dans la sandbox uniquement, pas sur votre VPS |
kill_task | Arrête une tâche de fond de la sandbox | |
upload_file / get_upload_url | Dépose un fichier dans une sandbox |
Niveau 3 — dépense, détruit des données ou accorde un accès (8)
| Outil | Ce qu'il fait | Contrôle côté serveur |
|---|---|---|
order_vps | Commande un serveur, payé sur le solde | Solde insuffisant → facture impayée, rien n'est débité |
change_plan | Changement d'offre sans réinstallation, différence débitée du solde | confirm: true ; solde insuffisant → 402 |
create_sandbox | Lance une sandbox facturée | Solde vide → 402 |
reinstall_vps | Efface le disque et installe un nouvel OS | confirm = nom d'hôte exact ou DELETE ; 4 appels/min |
reset_password | Nouveau mot de passe root, l'ancien cesse de fonctionner | confirm = nom d'hôte ou DELETE ; 6 appels/min |
cancel_service | end_of_period (par défaut, annulable) ou immediate (détruit le serveur tout de suite) | immediate exige confirm = nom d'hôte |
kill_sandbox | Supprime une sandbox et ses fichiers | aucun |
delegate_service | Donne à une autre personne un accès opérateur à un serveur | Propriétaire uniquement ; la personne doit accepter |
Journal des changements de l'ensemble d'outils
| Date | Version du serveur | Changement | Effet sur le risque |
|---|---|---|---|
| 2026-10-03 | 1.6.0 | Ajout de refresh_token ; les jetons durent 1 an par défaut | Niveau 2 |
| 2026-10-03 | 1.5.0 | undo_cancel, get_upgrade_options, change_plan | change_plan dépense le solde → niveau 3 |
| 2026-10-03 | 1.1.0 | 13 outils de sandbox | create_sandbox dépense, kill_sandbox détruit → niveau 3 |
La version en service est publique : curl -s https://mcp.eqvps.com/healthz. Quand elle change, ce tableau change avec elle.
Le solde est le plafond de dépenses
EQVPS fonctionne en prépayé. Pas de carte enregistrée, pas de ligne de crédit, pas de découvert : le maximum qu'un agent puisse dépenser, c'est ce qui se trouve sur le solde. Trois outils dépensent : order_vps, change_plan et create_sandbox. Les renouvellements de vos serveurs existants sortent du même solde.
L'agent peut créer des demandes de paiement, pas les régler. topup_balance et pay_invoice renvoient un lien de paiement crypto, et un lien ne fait rien sans portefeuille derrière. Il n'existe pas non plus d'endpoint de retrait : l'argent du solde peut acheter des services dans votre compte, pas en sortir. Les remboursements d'une résiliation immédiate reviennent eux aussi sur le solde.
Une réserve, et elle est réelle. Si vous gardez le solde très bas pour brider l'agent, vos propres renouvellements échouent et vos serveurs passent en période de grâce. Notre règle empirique : un cycle de renouvellement de ce que vous faites déjà tourner, plus le budget de la tâche en cours de l'agent. Le guide du budget d'agent détaille le calcul. Et si vous donnez à l'agent son propre portefeuille approvisionné, ce portefeuille devient un second plafond à surveiller.
Moindre privilège : pas (encore) de jeton en lecture seule
Réponse directe : chaque jeton client a les mêmes droits que le compte dans le tableau de bord. Le nom et la durée de vie d'un jeton se règlent, ses scopes non.
Ce qu'il y a de plus restreint aujourd'hui, c'est la délégation. Vous donnez à l'agent son propre compte, avec un solde à zéro, et vous lui déléguez un serveur :
delegate_service { "service_id": "EQ-XXXX", "email": "agent@yourdomain.com", "expires_days": 30 }
La même chose en REST :
curl -s -X POST "https://api.eqvps.com/api/v1/eqvps/services/EQ-XXXX/delegations" \
-H "Authorization: Bearer $EQVPS_TOKEN" -H "Content-Type: application/json" \
-d '{"email":"agent@yourdomain.com","expires_days":30}'
L'invitation doit être acceptée en étant connecté avec cet e-mail (accept_delegation), et expires_days va de 1 à 365. Pas à pas avec captures d'écran : déléguer un accès et l'accès dans la documentation.
| Un compte délégué peut | Un compte délégué ne peut pas |
|---|---|
| Voir l'état, les métriques et l'historique de ce seul serveur | Voir vos autres serveurs, votre solde ou vos factures |
| Démarrer, arrêter, redémarrer | Résilier, renouveler ou changer d'offre |
| Définir le nom d'hôte et le DNS inverse | Acheter des options ou des IP |
| Réinitialiser le mot de passe root | Ouvrir la console web |
| Réinstaller l'OS | Déléguer le serveur à quelqu'un d'autre |
Regardez les deux dernières lignes de gauche. Un délégué ne peut pas dépenser votre argent, mais il peut effacer ce serveur. Activez les sauvegardes sur tout serveur qu'un agent peut réinstaller.
Hygiène des jetons
Un jeton par agent, avec un nom. Créez-le dans Tableau de bord → Paramètres → Jetons API pour agents, ou ainsi :
curl -s -X POST "https://api.eqvps.com/api/v1/eqvps/auth/tokens" \
-H "Authorization: Bearer $EQVPS_TOKEN" -H "Content-Type: application/json" \
-d '{"name":"backup-agent","expires_in_days":90}'
Le jeton n'est affiché qu'une fois. Durée de vie de 1 à 1825 jours, 365 si vous ne précisez rien. Pour un agent, nous choisirions 90.
Gardez-le dans un fichier que vous seul pouvez lire, pas dans le dépôt, pas dans le prompt, pas dans une variable shell que vous copiez partout :
mkdir -p ~/.config/eqvps && chmod 700 ~/.config/eqvps
( umask 077; read -rsp 'EQVPS token: ' T; echo; printf 'EQVPS_TOKEN=%s\n' "$T" > ~/.config/eqvps/agent.env )
ls -l ~/.config/eqvps/agent.env # attendu : -rw-------
Chargez-le ensuite dans le service de l'agent avec EnvironmentFile= (systemd) ou set -a; . ~/.config/eqvps/agent.env; set +a.
Faites tourner le jeton avant expiration. L'outil refresh_token, ou POST /auth/tokens/{id}/refresh, émet un nouveau jeton du même nom et révoque l'ancien immédiatement. Si votre client MCP a le jeton en dur dans sa config, mettez-la à jour juste après, sinon la session suivante reçoit un 401.
Vérifiez qui utilise quoi : GET /auth/tokens liste chaque jeton avec son nom, son expiration et last_used_at. Un jeton que vous ne reconnaissez pas, ou utilisé après l'arrêt de l'agent, c'est votre signal.
Si un jeton fuite
Dans cet ordre :
- Révoquez-le. Tableau de bord → Paramètres → Jetons API pour agents → Révoquer, ou
curl -s -X DELETE -H "Authorization: Bearer $EQVPS_TOKEN" https://api.eqvps.com/api/v1/eqvps/auth/tokens/<id>. Il cesse de fonctionner dès la requête suivante. - Cherchez de nouveaux jetons que vous n'avez pas créés, et révoquez-les aussi.
- Mesurez la surface touchée : l'historique du service de chaque serveur, vos factures et votre solde, et
list_delegationspour repérer un accès que vous n'avez pas accordé. - Changez les mots de passe root de chaque serveur que ce jeton pouvait voir.
get_vps_statusavecreveal: truelivre le mot de passe root : un jeton divulgué, c'est un mot de passe root divulgué. Vérifiez~/.ssh/authorized_keysau passage. - Fermez la porte du mot de passe. Si votre compte n'a jamais eu de mot de passe, le détenteur du jeton a pu en définir un avec
set_password. Connectez-vous avec un code reçu par e-mail et changez-le.
La prévention pour l'étape 5 ne coûte rien : définissez vous-même un mot de passe de compte dès maintenant, et set_password renverra 409 à tous ceux qui viendront après.
La validation humaine
Ce que le serveur impose :
reinstall_vps,reset_passwordetcancel_serviceavectype: immediateexigentconfirmégal au nom d'hôte exact (DELETEfonctionne aussi pour la réinstallation et la réinitialisation).change_planexigeconfirm: true.- La résiliation se fait par défaut en
end_of_period: le serveur tourne jusqu'à la fin de la période payée, etundo_cancelrevient en arrière. - Limites de débit par compte : réinstallation 4/min, réinitialisation du mot de passe 6/min, alimentation 20/min, commandes 20/min. De quoi empêcher une boucle de le faire cinquante fois, pas d'arrêter un seul mauvais appel.
Soyez lucide sur ce qu'est confirm. Il empêche un agent d'agir sur « fais le ménage ». Il n'arrête pas un attaquant, car le nom d'hôte est à un appel get_vps_status de distance. La vraie validation vit dans votre client MCP. La plupart des clients savent demander avant chaque appel d'outil : laissez passer les niveaux 0 et 1, faites toujours demander pour le niveau 3. Dans les clients qui gèrent des permissions par outil, comme le settings.json de Claude Code (serveur enregistré sous le nom eqvps) :
{
"permissions": {
"ask": ["mcp__eqvps__order_vps", "mcp__eqvps__change_plan", "mcp__eqvps__create_sandbox", "mcp__eqvps__reset_password", "mcp__eqvps__delegate_service"],
"deny": ["mcp__eqvps__reinstall_vps", "mcp__eqvps__cancel_service", "mcp__eqvps__kill_sandbox"]
}
}
Ajoutez aussi une ligne aux instructions de l'agent. Ce n'est pas un contrôle de sécurité en soi, mais cela réduit les malentendus (laissez-la en anglais, les modèles la comprennent aussi bien) :
Never call reinstall_vps, reset_password, cancel_service (type=immediate), change_plan,
order_vps, create_sandbox, kill_sandbox or delegate_service unless the human has typed
the target server's hostname in this conversation for that specific action.
Si l'agent se connecte par code e-mail au lieu de détenir un jeton longue durée, voyez la connexion d'un agent via MCP.
Audit : ce que vous voyez après coup
- Liste des jetons (
GET /auth/tokens, ou Paramètres → Jetons API pour agents) : nom, création, expiration,last_used_at. C'est pour ça qu'il faut nommer les jetons par agent. - Historique du service (tableau de bord, page du serveur) : actions d'alimentation, réinstallations, réinitialisations de mot de passe, changements d'offre, paiements, chacun avec une heure et un auteur : vous, le support ou automatique. Il ne dit pas quel jeton ou délégué a agi, seulement que l'action vient de votre côté.
- Factures et solde : chaque débit et chaque remboursement.
list_delegations: qui a accès à quoi, et jusqu'à quand.
Ce trou dans l'historique du service est la limite honnête de l'audit côté serveur aujourd'hui. Si vous devez savoir quel agent a fait quoi, journalisez chaque appel d'outil avec ses arguments (sans les secrets) côté agent.
La configuration que nous choisirions
Pour un agent qui gère un serveur de production :
- Un compte séparé pour l'agent, solde à zéro, le serveur délégué avec
expires_days: 90. - Votre jeton de propriétaire reste chez vous, dans aucune config d'agent.
- Des sauvegardes sur ce serveur, parce qu'un délégué peut réinstaller.
- Les outils de niveau 3 sur « ask » ou « deny » dans le client.
- Le jeton de l'agent dans un fichier
600, renouvelé avant expiration.
Pour un agent qui doit commander des serveurs ou lancer des sandboxes, la délégation ne suffit pas, puisqu'il lui faut un solde. Le solde devient alors votre plafond : approvisionnez-le par tâche, nommez le jeton et lisez last_used_at une fois par semaine. Si un jeton en lecture seule changeait la façon dont vous déployez vos agents, dites-le-nous au support : ce sont ces retours qui décident de ce que nous construisons ensuite.
Commentaires
Pas encore de commentaires. Soyez le premier.