Configuration
Environment variables for the Pug backend and dashboard. Copy .env.example from each repo as the starting point.
Backend (cotton)
git clone git@github.com:fivebitsio/cotton.git
cd cotton
cp .env.example .envDatabase
| Variable | Required | Description |
|---|---|---|
DATABASE_URL | Yes | Postgres write connection string |
DATABASE_READ_URL | No | Postgres read replica (falls back to write URL) |
DATABASE_URL=postgres://pug:password@localhost:5432/pug?sslmode=disable
DATABASE_READ_URL=postgres://pug:password@localhost:5433/pug?sslmode=disableAnalytics storage
| Variable | Required | Description |
|---|---|---|
CLICKHOUSE_URL | Yes | ClickHouse HTTP connection |
CLICKHOUSE_URL=http://default:@localhost:8123/pugMessage queue
| Variable | Required | Description |
|---|---|---|
NATS_URL | Yes | NATS server URL |
NATS_URL=nats://localhost:4222Authentication
| Variable | Required | Description |
|---|---|---|
JWT_SECRET | Yes | Secret for signing dashboard JWTs — use a long random string |
MAGIC_LINK_SECRET | Yes | Secret for magic link tokens |
OAUTH_GOOGLE_CLIENT_ID | No | Google OAuth client ID |
OAUTH_GOOGLE_CLIENT_SECRET | No | Google OAuth client secret |
Generate secrets:
openssl rand -hex 32Never reuse secrets between environments.
Server
| Variable | Required | Description |
|---|---|---|
PORT | No | API server port (default 8080) |
ENV | No | development or production |
LOG_LEVEL | No | debug, info, warn, error |
Configure SMTP for magic links and transactional email:
| Variable | Required | Description |
|---|---|---|
SMTP_HOST | No | SMTP server hostname |
SMTP_PORT | No | SMTP port (default 587) |
SMTP_USER | No | SMTP username |
SMTP_PASSWORD | No | SMTP password |
SMTP_FROM | No | From address for transactional email |
Org-specific email providers can override these via OrgEmailProvidersService in the dashboard.
Dashboard (cotton-ui)
git clone git@github.com:fivebitsio/cotton-ui.git
cd cotton-ui
cp .env.example .env| Variable | Required | Description |
|---|---|---|
VITE_API_URL | Yes | Connect RPC endpoint (e.g. http://localhost:8080) |
VITE_GOOGLE_OAUTH_ENABLED | No | Set true to show Google sign-in button |
VITE_API_URL=http://localhost:8080
VITE_GOOGLE_OAUTH_ENABLED=trueFor production, set VITE_API_URL to your public API URL at build time.
Web SDK
Point the SDK at your self-hosted API:
init('PROJECT_ID', {
apiKey: 'YOUR_SDK_API_KEY',
endpoint: process.env.NEXT_PUBLIC_PUG_API_URL // e.g. https://api.yourcompany.com
})No SDK code changes required — only the endpoint option.
Google OAuth setup
- Create a project in Google Cloud Console
- Enable the Google+ API
- Create OAuth 2.0 credentials (Web application)
- Add authorized redirect URI:
https://your-api.example.com/auth/google/callback - Set
OAUTH_GOOGLE_CLIENT_IDandOAUTH_GOOGLE_CLIENT_SECRETin cotton.env - Set
VITE_GOOGLE_OAUTH_ENABLED=truein cotton-ui.env
Secrets management
Do not commit .env files to version control. In production:
- Use a secrets manager (AWS Secrets Manager, HashiCorp Vault, GCP Secret Manager)
- Inject secrets as environment variables at container startup
- Rotate
JWT_SECRETand API keys on a schedule
Verifying configuration
After starting the stack:
# API health
curl http://localhost:8080/health
# Send a test event
curl -X POST http://localhost:8080/events.v1.EventsService/BatchCreate \
-H "Authorization: Bearer YOUR_SDK_API_KEY" \
-H "x-project-id: YOUR_PROJECT_ID" \
-H "Content-Type: application/json" \
-H "Connect-Protocol-Version: 1" \
-d '{"events":[{"name":"test_event"}]}'See .env.example in each repo for the complete variable list.
Further reading
- Development — local workflow
- Requirements — infrastructure sizing
- Authentication — JWT and API key headers
Last updated on