Configure your application
Keep the state needed to run your application below .deliberate/:
.deliberate/├── project.yaml├── app.yaml└── storage.yamlproject.yaml identifies the Team, Project, and Environment Flow. Put the
application resources in any other YAML files you find useful. A file can
contain several documents separated by ---.
Preview and apply the complete configuration with:
deliberate diff --env productiondeliberate apply --env productionConnect a database, bucket, or volume
Section titled “Connect a database, bucket, or volume”Dependencies are explicit. needs grants access to a resource and, where
needed, opens the network path from this Component to it. An expression places
one of that resource’s outputs where the consuming software expects it:
env: DATABASE_URL: "${{ postgres.url }}"needs: databases: - postgresYour application chooses the environment-variable name. The dependency grants access; the expression maps the output into the configuration your application already expects.
For example, an application can use a database, object storage, and a durable filesystem with the names its libraries already expect:
env: DATABASE_URL: "${{ postgres.url }}" S3_ENDPOINT: "${{ assets.endpoint }}" S3_BUCKET: "${{ assets.bucket }}" S3_ACCESS_KEY: "${{ assets.access_key }}" S3_SECRET_KEY: "${{ assets.secret_key }}"needs: databases: - postgres buckets: - assets volumes: - name: uploads path: /app/uploadsDatabase and bucket credentials remain secret references in the deployed
workload. A volume is mounted only into the Component that asks for it. A
declared dependency that is not referenced in env grants access but does not
invent an environment-variable name.
Component outputs use ${{ component.host }}, ${{ component.port }}, or
${{ component.url }}. Route outputs use ${{ route.url }} or
${{ route.host }}. Blueprint instances expose only the outputs their author
declared. The YAML reference contains a complete example.
Set environment variables
Section titled “Set environment variables”Put non-sensitive configuration directly in env:
env: LOG_LEVEL: info FEATURE_SIGNUP: "true"Values are strings and belong to desired state. Commit them with the rest of
the Project, change them, and run deliberate apply again. The platform rolls
out the resulting Component revision.
Add secrets
Section titled “Add secrets”YAML declares which secrets a Component consumes, but values are stored outside Git:
secrets: - SESSION_SECRET - OPENAI_API_KEYSet a value through standard input, then apply:
echo -n "$SESSION_SECRET" | deliberate secret set SESSION_SECRET --env productiondeliberate apply --env productionEach declared name becomes an environment variable with the same name. To map a
secret to a different variable name, keep it in secrets and reference it:
env: PROVIDER_TOKEN: "${{secrets.OPENAI_API_KEY}}"secrets: - OPENAI_API_KEYSecret lookup is Component → Environment → Project → Team. Use the narrowest
scope that matches the intended sharing boundary. For example, omit scope flags
for a Team-wide value, use --project hello-java across its Environments, or
use --env production --component app for one deployed consumer. Inspect names
and scopes—not values—with deliberate secret list.
Changing a stored value restarts affected consumers so the new process receives it. Stored values are not returned by the CLI or console. Blueprint secret arguments follow the same boundary.
Run migrations and deployment automation
Section titled “Run migrations and deployment automation”Components can run a bounded release command before rollout or a postDeploy
command after the new revision is ready. The commands run in separate one-shot
containers and have deliberately different failure behavior.
Use lifecycle hooks for migrations, cache warming, and other revision-specific automation.
Expose the application
Section titled “Expose the application”Every declared Component port is reachable only by authorized siblings unless
you expose it. Marking an HTTP port visibility: public is the shortest path:
ports: - port: 8080 protocol: http visibility: publicThe platform creates a generated HTTPS address. Use an explicit route when
you want path routing, a chosen generated hostname, a custom domain, or Private
Net access:
resource: routehost: appvisibility: publicrules: - path: / to: web - path: /api to: apiThe most specific path wins, so /api is selected before / regardless of
declaration order. TLS for generated hostnames is platform-owned.
For a customer-owned hostname, declare the hostname and the matching route in the same Environment:
resource: domainhostname: app.example.com
---resource: routehost: app.example.comvisibility: publicrules: - path: / to: webAfter applying, deliberate domains show app.example.com --env production
prints the required DNS records. Once they resolve, run deliberate domains verify app.example.com --env production to verify ownership and start
certificate issuance. Follow Add a custom domain for
the complete DNS and verification workflow.
Set visibility: private when a route should answer only for permitted Team
members on enrolled devices. allow can narrow access to Team roles, handles,
or email addresses. Read Connect and grant access
before choosing private-first onboarding: the application may need a public
first-run page before its users have enrolled a device.
See the YAML reference for every resource and a complete, schema-tested example.