Process-compose: Docker Compose sans les conteneurs

date: Nov 22 2025 5 min de lecture

Tes BDD dans Podman, ton code en process. Le meilleur des deux mondes, orchestré proprement.

.docker.devops.development.tools

J’ai besoin de Postgres et Redis pour le dev local. Plus mon API Rust avec hot reload et un frontend Vite

Tout mettre dans Docker Compose ? Même avec des volumes montés, le hot reload rame. Les file watchers ratent des changements. Le HMR de Vite plante une fois sur deux. Les permissions de fichiers mettent le bordel sur Linux

Tout lancer en process natifs ? Là tu te tapes la gestion des versions Postgres et des configs Redis à la main

Je mixe les deux. Les BDD dans des conteneurs. Le code en process. Un seul outil pour orchestrer le tout

Ce que fait process-compose

C’est un orchestrateur de process et de conteneurs. Pas l’un ou l’autre. Les deux

Tu définis ce qui tourne, les dépendances, les health checks. Il démarre tout dans l’ordre, surveille, redémarre en cas d’échec, avec des logs unifiés

version: "0.5"

processes:
  postgres:
    command: podman run --rm -p 5432:5432 -e POSTGRES_PASSWORD=dev postgres:15
    readiness_probe:
      exec:
        command: pg_isready -h localhost
      initial_delay_seconds: 3

  redis:
    command: podman run --rm -p 6379:6379 redis:7

  api:
    command: cargo watch -x run
    depends_on:
      postgres:
        condition: process_healthy
      redis:
        condition: process_healthy

  frontend:
    command: npm run dev
    depends_on:
      api:
        condition: process_healthy

Les BDD tournent dans Podman avec les images officielles, zéro config. Ton code tourne en natif avec le hot reload qui fonctionne.

Une commande process-compose, tout démarre dans le bon ordre.

Pourquoi des conteneurs pour les BDD

Postgres, Redis, Elasticsearch. Ils ont tous des images officielles. Versionnées, testées, prêtes à l’emploi.

Tu veux Postgres 15 ? podman run postgres:15. C’est fait. Pas de prise de tête avec le package manager. Pas de conflits de version. Pas de configs qui traînent.

Besoin de Postgres 14 pour un autre projet ? Port différent, conteneur différent. Ils ne se marchent pas dessus.

Les conteneurs isolent les BDD. Tes changements de code n’y touchent pas. L’état persiste dans des volumes. Séparation propre.

Pourquoi des process pour ton code

Rust avec cargo watch. TypeScript avec Vite. Go avec air. Ils ont tous le hot reload intégré.

Tu les wraps dans des conteneurs ? Le hot reload plante. Les file watchers ne voient pas les changements. Les rebuilds sont lents.

Tu les lances en process. Les changements de fichiers déclenchent une recompilation instantanée. Le HMR fonctionne. Les debuggers s’attachent facilement.

Ton code, c’est ce qui change constamment. Garde ça rapide.

Config réelle pour une stack web

version: "0.5"

environment:
  - DATABASE_URL=postgresql://postgres:dev@localhost:5432/myapp
  - REDIS_URL=redis://localhost:6379

processes:
  db:
    command: podman run --rm -p 5432:5432 -v postgres-data:/var/lib/postgresql/data -e POSTGRES_PASSWORD=dev postgres:15
    availability:
      restart: on_failure
    readiness_probe:
      exec:
        command: pg_isready -h localhost
      initial_delay_seconds: 2
      period_seconds: 1

  redis:
    command: podman run --rm -p 6379:6379 redis:7
    availability:
      restart: on_failure
    readiness_probe:
      exec:
        command: redis-cli -h localhost ping
      initial_delay_seconds: 1

  migrate:
    command: sqlx migrate run
    depends_on:
      db:
        condition: process_healthy
    availability:
      restart: no

  api:
    command: cargo watch -x 'run --bin api'
    depends_on:
      db:
        condition: process_healthy
      migrate:
        condition: process_completed
      redis:
        condition: process_healthy
    readiness_probe:
      http_get:
        host: localhost
        port: 8080
        path: /health
      period_seconds: 2

  frontend:
    command: npm run dev
    depends_on:
      api:
        condition: process_healthy
    working_dir: ./frontend

Postgres et Redis dans des conteneurs. La migration de BDD s’exécute une fois. L’API Rust avec cargo watch pour le hot reload. Le frontend Vite attend que l’API soit healthy.

Tu changes ton code Rust. cargo watch recompile en 500ms. Pas de rebuild d’image. Pas de restart de conteneur.

La TUI montre tout

Tu lances process-compose et tu as une interface terminal qui affiche :

  • Tous les process, conteneurs et natifs
  • Le statut : running, healthy, failed
  • Les logs en temps réel
  • Les dépendances visualisées
  • Restart avec r

Les logs du conteneur Postgres. La sortie de compilation Rust. Les messages HMR de Vite. Tout au même endroit.

Tu tapes 1 pour les logs du process 1. l pour tous les logs. q pour quitter. Tout s’arrête proprement.

