Skip to content

Relationships

A relationship wires an application to a backing service — a database or cache. Declaring a relationship does two things: it injects the service's connection details as environment variables into the application, and it makes the application wait for the service to be healthy before starting.

<relationships>

<relationships> contains one or more <relationship> elements.

xml
<relationships>
    <relationship name="database" target="db"/>
    <relationship name="cache" target="redis"/>
</relationships>

<relationship>

AttributeRequiredDefaultDescription
nameYesLogical name of the relationship. Used to build the env var prefix.
targetYesName of the service to connect to. Must match a <service name>.

Target must exist

target must match the name of a service declared under <services>. A relationship that points at a non-existent service is invalid.

Environment variable injection

For each relationship, Tragwerk injects connection variables into the application container (and its workers and cron sidecar). The variable prefix is derived from the relationship name:

TRAGWERK_<NAME>_

where <NAME> is the relationship name upper-cased with spaces and hyphens replaced by underscores. So name="database" produces the prefix TRAGWERK_DATABASE_, and name="read-replica" produces TRAGWERK_READ_REPLICA_.

Keys for SQL services (postgresql, mysql, mariadb)

VariableValue (defaults)
TRAGWERK_<NAME>_HOSTservice hostname (slug)
TRAGWERK_<NAME>_PORT5432 (pg) / 3306 (mysql, mariadb)
TRAGWERK_<NAME>_DATABASEapp
TRAGWERK_<NAME>_USERapp
TRAGWERK_<NAME>_PASSWORDsecret

Keys for cache services (redis, valkey)

VariableValue (defaults)
TRAGWERK_<NAME>_HOSTservice hostname (slug)
TRAGWERK_<NAME>_PORT6379

TIP

There is no single *_URL variable — connection details are exposed as discrete HOST / PORT / DATABASE / USER / PASSWORD parts. Build any DSN your framework needs from these.

Worked example

xml
<application name="app" type="php:8.5" root="/">
    <web>
        <location path="/" root="public" index="index.php" passthru="/index.php"/>
    </web>
    <relationships>
        <relationship name="database" target="db"/>
        <relationship name="cache" target="redis"/>
    </relationships>
</application>
<!-- ... -->
<services>
    <service name="db" type="postgresql:18"/>
    <service name="redis" type="redis:8"/>
</services>

This injects the following environment variables into the app container:

bash
TRAGWERK_DATABASE_HOST=db
TRAGWERK_DATABASE_PORT=5432
TRAGWERK_DATABASE_DATABASE=app
TRAGWERK_DATABASE_USER=app
TRAGWERK_DATABASE_PASSWORD=secret

TRAGWERK_CACHE_HOST=redis
TRAGWERK_CACHE_PORT=6379

Health-gated startup

Each relationship also adds a depends_on entry on the target service with condition service_healthy. The application container does not start until the database or cache reports healthy (via the service's healthcheck), so your app never boots against a service that is not ready yet.

Tragwerk — self-hosted PHP application hosting.