Skip to content

Build1 publisher3 min readPublished

Every declared Compose dependency on this eight-server fleet ends in :false

Compose has carried a restart flag on depends_on since 2023. A read-only pass over 38 running containers on eight servers found seven declared dependencies, all of them waiting on health and all of them recording restart as false.

The Engineer · Build desk

Illustration accompanying Every declared Compose dependency on this eight-server fleet ends in :false

What happened

  • A read-only pass across eight servers on 2026-09-17 pulled each running container's healthcheck configuration and the depends_on label Compose writes at create time.
  • On 2026-07-31 an n8n upgrade from 2.30.6 to 2.32.6 left the worker dead in MigrationExecutor.executePendingMigrations and stuck unhealthy, while Postgres reported healthy throughout.
  • The fix still in the runbook is a hand-typed docker restart of the worker container once the main container reports healthy, run at every version bump for months.

Compiled by The EngineerSomething wrong?How this is made

Why it matters

  • constraint Ordering by health alone covers the cold boot, and on the post's illustrative server that is one event in 25 across a year; the other 24 deploys bring containers up in whatever order Compose replaces them.
  • cost Standing in for the flag costs an operator's presence at every version bump, and the step only works on the upgrades where the person running it remembers the line.
  • exposure Any stack whose migrations run inside a sibling container inherits this failure mode, because the database can report healthy while the dependent process meets a half-applied schema.

Compose v2 writes `com.docker.compose.depends_on` onto a container at create time, and the value is the resolved dependency in the form `service:condition:restart` [4]. Reading the label beats reading the YAML on disk, because the label records what the running container was actually created with [4]. The last token is the restart flag, and `false` means: when Compose updates the dependency, do not restart me [7]. Seven containers on this fleet declare a dependency at all, all seven wait for `service_healthy`, and all seven end in `:false` [6].

The specification scopes the flag narrowly. `restart: true` means "Compose restarts this service after it updates the dependency service" [10], and the update in question is the `docker compose up -d` that swaps a container for one on a new image [11]. Runtime crashes are covered by the restart policy instead [11]. So `condition` sets the order on a cold boot, and `restart` decides what happens to a service when the thing underneath it is replaced [12].

The post's own illustration is a server that boots once a year and deploys twice a month [13]. Twenty-four deploys plus one boot is 25 ordering events in a year, so the declared health conditions govern one of them, about four percent [14].

The 2026-07-31 incident is the case the flag covers. Postgres was healthy on the question its healthcheck asked, which was whether it accepted connections [16]. The n8n main container and the worker both came up against that database and both began running migrations; main won, and the worker died on a half-applied schema with its stack trace in `MigrationExecutor.executePendingMigrations` [15][16]. It went unhealthy and stayed there [15]. Rewriting the Postgres healthcheck cannot help, because whether the application's schema is current is a fact about the sibling container doing the migrating [17].

Switching the flag on changes deploy behaviour. Because restart fires when Compose updates the dependency, a worker declared `restart: true` will restart on every deploy that replaces main, including the bumps that migrate nothing [21]. The hand-typed step has the same effect on the deploys where someone remembers it [1][18]. The post's author wrote: "My runbook is a human being standing in for one boolean." [20]

The author declared the dependencies being audited, so the zero describes one operator's defaults on eight servers running clients' work [22][3]. For it to say anything about other fleets, the same label pull would have to come back the same way on Compose files other people wrote. Thirty-one of the 38 containers carry no `depends_on` at all, and the post sets those aside as a separate question [8]. Its account of the 2026-09-04 engine upgrade, where live-restore carried every container through 29.7.2 to 29.8.0 at 8, 5 and 3 per host, ends mid-sentence [19].

What to watch

  • Whether the post's cut-off account of the 2026-09-04 engine upgrade identifies the container that broke while live-restore held the other 15.
  • Whether the 31 containers with no depends_on get the same label-based pass, and how many of them have a real ordering requirement.
  • Whether restart: true on the n8n worker survives contact with deploys that replace main and migrate nothing.
Loading claim ledger
Loading source directory links
Loading share composer
Loading topic controls
Loading related stories