---
title: "Deploy Kaneo | (Just Updated) Self-Hosted Project Management with REST API & MCP, Admin Pre-Created"
description: "Kaneo self-hosted project management, REST API, MCP, Postgres"
category: "Other"
url: https://railway.com/deploy/kaneo-or-just-updated-self-hosted-projec
---

# Deploy Kaneo | (Just Updated) Self-Hosted Project Management with REST API & MCP, Admin Pre-Created

Kaneo self-hosted project management, REST API, MCP, Postgres

**[Deploy Kaneo | (Just Updated) Self-Hosted Project Management with REST API & MCP, Admin Pre-Created on Railway](https://railway.com/template/kaneo-or-just-updated-self-hosted-projec)**

Machine-readable deploy manifest (JSON, validated by TemplateCI): https://railway.com/deploy/kaneo-or-just-updated-self-hosted-projec/manifest.json

- **Creator:** SuperSlowSloth
- **Category:** Other

## Template content

### postgres

- **Image:** postgres:18.6@sha256:74935e72241653ca55e0414067e6d8763aceb8a810eb51b452253ec3dcfc4336

### kaneo

- **Image:** ghcr.io/bon5co/kaneo-railway:2.49.0@sha256:b6bf1b6bc3f3b039239c481e8cc86e12c321d1a9f8dd99df6cbb776baab6cb1f
- **Health check:** /api/health
- **Public domain:** Yes

## Documentation

# Deploy and Host Kaneo on Railway

**Built for an LLM agent to deploy and use.** The deploy form has no fields to fill: the instance administrator is created from generated credentials at first boot, public sign-up is closed before the first request is served, and the REST API takes a bearer token from a normal sign-in. Kaneo is an open-source, self-hosted project management tool: workspaces, projects, kanban boards, tasks, labels, time tracking, notifications, API keys and a built-in MCP server, on PostgreSQL.

## About Hosting Kaneo

This template runs two services: **kaneo** (the web app and the REST API behind one public domain) and **postgres** (PostgreSQL 18 on a volume mounted at `/var/lib/postgresql`). The kaneo service keeps no state of its own; every workspace, project and task lives in the database.

**Locked from boot.** A stock Kaneo lets the first visitor to the URL register and become the instance administrator, regenerates its session signing secret (`AUTH_SECRET`) on every start when unset (every session dies on each redeploy), and its bundled nginx listens on a hard-coded port that Railway's proxy and healthcheck never reach. This template's image listens on Railway's `PORT`, refuses to start without a stable `AUTH_SECRET`, creates the administrator from `ADMIN_EMAIL` and `ADMIN_PASSWORD` before the sign-up route is reachable (it answers 503 until then) and then turns public registration off in the instance settings.

**What persists.** Users, workspaces, projects, tasks, comments and API keys live in the PostgreSQL volume. File attachments need an S3-compatible bucket (`S3_*` variables, see the Kaneo docs); without one, attachments are unavailable and everything else works.

**Using the web interface.** Open the public URL and sign in with the `ADMIN_EMAIL` and `ADMIN_PASSWORD` values from the kaneo service variables.

### Agent contract

- Public URL: `https://RAILWAY_PUBLIC_DOMAIN` (the generated domain of the `kaneo` service)
- Private URL: `http://kaneo.railway.internal:8080`
- Credentials: the variables `ADMIN_EMAIL` and `ADMIN_PASSWORD` on the `kaneo` service
- Auth: sign in with `POST /api/auth/sign-in/email` (JSON `email`, `password`); the response header `set-auth-token` is a token to send as `Authorization: Bearer TOKEN` on every `/api` request, and without it the API answers `401`. After sign-in an agent can also create an API key (`x-api-key` header) from the web interface
- Health: `GET /api/health` returns 200 without credentials

```bash
# needs: SITE_URL (public https URL of the kaneo service), ADMIN_EMAIL and ADMIN_PASSWORD (its variables); also curl, sed
login() { curl -s -i -X POST "$SITE_URL/api/auth/sign-in/email" -H "Content-Type: application/json" -d "{\"email\":\"$ADMIN_EMAIL\",\"password\":\"$ADMIN_PASSWORD\"}" | tr -d '\r' | sed -n 's/^set-auth-token: //Ip'; }
TOKEN=$(login)
AUTH="Authorization: Bearer $TOKEN"
curl -s -o /dev/null -w "health: %{http_code}\n" "$SITE_URL/api/health"
curl -s -o /dev/null -w "read without key: %{http_code}\n" "$SITE_URL/api/project"
curl -s -o /dev/null -w "write without key: %{http_code}\n" -X POST -H "Content-Type: application/json" -d '{"name":"x","workspaceId":"x","icon":"Layout","slug":"x"}' "$SITE_URL/api/project"
curl -s -o /dev/null -w "write wrong key: %{http_code}\n" -X POST -H "Authorization: Bearer wrong" -H "Content-Type: application/json" -d '{"name":"x","workspaceId":"x","icon":"Layout","slug":"x"}' "$SITE_URL/api/project"
curl -s -o /dev/null -w "public sign-up: %{http_code}\n" -X POST -H "Content-Type: application/json" -d '{"email":"intruder@example.com","password":"Sup3rSecretPassw0rd","name":"x"}' "$SITE_URL/api/auth/sign-up/email"
WSID() { curl -s -H "$AUTH" "$SITE_URL/api/workspace" | sed -n 's/.*"id":"\([^"]*\)".*/\1/p'; }
WS=$(WSID)
if [ -z "$WS" ]; then curl -s -o /dev/null -X POST -H "$AUTH" -H "Content-Type: application/json" -d '{"name":"Agent","slug":"agent"}' "$SITE_URL/api/auth/organization/create"; WS=$(WSID); fi
echo "workspace: $WS"
PID=$(curl -s -X POST -H "$AUTH" -H "Content-Type: application/json" -d "{\"name\":\"Agent check\",\"workspaceId\":\"$WS\",\"icon\":\"Layout\",\"slug\":\"agent-check\"}" "$SITE_URL/api/project" | sed -n 's/^{"id":"\([^"]*\)".*/\1/p')
echo "project created: $PID"
TID=$(curl -s -X POST -H "$AUTH" -H "Content-Type: application/json" -d '{"title":"agent-check task","description":"created by the agent contract","priority":"low","status":"to-do"}' "$SITE_URL/api/task/$PID" | sed -n 's/^{"id":"\([^"]*\)".*/\1/p')
echo "task created: $TID"
{ curl -s -H "$AUTH" "$SITE_URL/api/task/tasks/$PID"; echo; } | sed -n 's/.*"title":"\(agent-check task\)".*/task read: \1/p'
curl -s -o /dev/null -w "task delete: %{http_code}\n" -X DELETE -H "$AUTH" "$SITE_URL/api/task/$TID"
curl -s -o /dev/null -w "project delete: %{http_code}\n" -X DELETE -H "$AUTH" "$SITE_URL/api/project/$PID"
```

A fresh deploy prints `health: 200`, `read without key: 401`, `write without key: 401`, `write wrong key: 401`, `public sign-up: 403`, a workspace id, a created project id, a created task id, `task read: agent-check task`, `task delete: 200` and `project delete: 200`.

## Why Deploy Kaneo on Railway?

Railway is a singular platform to deploy your infrastructure stack. Railway will host your infrastructure so you don't have to deal with configuration, while allowing you to vertically and horizontally scale it.

By deploying Kaneo on Railway, you are one step closer to supporting a complete full-stack application with minimal burden. Host your servers, databases, AI agents, and more on Railway.

- **Agent-ready** - no deployer fields, a contract block and one script that proves a sign-in, a write, a read, a delete and the refusal without a token.
- **Locked by default** - the deploy cannot start as an open instance where the first visitor becomes administrator.
- **Sessions survive redeploys** - the signing secret is generated once and kept stable.
- **Data survives redeploys** - PostgreSQL sits on a volume.
- **Pinned** - both images are pinned by digest.
- **Your tasks stay yours** - no SaaS seat pricing, no cloud account.

## Common Use Cases

- **Team or personal project management** - boards, tasks, labels and time tracking without a per-seat subscription.
- **Agent-driven task tracking** - a coding or ops agent files, updates and closes tasks over the REST API or the MCP server.
- **Jira or Linear alternative** - a lightweight self-hosted tracker you control.
- **Client and side-project boards** - one workspace per client, data on your own infrastructure.

## Dependencies for Kaneo Hosting

- PostgreSQL, deployed alongside as the `postgres` service. An S3-compatible bucket is optional (attachments). A custom domain is optional.

### Deployment Dependencies

- [Kaneo repository](https://github.com/usekaneo/kaneo)
- [Kaneo documentation](https://kaneo.app/docs)
- [Official Docker image](https://github.com/usekaneo/kaneo/pkgs/container/kaneo)
- [Wrapper image source](https://github.com/bon5co/kaneo-railway)


## Similar templates

- [Rocky Linux](https://railway.com/deploy/rocky-linux) — Hosted Rocky Linux 9 workspace with SSH and persistent storage. 🚀
- [Foundry Virtual Tabletop](https://railway.com/deploy/X5tR6G) — A Self-Hosted & Modern Roleplaying Platform
- [Letta Code Remote](https://railway.com/deploy/letta-code-remote) — Run a Letta Code agent 24/7. No inbound ports, just deploy.

Open this page in a browser: https://railway.com/deploy/kaneo-or-just-updated-self-hosted-projec
