Builtin Authentication
Builtin authentication provides user management with role-based access control (RBAC) using JWT tokens.
Features
- User Management: Create, update, and delete users through the web UI
- Role-Based Access Control: Four roles with different permission levels
- JWT Authentication: Secure token-based authentication
- Password Management: Users can change their own passwords; admins can reset any user's password
Roles
| Role | Permissions |
|---|---|
admin | Full access including user management |
manager | Create, edit, delete, run, and stop DAGs |
operator | Run and stop DAGs (execute only) |
viewer | Read-only access to DAGs and execution history |
Configuration
YAML Configuration
yaml
# ~/.config/dagu/config.yaml
auth:
mode: builtin
builtin:
admin:
username: admin
# password: optional - auto-generated if not set
token:
secret: your-secure-random-secret-key
ttl: 24h
# Optional: API token for programmatic access (works alongside JWT)
token:
value: your-api-tokenToken TTL Format
The ttl field uses Go's duration format. Valid time units are:
| Unit | Description | Example |
|---|---|---|
ns | nanoseconds | 1000000ns |
us (or µs) | microseconds | 1000us |
ms | milliseconds | 1000ms |
s | seconds | 3600s |
m | minutes | 60m |
h | hours | 24h |
Note: Days (d) and weeks (w) are not supported. Use hours instead.
Common TTL examples:
| Duration | Value |
|---|---|
| 1 hour | 1h |
| 8 hours | 8h |
| 24 hours (1 day) | 24h |
| 7 days | 168h |
| 30 days | 720h |
| 365 days | 8760h |
You can also combine units: 1h30m, 2h45m30s
Environment Variables
bash
# Required
export DAGU_AUTH_MODE=builtin
export DAGU_AUTH_TOKEN_SECRET=your-secure-random-secret-key
# Optional - admin credentials
export DAGU_AUTH_ADMIN_USERNAME=admin # default: admin
export DAGU_AUTH_ADMIN_PASSWORD= # auto-generated if not set
# Optional - token settings
export DAGU_AUTH_TOKEN_TTL=24h # default: 24h
dagu start-allInitial Setup
On first startup with builtin auth enabled:
- If no users exist, an admin user is automatically created
- If
DAGU_AUTH_ADMIN_PASSWORDis not set, a secure password is auto-generated and printed to stdout:
================================================================================
ADMIN USER CREATED
Username: admin
Password: <auto-generated-password>
NOTE: Please change this password immediately!
================================================================================- Use these credentials to log in and access the user management page
API Access
Login
bash
# Get JWT token
curl -X POST http://localhost:8080/api/v2/auth/login \
-H "Content-Type: application/json" \
-d '{"username": "admin", "password": "your-password"}'
# Response:
# {"token": "eyJhbG...", "user": {"id": "...", "username": "admin", "role": "admin"}}Using the Token
bash
# Include token in Authorization header
curl -H "Authorization: Bearer eyJhbG..." \
http://localhost:8080/api/v2/dagsGet Current User
bash
curl -H "Authorization: Bearer eyJhbG..." \
http://localhost:8080/api/v2/auth/meChange Password (Self)
bash
curl -X POST http://localhost:8080/api/v2/auth/change-password \
-H "Authorization: Bearer eyJhbG..." \
-H "Content-Type: application/json" \
-d '{"currentPassword": "old-pass", "newPassword": "new-pass"}'User Management (Admin Only)
List Users
bash
curl -H "Authorization: Bearer eyJhbG..." \
http://localhost:8080/api/v2/usersCreate User
bash
curl -X POST http://localhost:8080/api/v2/users \
-H "Authorization: Bearer eyJhbG..." \
-H "Content-Type: application/json" \
-d '{"username": "newuser", "password": "secure-pass", "role": "operator"}'Update User
bash
curl -X PUT http://localhost:8080/api/v2/users/{user-id} \
-H "Authorization: Bearer eyJhbG..." \
-H "Content-Type: application/json" \
-d '{"role": "manager"}'Reset User Password (Admin)
bash
curl -X PUT http://localhost:8080/api/v2/users/{user-id}/password \
-H "Authorization: Bearer eyJhbG..." \
-H "Content-Type: application/json" \
-d '{"newPassword": "new-secure-pass"}'Delete User
bash
curl -X DELETE http://localhost:8080/api/v2/users/{user-id} \
-H "Authorization: Bearer eyJhbG..."Docker Compose Example
yaml
services:
dagu:
image: ghcr.io/dagu-org/dagu:latest
environment:
- DAGU_AUTH_MODE=builtin
- DAGU_AUTH_TOKEN_SECRET=change-me-to-secure-random-string
# Password auto-generated on first run, printed to stdout
ports:
- "8080:8080"
volumes:
- dagu-data:/var/lib/dagu
volumes:
dagu-data:Important Notes
Basic Auth Ignored: When
auth.modeis set tobuiltin, anyauth.basicconfiguration is ignored. A warning will be logged. Use the builtin admin credentials instead.API Token Support: API tokens (
auth.token.value) work alongside builtin auth for programmatic access without requiring JWT login.yamlauth: mode: builtin builtin: token: secret: your-jwt-secret token: value: your-api-token # Use with: curl -H "Authorization: Bearer your-api-token"
Security Notes
- Token Secret: Use a strong, random secret (at least 32 characters). This is used to sign JWT tokens.
- Password Requirements: Minimum 8 characters
- Token Expiry: Tokens expire after the configured TTL (default: 24 hours)
- V1 API: The V1 API is disabled when builtin auth is enabled (use V2 API)
Comparison with Other Auth Methods
| Feature | Basic Auth | Token Auth | OIDC | Builtin |
|---|---|---|---|---|
| User Management | No | No | External | Yes |
| Role-Based Access | No | No | External | Yes |
| Password Change | No | No | External | Yes |
| Multiple Users | No | No | Yes | Yes |
| Self-Hosted | Yes | Yes | No | Yes |
