Des tâches cron à
surveiller, relancer et versionner dans Git

Planifiez, exécutez et surveillez vos tâches cron au même endroit — infrastructure-as-code d’abord, hébergé en UE.

Offre gratuite — sans carte bancaire.

Chaque composant, et où il s'exécute

Hébergé dans l'UE sur une VM Hetzner en Allemagne, derrière Cloudflare. Tout le système tient dans une seule vue — et les seuls sous-traitants sont Cloudflare, Paddle et SMTP2GO.

Clients

Browser

steadycron.com

Site & docs

Browser

app.steadycron.com

Interface du tableau de bord

CLI / scripts

api.steadycron.com

REST + manifestes

Your cron

ping.steadycron.com

Pings heartbeat

Cloudflare

DNS · TLS · WAF · CDN

Proxy edge, pare-feu et limitation de débit devant tout le reste.

Cloudflare Pages

Astro · static

Ce site, servi en périphérie — ne touche jamais la VM.

Caddy

reverse proxy

Sur la VM : TLS automatique, route app. / api. / ping. vers les conteneurs.

VM Hetzner · Allemagne · Docker Compose

Dashboard

steadycron-dashboard

Next.js. UI authentifiée ; appelle l'API via le réseau interne.

API + Ping

steadycron-api · .NET

REST · ingestion ping · aperçu cron · variables · activité · admin.

steadycron-scheduler · Quartz.NET clustered

HTTP executor

Polly · SSRF guard

Effectue les appels HTTPS planifiés — réessais, délais, re-vérif des redirections.

Heartbeat watcher

30s tick

Repère les exécutions manquées ou bloquées selon le délai de grâce.

Alert dispatcher

outbox · NOTIFY

Vide l'outbox ; met en forme, livre et réessaie les alertes.

Background workers

×4 services

Flush des envois, détection d'anomalies, purge de rétention, réconciliation Paddle.

PostgreSQL 17

app · Quartz · outbox

Une seule instance pour tout. LISTEN/NOTIFY remplace un broker — pas de Redis.

Backups

nightly · encrypted

pg_dump chiffré, stocké hors site ; tests de restauration trimestriels.

Services externes & vos systèmes

Your endpoints

the jobs we call

Vos handlers HTTPS, appelés selon le planning.

Alert channels

Slack · Discord · …

Telegram, webhook, e-mail — sortant uniquement.

Paddle

billing · MoR

Merchant of Record — gère la TVA. Aucune donnée de carte ici.

SMTP2GO

email

Vérification, réinitialisation de mot de passe et alertes e-mail.

Observabilité · OpenTelemetry → Grafana auto-hébergé Infrastructure-as-code · Terraform (Cloudflare + Hetzner) Planification · Quartz.NET en cluster (AdoJobStore)

Exécution de tâches HTTP

Nous appelons votre endpoint selon le planning ; vous vous concentrez sur le handler. Un vrai constructeur de requêtes — pas une simple barre d’URL — avec les contrôles que vous devriez sinon bricoler autour du cron système.

  • N’importe quelle méthode — GET, POST, PUT, PATCH, DELETE — avec en-têtes personnalisés et corps JSON
  • Variables de gabarit : placez {{var}} dans l’URL, les en-têtes ou le corps, résolues côté serveur à l’exécution
  • Organisez les tâches avec des tags comme env:prod ou team:backend, puis groupez et filtrez le tableau de bord
  • Réessais configurables avec backoff exponentiel — et seulement sur les codes de statut que vous choisissez
  • Délai d’expiration par tâche et « ignorer si en cours », pour qu’une exécution lente n’empiète jamais sur la suivante
  • Fuseau horaire par tâche avec gestion correcte de l’heure d’été — planifiez en local, exécutez juste toute l’année
  • Chaque exécution entièrement journalisée : statut, corps et durée de la réponse, conservés pour l’audit
  • Exécuter, mettre en pause ou reprendre depuis l’UI — ou synchroniser toute la tâche en YAML ou via la CLI
