Zitadel — Zitadel is the identity provider (users, roles, authentication). ⬆ índice
Zitadel Guide
Zitadel is the identity provider (users, roles, authentication).
Quick start (local)
./infra up security/zitadel # start
./infra logs security/zitadel # follow logs
./infra status security/zitadel # compose ps
From the service directory (alternative):
cd security/zitadel
./run.sh up
./run.sh logs
Access (local)
- Main service:
http://localhost:${ZITADEL_PORT:-8084} - Login UI:
http://localhost:${LOGIN_UI_PORT:-8085}
Access (remote)
When deployed with the default Traefik endpoint registry (deployment/remote.env), Zitadel uses:
- Main service:
https://iam.<base-domain> - Login UI:
https://iam.<base-domain>/ui/v2/login - Login alias:
https://iam.<base-domain>/login
If you changed the default domains or paths, update deployment/remote.env and redeploy core so Traefik regenerates routes/certs.
Access (local VM / Vagrant targets)
When you deploy to a server marked as local (core2_is_local=true in Ansible inventory), endpoints use short test hostnames over HTTP:
- Add hostnames on your laptop (example):
sudo sh -c 'printf "%s\n" "192.168.56.10 iam portal things" >> /etc/hosts'
- Access example:
http://iam
Prerequisites
- Centralized DB layer must be running (PostgreSQL + Redis).
- Quick check:
./infra db status
- Quick check:
- Env must exist and be valid:
./infra env generate./infra env check
Default bootstrap login
- User:
zitadel-admin@[FIRSTINSTANCE_ORG_NAME].[ZITADEL_EXTERNALDOMAIN] - Password:
Password1!
Notes:
- These defaults come from the repo’s first-instance configuration in
security/zitadel/.env. - The login identifier uses the organization name prefix from
FIRSTINSTANCE_ORG_NAMEbefore the external domain. - If you changed first-instance variables (or already bootstrapped before), the credentials may differ.
Automated bootstrap
Fresh installs now bootstrap automatically:
- Zitadel writes the first-instance management PAT to:
security/zitadel/.runtime/management.pat
- Bootstrap reconciliation uses that PAT to:
- create/reconcile the automation machine user
- generate/reconcile the durable management client secret
- create/reconcile the
Aithaproject - create/reconcile project roles and apps/clients
- write resulting
GLOBAL_ZITADEL_*values back into.env.secrets
Manual recovery is still possible:
./infra zitadel pat set '<PAT>'
python3 deployment/scripts/python/zitadel_bootstrap.py \
--base-url http://127.0.0.1:${ZITADEL_PORT:-8084} \
--pat-file security/zitadel/.runtime/management.pat \
--env-file .env.secrets \
--url-mode localhost
Import / export helpers
./infra zitadel export [project_name_or_id] [output_file]
./infra zitadel import <json_file> [new_project_name] [--pat <token>] [--org-id <org_id>]
Org ID (--org-id)
- If your PAT is scoped in a specific org,
importmay need--org-id. - You can usually find the org id in the console (org settings/details), or in console URLs after selecting an org.
PAT resolution order for import:
--pat <token>ZITADEL_MANAGEMENT_PATenv varsecurity/zitadel/.runtime/management.pat- interactive prompt (TTY)
About login-client.pat
- The bootstrap process can also generate a
security/zitadel/.runtime/login-client.pattoken for login/bootstrap flows. - Do not use
login-client.patfor project import/export automation (it is typically missing permissions forAddProjectoperations).
zitadel guide
./infra zitadel guide prints this document (used by local + remote init flows).
Notes
- If you change Zitadel first-instance/domain/redirect values, update
security/zitadel/.envand rerun./infra up security/zitadel. - Keep the
security/zitadelphase correct before generating the full application envs. - The canonical bootstrap spec now lives in
security/zitadel/bootstrap.json.
Related documentation
- Technology overview:
docs/internal/technologies/zitadel.md - Roles model:
docs/internal/architecture/roles-and-permissions.md