Skip to main content

Understanding the depends_on condition in Docker compose files

Prevent startup errors in your multi-service applications. Learn to use the healthcheck property and depends_on condition service_healthy in Docker Compose to ensure your application waits for the database to be fully ready before starting.

· 4 min read
View raw
Christophe
Markdown, WSL and Docker lover ~ Insatiable curious.
Cet article existe aussi en français — lire la version française.

This article is over a year old but was reviewed on July 30, 2026 — the content is still accurate.

Understanding the depends_on condition in Docker compose files

⚡
TL;DR

This article explains how to prevent an application container from starting before its database is ready, using Docker Compose's healthcheck property (to define when a service is considered ready) combined with depends_on: condition: service_healthy on the dependent service — replacing fragile manual retry-loop scripts.

It's only been ten days or so since I learned the trick, even though it was well documented: managing service startups and, above all, blocking one if the other isn't ready (official documentation).

Imagine a two-service application like Joomla (see my Create your Joomla website using Docker), WordPress, LimeSurvey, Laravel and many, many more use cases: you've an application and that application requires a database.

This article is about waiting for a healthy service; Get health information from your running containers is about reading that health status from the command line. And FrankenPHP, a modern application server for PHP shows exactly the kind of "Connection refused" storm you get without it.

You've, roughly speaking, a compose.yaml file like this:

services:
joomla:
image: joomla
[...]
joomladb:
image: mysql:8.0.13
[...]

This is a Docker Compose configuration that sets up two services: a Joomla web application and a MySQL database it depends on. The configuration defines which container images to use for each service, allowing them to run together as a coordinated application stack.

And, yeah, it works. You can execute docker compose up --detach and wait until the two services are up and, sooner or later, you'll get your application ready.

But you have the intuition that something isn't quite right here... What happens if the database service is slow to load? You'd have the application (Joomla here, but it doesn't really matter) which, in its initialization process, is going to want to connect to the database, and wham! This will not work and you will receive Error when connecting to the database errors. With a bit of luck, the application will try several times before stopping in error. Without luck, the application will just crash.

How to solve this? The answer is in two parts.

  1. You need to instruct Docker how he can know that the service is ready,
  2. You need to pause the application service until the database is ready.

The healthcheck property​

The idea is to ask Docker to run a given command each xxx seconds until he gets a Success status (in terms of Linux, it's a command that returns an exit code equal to 0).

By searching on the Internet using docker healthcheck followed by the name of a service (MySQL, PostgreSQL, Apache, Redis, ...), you'll find a lot of possibilities.

For MySQL, we'll use the next one:

services:
joomla:
image: joomla
[...]
joomladb:
image: mysql:8.0.13
[...]
// highlight-next-line
healthcheck:
// highlight-next-line
test: ["CMD", "mysqladmin" ,"ping", "-h", "localhost"]
// highlight-next-line
timeout: 20s
// highlight-next-line
retries: 10

This is a Docker Compose configuration that defines two services: a Joomla web application and a MySQL database. The database service includes a health check that periodically verifies the database is running by pinging it, and will retry up to 10 times if the ping fails, allowing up to 20 seconds for each attempt.

The four lines above instruct Docker to check the command defined by the test property every 20 seconds, up to 10 times. While that command doesn't return 0, the container is considered unhealthy. Then, hopefully, the command will return 0 and Docker will consider the service as healthy.

The depends_on property​

Now, the second part is to create a dependency in our application. Back to the Joomla service (in our example), we'll add a depends_on property like below.

services:
joomla:
image: joomla
[...]
// highlight-next-line
depends_on:
// highlight-next-line
joomladb:
// highlight-next-line
condition: service_healthy
joomladb:
image: mysql:8.0.13
[...]
healthcheck:
test: ["CMD", "mysqladmin" ,"ping", "-h", "localhost"]
timeout: 20s
retries: 10

This Docker Compose configuration defines two services: a Joomla web application and a MySQL database. The key detail is that Joomla won't start until the database service is not just running, but actually healthy—meaning it's passing its health checks. This prevents Joomla from crashing because it tried to connect to a database that wasn't ready yet.

It's pretty self-explanatory, I think. Docker will pause the creation of the Joomla container (just the creation, not downloading the image or any previous step) while the depends_on service isn't healthy.

And do you know what? I'm mad I didn't know about this sooner, because I've already set up a script like the one below in my applications:

Very simplified script

while [[ ! "$exitCode" = "0" ]]; do
echo "Waiting MySQL to launch on 3306..."
exitCode="$(nc joomladb 3306)"
done

Was this article helpful?
Did you try the steps in this article?