Monitoring as Code
Monitoring as Code
Monitoring as Code vous permet de définir votre configuration de monitoring LoadFocus sous forme de fichiers versionnés et de l'appliquer depuis la ligne de commande ou la CI — de la même façon que vous gérez votre infrastructure avec Terraform ou Pulumi. Vous décrivez les moniteurs, groupes, alertes, fenêtres de maintenance, tableaux de bord et pages de statut que vous voulez ; la CLI @loadfocus/monitoring calcule la différence par rapport à ce qui est en production et la réconcilie (création, mise à jour, suppression).
C'est déclaratif et idempotent : exécuter deploy deux fois ne change rien la seconde fois. Vos fichiers sont la source de vérité, donc les changements passent par des pull requests et l'historique de votre monitoring vit dans git.
Tout s'exécute dans votre compte et votre équipe active, avec les limites de votre offre appliquées par le backend LoadFocus exactement comme dans le tableau de bord. La CLI ne fait que ce que vous pourriez faire vous-même dans l'interface.
Comment ça marche
Vous conservez un dossier de petits fichiers YAML (ou JavaScript) — une ressource par fichier — plus un loadfocus.config.yaml qui pointe vers eux. La CLI envoie ces définitions à LoadFocus, qui les associe aux ressources en production, calcule le diff et renvoie un plan. Vous examinez le plan, puis vous l'appliquez.
- Rédiger — décrivez les ressources sous forme de fichiers (constructs YAML ou JS).
- Planifier —
deploy --dry-runmontre exactement ce qui sera créé, mis à jour, adopté ou supprimé. - Appliquer —
deployréconcilie votre compte pour qu'il corresponde aux fichiers. - Réconcilier l'identité — chaque ressource porte un
logicalIdstable que vous choisissez. C'est ainsi que la CLI suit une ressource à travers les renommages, de sorte que changer le nom d'affichage d'une vérification ne la recrée jamais.
Installation
La CLI est un package Node (Node 18+). Exécutez-la à la demande avec npx :
npx @loadfocus/monitoring --help
…ou installez-la globalement pour obtenir la commande loadfocus-monitoring :
npm install -g @loadfocus/monitoringloadfocus-monitoring --help
Authentification
La CLI s'authentifie avec une clé d'API LoadFocus et un id d'équipe. Trouvez votre clé d'API dans le tableau de bord sous les paramètres de votre compte/API, et votre id d'équipe sur la page des équipes.
Connectez-vous une fois et les identifiants sont enregistrés dans ~/.loadfocus/config.json :
loadfocus-monitoring loginloadfocus-monitoring whoami # confirm who you are and which team you're targeting
Pour la CI, préférez les variables d'environnement (elles ont priorité sur la configuration enregistrée et ne touchent jamais le disque) :
export LOADFOCUS_API_KEY="apikey_xxxxxxxx"export TEAM_ID="team_xxxxxxxx"# optional: export API_URL="https://apimonitor.loadfocus.com"
Créer un projet
Générez un fichier de configuration et un moniteur d'exemple dans votre dépôt :
loadfocus-monitoring init
Cela écrit loadfocus.config.yaml :
project: my-project # a namespace for this set of resourcescheckMatch:- "monitors/**/*.{check,group,alertRule,maintenanceWindow,dashboard,statusPage,alertChannel,variable}.{yaml,yml,js}"defaults:schedule: "300" # applied to checks that omit a schedulelocations: [us-east-1]
projectdélimite tout ce que la CLI gère. Les ressources d'un projet sont réconciliées ensemble ; tout ce qui est dans le projet et qui ne figure plus dans vos fichiers est supprimé audeploy. Utilisez des projets distincts pour gérer des ensembles de moniteurs indépendants.checkMatchest le ou les globs de vos fichiers de rédaction.defaultsrenseigneschedule,locationsetalertChannelspour les vérifications qui les omettent.
Le workflow
loadfocus-monitoring validate # compile locally + server-side dry-run; great as a PR gateloadfocus-monitoring deploy --dry-run # show the plan (created / updated / adopted / deleted)loadfocus-monitoring deploy # apply itloadfocus-monitoring list # inventory of what's deployed in the projectloadfocus-monitoring list --status # …with each check's latest up/down/degraded statusloadfocus-monitoring get <logicalId> # show one deployed resourceloadfocus-monitoring trigger <logicalId> # run a check nowloadfocus-monitoring destroy # delete everything managed in the project
deploy est sûr par défaut : il montre le plan et, lorsqu'il est exécuté de manière interactive, demande avant de supprimer quoi que ce soit. En CI (non interactif), il refuse de supprimer sans --yes et se termine avec un code clair plutôt que de rester bloqué sur une invite. Ajoutez --json aux commandes de lecture/résultat pour une sortie exploitable par machine.
Adopter des moniteurs existants
Vous avez déjà des moniteurs dans le tableau de bord ? Importez-les dans des fichiers au lieu de les recréer :
loadfocus-monitoring import --project my-project --out monitors
Cela écrit un fichier par ressource et un loadfocus.config.yaml. Examinez, validez (commit), puis exécutez deploy --dry-run — les ressources correspondantes sont adoptées sur place (prises en gestion) plutôt que dupliquées.
Ressources
Chaque ressource est un fichier avec un kind, un logicalId (votre identifiant stable) et les champs propres à ce kind. Les références entre ressources utilisent des logicalId (ou des noms pour les canaux d'alerte) — le serveur les résout, et l'ordre de déploiement est géré pour vous.
Vérifications
Un seul kind Monitor couvre chaque type de vérification via type : api, browser, multistep, tcp, heartbeat.
kind: checktype: apilogicalId: homename: Home APIschedule: "300" # seconds between runslocations: [us-east-1, eu-west-1]request:url: "https://example.com/health"method: GETassertions:- { type: statusCode, comparison: equals, value: 200 }- { type: responseTime, comparison: lessThan, value: 1000 }
- api — requête HTTP avec des assertions sur le statut, le corps, les en-têtes, le temps de réponse, l'expiration SSL.
- browser — un script de parcours utilisateur Playwright avec captures d'écran et chronométrages par étape (payant).
- multistep — une séquence ordonnée de requêtes API qui passent des données entre les étapes.
- tcp — une vérification de port/joignabilité depuis plusieurs régions.
- heartbeat — un dispositif d'homme mort : un job externe ping une URL selon une planification, et LoadFocus alerte si un ping est manqué.
Groupes
Partagez les régions, les canaux d'alerte, la fréquence et l'activation entre plusieurs vérifications. Une vérification rejoint un groupe avec group: <logicalId>.
kind: grouplogicalId: webname: Web serviceslocations: [us-east-1, eu-west-1]
Règles d'alerte
Alerter quand une métrique d'une vérification franchit un seuil.
kind: alertRulelogicalId: home-latencyname: Home API latencycheck: home # reference a check by logicalIdmetric: responseTime # responseTime | statusCode | durationcondition: aboveconditionValue: 1500 # milliseconds
Canaux d'alerte
Gérez les canaux de notification en tant que code et référencez-les par leur nom depuis une vérification, un groupe ou une règle d'alerte. Types (type) pris en charge : email, slack, microsoftteams, webhook, discord, pagerduty, opsgenie. Les champs secrets (webhookUrl, routingKey, apiKey) acceptent une référence {{secrets.NAME}} — la valeur est stockée avec env set-secret et résolue lors de l'envoi d'une alerte, jamais versionnée dans vos fichiers.
kind: alertChannellogicalId: oncall # the name checks / groups / alert rules referencetype: pagerdutyroutingKey: "{{secrets.PAGERDUTY_KEY}}"
Fenêtres de maintenance
Supprimer les alertes pendant des travaux planifiés. Les horaires sont en UTC. startsAt / endsAt acceptent une chaîne ISO-8601 (par ex. "2026-07-01T00:00:00Z") ou des millisecondes unix.
kind: maintenanceWindowlogicalId: weekly-deployname: Weekly deploy windowenabled: truestartsAt: "2026-07-01T00:00:00Z" # ISO-8601 or unix msendsAt: "2026-07-01T02:00:00Z"repeat: weekly # none | daily | weekly | monthlyweekdays: [2] # 0=Sun … 6=Sattargets:allChecks: falsecheckIds: [home] # by logicalId
Tableaux de bord
Une vue partagée de vérifications sélectionnées, éventuellement publique via un slug.
kind: dashboardlogicalId: status-overviewname: Status overviewvisibility: private # private | publicchecks: [home] # by logicalIdwindow: 24h # 24h | 7d | 30d
Pages de statut
Une page de statut publique à <slug>.loadfoc.us, éventuellement sur votre propre domaine personnalisé.
kind: statusPagelogicalId: public-statustitle: Acme Statusslug: acme # -> acme.loadfoc.us (globally unique)enabled: truecustomDomain: status.acme.com # optional, paid; point a CNAME at cname.loadfoc.usgroups:- { id: core, name: Core Services, order: 0 }components:- id: apiname: APIgroupId: coremonitors: [home] # checks shown on this component, by logicalIdbranding:brandColor: "#5353a4"colorTheme: dark
Un domaine personnalisé est mis en service une fois que vous créez le CNAME et que le certificat est émis — deploy le déclare ; la vérification se fait hors bande.
Variables
Valeurs non secrètes (URLs de base, identifiants) que les vérifications référencent au moment de l'exécution via {{vars.NAME}}. Le logicalId est la clé de la variable. (Pour les secrets, utilisez env set-secret — ne les placez jamais dans des fichiers.)
kind: variablelogicalId: BASE_URLvalue: "https://api.example.com"
Rédiger en JavaScript ou TypeScript
Si vous préférez le code au YAML, construisez les mêmes définitions de manière programmatique et exportez-les — les constructs produisent des ressources identiques :
const { Monitor, Group, AlertRule, Maintenance, Dashboard, StatusPage, AlertChannel, Variable } = require('@loadfocus/monitoring');new Monitor({type: 'api', logicalId: 'home', name: 'Home API', schedule: '300',locations: ['us-east-1'],request: { url: 'https://example.com/health', method: 'GET' },assertions: [{ type: 'statusCode', comparison: 'equals', value: 200 }],});new Group({ logicalId: 'web', name: 'Web services', locations: ['us-east-1'] });
Pointez checkMatch vers vos fichiers .js et la CLI les charge comme n'importe quelle autre ressource.
Secrets et variables
Référencez des valeurs depuis vos vérifications sans les versionner. Les secrets (jetons, mots de passe) sont gérés uniquement de manière impérative et référencés via {{secrets.NAME}} dans les champs de vérification et les champs secrets des canaux d'alerte. Les variables (non secrètes) peuvent être déclarées sous forme de fichiers (kind: variable, ci-dessus) ou définies de manière impérative, et sont référencées via {{vars.NAME}}.
loadfocus-monitoring env set-secret API_TOKEN "s3cr3t"loadfocus-monitoring env set-variable BASE_URL "https://example.com"loadfocus-monitoring env ls # list secret + variable keys (values never shown)
L'exécuter en CI
Un pipeline typique valide à chaque pull request et déploie à la fusion sur la branche principale.
# .github/workflows/monitoring.ymlname: monitoringon:pull_request:push:branches: [main]jobs:monitoring:runs-on: ubuntu-latestenv:LOADFOCUS_API_KEY: ${{ secrets.LOADFOCUS_API_KEY }}TEAM_ID: ${{ secrets.LOADFOCUS_TEAM_ID }}steps:- uses: actions/checkout@v4- uses: actions/setup-node@v4with: { node-version: 20 }- run: npx @loadfocus/monitoring validate- if: github.ref == 'refs/heads/main'run: npx @loadfocus/monitoring deploy --yes
Bon à savoir
logicalIdest l'identité. Gardez-le stable. Vous pouvez renommer librement lenameou letitled'une vérification ; changer sonlogicalIdest traité comme la suppression d'une ressource et la création d'une autre.- Les suppressions sont limitées au projet.
deployne retire que les ressources duprojectcourant qui ne figurent plus dans vos fichiers — jamais quoi que ce soit dans un autre projet ou créé en dehors de Monitoring as Code (jusqu'à ce que vous l'adoptiez). - Les slugs de page de statut sont globaux.
slugdevient un sous-domaine, il doit donc être unique parmi tous les clients LoadFocus. - Les fonctionnalités payantes échouent bruyamment. Une équipe gratuite qui déclare un champ réservé aux offres payantes (un domaine personnalisé de page de statut, la suppression du badge « Powered by ») reçoit une erreur claire au
deployplutôt qu'un résultat partiel silencieux. - Les limites d'offre s'appliquent. Créer des ressources via la CLI est soumis aux mêmes quotas d'offre que le tableau de bord.