# ============================================================================= # Server # ============================================================================= SERVER_HOST=127.0.0.1 SERVER_PORT=3000 # The public-facing hostname of the PDS (used in DID documents, JWTs, etc.) PDS_HOSTNAME=localhost:3000 # ============================================================================= # Database # ============================================================================= DATABASE_URL=postgres://postgres:postgres@localhost:5432/pds # Connection pool settings (defaults are good for most deployments) # DATABASE_MAX_CONNECTIONS=100 # DATABASE_MIN_CONNECTIONS=10 # DATABASE_ACQUIRE_TIMEOUT_SECS=30 # ============================================================================= # Blob Storage # ============================================================================= # Backend: "filesystem" (default) or "s3" # BLOB_STORAGE_BACKEND=filesystem # For filesystem backend: BLOB_STORAGE_PATH=/var/lib/tranquil/blobs # For S3 backend: # S3_ENDPOINT=http://localhost:9000 # AWS_REGION=us-east-1 # S3_BUCKET=pds-blobs # AWS_ACCESS_KEY_ID=minioadmin # AWS_SECRET_ACCESS_KEY=minioadmin # ============================================================================= # Backups # ============================================================================= # Enable/disable automatic repo backups # BACKUP_ENABLED=true # Backend: "filesystem" (default) or "s3" # BACKUP_STORAGE_BACKEND=filesystem # For filesystem backend: BACKUP_STORAGE_PATH=/var/lib/tranquil/backups # For S3 backend: # BACKUP_S3_BUCKET=pds-backups # Backup schedule and retention # BACKUP_RETENTION_COUNT=7 # BACKUP_INTERVAL_SECS=86400 # ============================================================================= # Cache & Rate Limiting # ============================================================================= # Ripple (in-process CRDT cache) is the default. No config needed for single-node. # Set VALKEY_URL to use valkey instead (disables ripple). # VALKEY_URL=redis://localhost:6379 # # Ripple multi-node settings (only needed when clustering): # RIPPLE_BIND=0.0.0.0:7890 # RIPPLE_PEERS=10.0.0.2:7890,10.0.0.3:7890 # RIPPLE_MACHINE_ID=1 # RIPPLE_GOSSIP_INTERVAL_MS=200 # RIPPLE_CACHE_MAX_MB=256 # ============================================================================= # Security Secrets # ============================================================================= # These MUST be set in production (minimum 32 characters each) # In development, set TRANQUIL_PDS_ALLOW_INSECURE_SECRETS=1 to use defaults # Server-wide secret for OAuth token signing (HS256) # JWT_SECRET=your-secure-random-string-at-least-32-chars # Secret for DPoP proof validation # DPOP_SECRET=your-secure-random-string-at-least-32-chars # Key for encrypting user signing keys at rest (AES-256-GCM) # MASTER_KEY=your-secure-random-string-at-least-32-chars # Set this ONLY in development to allow default/weak secrets # TRANQUIL_PDS_ALLOW_INSECURE_SECRETS=1 # ============================================================================= # PLC Directory # ============================================================================= # PLC_DIRECTORY_URL=https://plc.directory # PLC_TIMEOUT_SECS=10 # PLC_CONNECT_TIMEOUT_SECS=5 # Optional: rotation key for PLC operations (defaults to user's key) # PLC_ROTATION_KEY=did:key:... # ============================================================================= # DID Resolution # ============================================================================= # Cache TTL for resolved DID documents (default: 300 seconds) # DID_CACHE_TTL_SECS=300 # ============================================================================= # Relays # ============================================================================= # Comma-separated list of relay URLs to notify via requestCrawl # CRAWLERS=https://bsky.network,https://relay.upcloud.world # ============================================================================= # Firehose (subscribeRepos WebSocket) # ============================================================================= # Buffer size for firehose broadcast channel # FIREHOSE_BUFFER_SIZE=10000 # Disconnect slow consumers after this many events of lag # FIREHOSE_MAX_LAG=5000 # ============================================================================= # Notification Service # ============================================================================= # Queue processing settings # NOTIFICATION_BATCH_SIZE=100 # NOTIFICATION_POLL_INTERVAL_MS=1000 # Email notifications (via sendmail/msmtp) # MAIL_FROM_ADDRESS=noreply@example.com # MAIL_FROM_NAME=My PDS # SENDMAIL_PATH=/usr/sbin/sendmail # Discord notifications (via bot DM) # DISCORD_BOT_TOKEN=bot-token # Telegram notifications (via bot) # TELEGRAM_BOT_TOKEN=bot-token # TELEGRAM_WEBHOOK_SECRET=random-secret # Signal notifications (via signal-cli) # SIGNAL_CLI_PATH=/usr/local/bin/signal-cli # SIGNAL_SENDER_NUMBER=+1234567890 # ============================================================================= # Upload Limits # ============================================================================= # Maximum blob/body size in bytes (default: 10GB) # This controls both the Axum body limit and blob upload limits. # Make sure your nginx client_max_body_size matches or exceeds this value. # MAX_BLOB_SIZE=10737418240 # ============================================================================= # Repository Import # ============================================================================= # Set to "true" to accept repository imports # ACCEPTING_REPO_IMPORTS=false # Maximum import size in bytes (default: 100MB) # MAX_IMPORT_SIZE=104857600 # Maximum blocks per import (default: 100000) # MAX_IMPORT_BLOCKS=100000 # Skip verification during import (testing only) # SKIP_IMPORT_VERIFICATION=false # ============================================================================= # Account Registration # ============================================================================= # Require invite codes for registration # INVITE_CODE_REQUIRED=false # Comma-separated list of available user domains # AVAILABLE_USER_DOMAINS=example.com # Enable self-hosted did:web identities (default: true) # Hosting did:web requires a long-term commitment to serve DID documents. # Set to false if you don't want to offer this option. # ENABLE_SELF_HOSTED_DID_WEB=true # ============================================================================= # Server Metadata (returned by describeServer) # ============================================================================= # Privacy policy URL (optional) # PRIVACY_POLICY_URL=https://example.com/privacy # Terms of service URL (optional) # TERMS_OF_SERVICE_URL=https://example.com/terms # Contact email address (optional) # CONTACT_EMAIL=admin@example.com # ============================================================================= # Rate Limiting # ============================================================================= # Disable all rate limiting (testing only, NEVER in production) # DISABLE_RATE_LIMITING=1 # ============================================================================= # Account Deletion # ============================================================================= # How often to check for scheduled account deletions (default: 3600 = 1 hour) # SCHEDULED_DELETE_CHECK_INTERVAL_SECS=3600 # ============================================================================= # Moderation / Report Service # ============================================================================= # If configured, moderation reports will be proxied to this service # instead of being stored locally. The service should implement the # com.atproto.moderation.createReport endpoint (eg., Bluesky's Ozone). # Both URL and DID must be set for proxying to be enabled. # REPORT_SERVICE_URL=https://mod.bsky.app # REPORT_SERVICE_DID=did:plc:ar7c4by46qjdydhdevvrndac # ============================================================================= # Age Assurance Override # ============================================================================= # Enable this if you have separately assured the ages of your users # (eg., through your own age verification process). When enabled, the PDS # will return "assured" status for age assurance checks instead of proxying # to the appview. This helps migrated users avoid the age assurance # catch-22 on bsky.app. # PDS_AGE_ASSURANCE_OVERRIDE=1 # ============================================================================= # Miscellaneous # ============================================================================= # Allow HTTP for proxy requests (development only) # ALLOW_HTTP_PROXY=1 # ============================================================================= # SSO / Social Login # ============================================================================= # Each provider requires ENABLED=true plus CLIENT_ID and CLIENT_SECRET. # Register your PDS as an OAuth application with each provider to get credentials. # GitHub # SSO_GITHUB_ENABLED=true # SSO_GITHUB_CLIENT_ID= # SSO_GITHUB_CLIENT_SECRET= # Discord # SSO_DISCORD_ENABLED=true # SSO_DISCORD_CLIENT_ID= # SSO_DISCORD_CLIENT_SECRET= # Google # SSO_GOOGLE_ENABLED=true # SSO_GOOGLE_CLIENT_ID= # SSO_GOOGLE_CLIENT_SECRET= # GitLab (set ISSUER for self-hosted instances) # SSO_GITLAB_ENABLED=false # SSO_GITLAB_CLIENT_ID= # SSO_GITLAB_CLIENT_SECRET= # SSO_GITLAB_ISSUER=https://gitlab.com # Generic OIDC # SSO_OIDC_ENABLED=false # SSO_OIDC_CLIENT_ID= # SSO_OIDC_CLIENT_SECRET= # SSO_OIDC_ISSUER=https://your-identity-provider.com # SSO_OIDC_NAME=Custom Provider # Apple Sign-in # SSO_APPLE_ENABLED=true # SSO_APPLE_CLIENT_ID=com.example.signin # Services ID from Apple Developer Portal # SSO_APPLE_TEAM_ID=XXXXXXXXXX # 10-character Team ID # SSO_APPLE_KEY_ID=XXXXXXXXXX # Key ID from portal # SSO_APPLE_PRIVATE_KEY="-----BEGIN PRIVATE KEY-----\n...\n-----END PRIVATE KEY-----" CARGO_MOMMYS_LITTLE=mister CARGO_MOMMYS_PRONOUNS=his CARGO_MOMMYS_ROLES=daddy CARGO_MOMMYS_EMOTES="🚛/🧱/🚜/🔩/🦺" CARGO_MOMMYS_MOODS=ominous