app.steadycron.com/jobs/new
invoice-send

Request

Configure the HTTP request sent on each execution. Use {{variable}} for template substitution.

POST
{{baseUrl}}/v1/invoices/{{invoiceId}}/send
Send
Params Headers 1 Body

Headers

Authorization Bearer {{apiToken}}
Body raw · JSON
{
  "account_id": "{{accountId}}",
  "amount_cents": 4900,
  "send_email": true
}

Valid JSON

Schedule

When it runs — cron or interval, with DST-correct timezones and a live next-runs preview.

Cron Interval

Cron expression

0 9 * * 1-5

Weekdays at 09:00

Timezone

Europe/Berlin

Next runs

Mon 09:00Tue 09:00Wed 09:00Thu 09:00
timeout 30sretries 3skip if still running

Surveillance heartbeat

Surveillez les tâches cron que vous exécutez déjà, où qu’elles soient. Votre tâche nous envoie un ping ; nous surveillons l’horloge. Si le ping manque — processus planté, serveur redémarré, tâche bloquée — vous le savez avant vos utilisateurs.

  • Un interrupteur « homme mort » pour tout cron, script ou worker — dans n’importe quel langage ou shell
  • Pinguez /start puis /success ou /fail pour mesurer la durée et repérer les tâches mortes en cours
  • Les périodes de grâce absorbent la gigue normale : alerte seulement quand une exécution est vraiment en retard
  • Détecte trois types d’échec : exécutions manquées, échecs explicites et tâches bloquées qui ne finissent jamais
  • Chaque contrôle a une URL de ping stable — renommez la tâche librement, vos scripts continuent de fonctionner
  • Alerte par e-mail, Slack, Discord, Telegram ou webhook — résolue automatiquement au rétablissement
  • Groupez et filtrez par tag : un environnement en échec remonte en haut de la liste
  • Une ligne à intégrer : un simple curl sur l’URL de ping à la fin de votre tâche
app.steadycron.com/jobs

Jobs

New job
Search jobs…
All HTTP Heartbeat
Status Group: env
env:prod 5 jobs 1 failing
weekly-digest-email HTTP 0 9 * * 1 in 2 days 3 days ago
nightly-db-backup Heartbeat 0 2 * * * in 19 h 5 h ago
stripe-reconciliation HTTP 0 */4 * * * in 38 min 3 h ago
cache-warmup HTTP */15 * * * * in 11 min now
search-index-sync Heartbeat */30 * * * * in 6 min 24 min ago
env:dev 3 jobs
seed-test-data HTTP 0 4 * * * in 14 h 10 h ago
preview-env-cleanup Heartbeat 0 */6 * * * in 2 h 4 h ago
trial-expiry-sweep HTTP 0 6 * * * yesterday

Tout définir comme du code

Déclarez tout votre compte — tâches, heartbeats, canaux, tags et variables — dans un manifeste YAML versionné. Réconciliez depuis la CLI ou directement en CI.

  • Un manifeste YAML versionné définit tâches, heartbeats, canaux, tags et variables
  • Adoptez un compte existant en quelques secondes — steadycron export le transforme en manifeste
  • validate → plan → apply, avec des diffs façon Terraform à relire en pull request
  • --prune supprime ce que vous retirez ; les namespaces séparent proprement IaC et tâches manuelles
  • IDs stables : renommer reste renommer — pas de recréation, les URLs de heartbeat sont préservées
  • Les secrets ne touchent jamais Git : ${ENV} est résolu par la CLI, {{template}} par le serveur
  • L’action GitHub publie le plan à chaque PR et l’applique au merge
  • Tout ce que fait la CLI est aussi une API REST — clés scoped, en lecture seule ou complètes
