by markrai
a self-hosted project management & Kanban solution + Instant shareable boards
# Add to your Claude Code skills
git clone https://github.com/markrai/scrumboyRuns in seconds. No setup required.
No .env file, TLS certificates, or encryption key are required to start the app.
docker compose up --build
Open http://localhost:8080.
go run ./cmd/scrumboy
Open http://localhost:8080.
Note: scrumboy.env is not a standard KEY=value file — it contains only the raw encryption key on a single line.
.env files.export SCRUMBOY_ENCRYPTION_KEY=...).scrumboy.env automatically.SCRUMBOY_ENCRYPTION_KEY is not required for basic startup.Generate a key with: openssl rand -base64 32
Scrumboy supports OpenID Connect for single sign-on with any standards-compliant provider (Keycloak, Authentik, Auth0, Entra ID, etc.). OIDC is enabled by setting all four required environment variables:
No comments yet. Be the first to share your thoughts!
| Variable | Description |
|----------|-------------|
| SCRUMBOY_OIDC_ISSUER | Issuer URL (e.g. https://auth.example.com/realms/main) |
| SCRUMBOY_OIDC_CLIENT_ID | OAuth client ID |
| SCRUMBOY_OIDC_CLIENT_SECRET | Confidential client secret |
| SCRUMBOY_OIDC_REDIRECT_URL | Full callback URL registered at IdP (e.g. https://scrumboy.example.com/api/auth/oidc/callback) |
Optional:
| Variable | Description |
|----------|-------------|
| SCRUMBOY_OIDC_LOCAL_AUTH_DISABLED | Set to true to disable local password login when OIDC is configured (SSO-only mode) |
Local password authentication remains available by default alongside OIDC. After successful OIDC login, the user receives a standard Scrumboy session cookie. The IdP must return a verified email (email_verified: true). HTTPS is recommended when using OIDC to ensure session cookies are Secure.
See docs/oidc.md for full setup details, constraints, and troubleshooting.
SCRUMBOY_TLS_CERT and SCRUMBOY_TLS_KEY files exist.The Docker image and go run embed prebuilt assets under internal/httpapi/web/dist. If they are missing, build them:
cd internal/httpapi/web
npm install
npx tsc
Then run docker compose up --build or go run ./cmd/scrumboy again from the repository root.
Simplicity of a light Kanban, with the power of structured systems: Roles, sprints, audit trails & customizable workflows - without being locked into SaaS tools.
Full (SCRUMBOY_MODE=full, default): Auth can be enabled. First user via bootstrap; then login/session. Backup/export, tags, multi-project. Projects can be user-owned (project_members) or anonymous (shareable by URL): /anon (or /temp) creates a throwaway board and redirects to /{slug}.
Anonymous (SCRUMBOY_MODE=anonymous): No auth. Landing at /; live deployment at: https://scrumboy.com/
Custom Workflows: You can create any combination of workflow you want, per project, with user-defined "Done" lane.
Realtime SSE enabled boards for instant multi-user actions.
Customizable Tags: Users can inherit and customize tag colors.
Advanced filtering: Search todos based on text or tags.
Sprints: create, activate, close; sprint filter on board; default sprint weeks (1 or 2) per project.
Authentication & 2FA: TOTP supported when SCRUMBOY_ENCRYPTION_KEY is set.
Audit trail: append-only audit_events table; todo/member/project/link actions logged (see docs/AUDIT_TRAIL.md).
Backup: export/import JSON; merge or replace; scope full or single project (see store backup logic).
PWA: Excellent UX for mobile users.
Anonymous shareable boards can be created in both Full & Anonymous deployments.
Scrumboy supports API access tokens for automation, integrations, and programmatic MCP access (legacy HTTP and JSON-RPC — see below).
You can create a token from the API and use it to call MCP endpoints directly — no browser session or cookies required.
Create a token (requires login session):
curl -b cookies.txt -X POST http://localhost:8080/api/me/tokens \
-H "Content-Type: application/json" \
-H "X-Scrumboy: 1" \
-d '{"name":"cli"}'
Response includes a one-time token (starts with sb_).
Use it with MCP:
curl -X POST http://localhost:8080/mcp \
-H "Content-Type: application/json" \
-H "Authorization: Bearer sb_your_token_here" \
-d '{"tool":"projects.list","input":{}}'
Scrumboy exposes a Model Context Protocol (MCP) compatible JSON-RPC endpoint for AI agents (Claude, etc.) and MCP-compatible clients.
Endpoint: POST /mcp/rpc
This is separate from the /mcp HTTP endpoint above and follows JSON-RPC 2.0 (initialize, tools/list, tools/call, etc.). See API.md for full detail.
initializecurl -X POST http://localhost:8080/mcp/rpc \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{}}'
curl -X POST http://localhost:8080/mcp/rpc \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","id":2,"method":"tools/list","params":{}}'
curl -X POST http://localhost:8080/mcp/rpc \
-H "Content-Type: application/json" \
-H "Authorization: Bearer sb_your_token_here" \
-d '{
"jsonrpc":"2.0",
"id":3,
"method":"tools/call",
"params":{
"name":"todos.create",
"arguments":{
"projectSlug":"my-project",
"title":"Created via MCP"
}
}
}'
Notes
/mcp).This enables:
POST /mcp/rpc for JSON-RPC; POST /mcp remains available for the legacy { "tool", "input" } envelope)Env vars and defaults are defined in internal/config/config.go. ResolveDataDir uses DATA_DIR and SQLITE_PATH as documented there.
None of these are required for basic startup.
| Variable | Default (from code) |
|----------|---------------------|
| BIND_ADDR | :8080 |
| DATA_DIR | ./data |
| SQLITE_PATH | (empty; then $DATA_DIR/app.db) |
| SQLITE_BUSY_TIMEOUT_MS | 30000 |
| SQLITE_JOURNAL_MODE | WAL |
| SQLITE_SYNCHRONOUS | FULL |
| MAX_REQUEST_BODY_BYTES | 1048576 (1 MiB) |
| SCRUMBOY_MODE | full (or anonymous) |
| SCRUMBOY_ENCRYPTION_KEY | (empty) - Required for 2FA. Base64-encoded 32-byte key. Generate with openssl rand -base64 32. Without it, 2FA setup returns 503. |
| SCRUMBOY_TLS_CERT | ./cert.pem - TLS cert for HTTPS |
| SCRUMBOY_TLS_KEY | ./key.pem - TLS key for HTTPS |
| SCRUMBOY_INTRANET_IP | 192.168.1.250 - LAN IP to log for intranet access |
docker-compose.yml overrides some of these (e.g. SQLITE_BUSY_TIMEOUT_MS=5000).
In full mode, access is governed by two separate role systems. System roles do not grant project access; project access comes only from project membership.
| Role | Who has it | Allowed actions | |--------|------------|------------------| | Owner | Bootstrap (first) user; can be assigned by another owner | List all users; create users (admin-only API); update any user’s system role (owner/admin/user); delete users (except cannot delete the last owner). | | Admin | Assigned by an owner | List all users; create users. Cannot change system roles or delete users. | | User | Default for new users; assigned by owner | No system-level user management. Access to projects only via project membership. |
A user must be a member of a project to access it; system role alone does not grant access.
| Role | View board & todos | Create/edit/move/delete todos | Edit body when assigned | Manage members | Delete project | Tag delete/color (project-scoped) | |---------------|--------------------|-------------------------------|--------------------------|----------------|----------------|-----------------------------------| | Maintainer| ✓ | ✓ | ✓ | ✓ | ✓ | ✓ (maintainer) | | Contributor| ✓ | - | ✓ (body only) | - | - | - | | Viewer | ✓ | - | - | -