Health checks qui marchent vraiment

processes:
  api:
    command: cargo watch -x run
    readiness_probe:
      http_get:
        host: localhost
        port: 8080
        path: /health
      initial_delay_seconds: 5
      period_seconds: 3
      timeout_seconds: 2

Des health checks pour les process natifs. HTTP, exec, TCP. Comme Kubernetes, mais en local.

Le frontend ne démarre pas tant que l’API n’est pas healthy. Pas juste “démarrée”, vraiment en train de servir des requêtes.

Les conteneurs ont aussi des health checks :

processes:
  db:
    command: podman run --rm postgres:15
    readiness_probe:
      exec:
        command: pg_isready -h localhost

Les dépendances attendent la vraie santé. Pas de race conditions.

Combine avec Devbox

Devbox pour tes outils de dev. process-compose pour les lancer

{
  "packages": [
    "podman",
    "postgresql",
    "redis",
    "rustup",
    "nodejs",
    "process-compose"
  ],
  "shell": {
    "init_hook": [
      "rustup default stable"
    ]
  }
}

devbox shell te donne Podman, les outils clients Postgres, Node, Rust et process-compose. Les mêmes versions partout.

Tu ajoutes .envrc :

use devbox
export DATABASE_URL=postgresql://postgres:dev@localhost:5432/myapp
export REDIS_URL=redis://localhost:6379

direnv allow charge tout. process-compose démarre ta stack.

Devbox gère les outils. Podman gère les BDD. process-compose orchestre. Séparation claire.

Quand utiliser des conteneurs pour le code

Tu build pour la prod. Tu as besoin de l’environnement d’exécution exact.

Tu testes le Dockerfile réel. Tu vérifies que ça marche avant de déployer.

Multi-stage builds où la conteneurisation fait partie du processus de build.

Mais le dev quotidien avec hot reload ? Les process gagnent.

Si t’es obsédé par les conteneurs

Tu aimes vraiment Docker Compose et lancer une commande podman run te semble contre nature ? Utilise Docker Compose DANS process-compose

version: "0.5"

processes:
  infra:
    command: docker compose -f infra.yml up
    working_dir: ./infra
    shutdown:
      command: docker compose -f infra.yml down

  api:
    command: cargo watch -x run
    depends_on:
      infra:
        condition: process_healthy

  frontend:
    command: npm run dev
    depends_on:
      api:
        condition: process_healthy

Ton infra.yml contient tous tes services conteneurisés (Postgres, Redis, etc.), et process-compose le lance comme un seul process. Garde ton Docker Compose pour l’infra, ton code en process natifs.

Le meilleur ? Quand tu quits process-compose, il exécute automatiquement docker compose down. Tout se nettoie proprement.

Plusieurs environnements, même config

Le dev utilise des conteneurs pour les BDD :

processes:
  db:
    command: podman run --rm postgres:15

La CI utilise du vrai Postgres :

processes:
  db:
    command: postgres -D /ci/postgres

Même fichier process-compose.yaml, environnement différent. Override avec process-compose -f base.yaml -f ci.yaml.

Démarrer

Installe process-compose :

# Arch
yay -S process-compose

# Avec Devbox
devbox add process-compose

# Manuel
wget https://github.com/F1bonacc1/process-compose/releases/latest/download/process-compose_linux_amd64.tar.gz
tar xf process-compose_linux_amd64.tar.gz
sudo mv process-compose /usr/local/bin/

Crée process-compose.yaml :

version: "0.5"

processes:
  db:
    command: podman run --rm -p 5432:5432 -e POSTGRES_PASSWORD=dev postgres:15

  app:
    command: cargo watch -x run
    depends_on:
      db:
        condition: process_started

Lance :

process-compose

Le conteneur Postgres démarre. L’app Rust attend qu’il soit prêt, puis se lance avec le hot reload. Les logs streamés dans la TUI.

Tu changes le code. cargo watch recompile. Pas de rebuild de conteneur.

Comparaison réelle

Docker Compose pour tout :

  • Les BDD : ça marche bien
  • Le code : rebuilds lents, hot reload cassé, problèmes de permissions sur les volumes
  • Logs : docker compose logs -f service
  • Restart : docker compose restart
  • Changement de code : rebuild d’image

process-compose en mixant :

  • Les BDD : conteneurs, images officielles
  • Le code : process natifs, hot reload qui marche
  • Logs : TUI unifiée
  • Restart : tu tapes r
  • Changement de code : hot reload automatique

J’ai basculé un projet Rust + TypeScript sur ce setup. Les changements de code sont passés de 8 secondes de rebuild Docker à 500ms de hot reload. Le HMR de Vite s’est remis à fonctionner. Le debugging est devenu bien plus simple.

Les BDD dans des conteneurs. Isolées, reproductibles. Le code en process. Rapide, debuggable.

Le meilleur des deux mondes.

Vous avez aimé cet article ? Partagez-le !

Sofiane Djerbi
Sofiane Djerbi

Architecte Cloud & Kubernetes, Expert FinOps.

Commentaires