steadycron — bash
$ steadycron jobs list
╭────────────────┬───────────┬─────────┬────────────────────┬──────────┬──────────╮
Name Kind Status Schedule Next run Last run
├────────────────┼───────────┼─────────┼────────────────────┼──────────┼──────────┤
weekly-digest http success 0 9 * * 1 (UTC) in 2d 3d ago
nightly-backup heartbeat late 0 2 * * * (UTC) 5h ago
stripe-recon http failure 0 */4 * * * (UTC) in 38m 3h ago
cache-warmup http running */15 * * * * (UTC) in 11m now
search-sync heartbeat success */30 * * * * (UTC) 24m ago
report-export http success 0 6 * * * (UTC) in 14h 10h ago
token-refresh http success 0 */6 * * * (UTC) in 2h 4h ago
trial-sweep http paused 0 6 * * * (UTC) 1d ago
╰────────────────┴───────────┴─────────┴────────────────────┴──────────┴──────────╯
8 job(s).
$ steadycron cron preview "0 9 * * 1-5" --timezone Europe/Berlin
Next 5 fires of 0 9 * * 1-5 (Europe/Berlin):
╭───┬───────────────────────────┬──────────╮
# Fire time (Europe/Berlin) Relative
├───┼───────────────────────────┼──────────┤
1 2026-06-08 09:00:00 in 3d
2 2026-06-09 09:00:00 in 4d
3 2026-06-10 09:00:00 in 5d
4 2026-06-11 09:00:00 in 6d
5 2026-06-12 09:00:00 in 7d
╰───┴───────────────────────────┴──────────╯
$ steadycron jobs run cache-warmup
triggered cache-warmup · 200 OK · 412 ms
$ steadycron validate manifests/production.yaml
manifest valid · 0 errors
$ steadycron plan manifests/production.yaml
~ weekly-digest update retries: 2 → 3
+ invoice-reminder create kind: http · 0 17 * * 5
- legacy-report destroy (absent from manifest)
Plan: 1 to add · 1 to change · 1 to destroy
$ steadycron apply --prune manifests/production.yaml
apply complete · 1 added · 1 changed · 1 destroyed

Vos questions, nos réponses

Où mes données sont-elles stockées ?

Tout tourne sur l’infrastructure Hetzner en Allemagne, sous droit allemand. L’exécution principale n’utilise aucun sous-traitant américain, et un DPA RGPD est disponible.

Puis-je surveiller des tâches cron qui tournent sur mes propres serveurs ?

Oui. Ajoutez un heartbeat et faites envoyer un ping à votre tâche lorsqu’elle se termine (un simple curl à la fin de votre script). Si le ping n’arrive pas à l’heure prévue, SteadyCron vous alerte. Cela fonctionne depuis n’importe quel langage ou shell.

SteadyCron remplace-t-il AWS EventBridge ou le cron de Cloudflare/Vercel ?

Pour les tâches HTTP planifiées, oui. SteadyCron appelle votre point de terminaison à l’heure prévue, avec réessais, délais d’expiration et journaux complets requête/réponse — sans vous enfermer dans un cloud. La surveillance et les alertes sont au même endroit.

En quoi est-ce différent de Healthchecks.io ?

Healthchecks excelle dans la surveillance heartbeat. SteadyCron fait les deux moitiés — il exécute vos tâches HTTP et surveille les heartbeats depuis un seul tableau de bord — et il est hébergé en UE avec des workflows infrastructure-as-code intégrés.

Existe-t-il une offre gratuite ?

Oui — 4 tâches HTTP et 12 heartbeats, gratuits pour toujours, sans carte bancaire. Les offres payantes démarrent à 10 €/mois.

Puis-je définir mes tâches comme du code ?

Oui. Définissez vos tâches dans un manifeste YAML et synchronisez-les avec steadycron sync jobs.yaml via la CLI, ou utilisez directement l’API REST. Pas de click-ops, pas de dérive entre environnements.