Vikunja on a VPS: Self-Hosted Task and Project Management with Kanban, Gantt, and Lists
Vikunja is an open-source task management application — a self-hosted alternative to Todoist, Asana, or Linear for personal and team task tracking. It provides tasks organized in projects, Kanban board view, Gantt chart, calendar view, labels, priorities, due dates, reminders, CalDAV sync (works with iOS Reminders and Android tasks), and a REST API. A single binary for easy self-hosting, or Docker for isolation.
Step 1: Single Binary Install
<code"># Download Vikunja binary (includes frontend + backend in one file)
mkdir -p /opt/vikunja && cd /opt/vikunja
wget https://dl.vikunja.io/vikunja/stable/vikunja-stable-linux-amd64 \
-O vikunja
chmod +x vikunja
# Create configuration:
cat > config.yml << 'EOF'
database:
type: "sqlite"
path: "./vikunja.db"
service:
jwtsecret: "CHANGE_THIS_RANDOM_SECRET_64_CHARS"
publicurl: "https://tasks.yourdomain.com"
enableregistration: false # Invite-only
enableemailreminders: true
mailer:
enabled: true
host: "smtp.mailgun.org"
port: 587
username: "[email protected]"
password: "your_smtp_password"
fromemail: "[email protected]"
tls: true
EOF
# Start Vikunja
./vikunja &
<code">sudo nano /etc/systemd/system/vikunja.service
<code">[Unit] Description=Vikunja Task Manager After=network.target [Service] Type=simple User=ubuntu WorkingDirectory=/opt/vikunja ExecStart=/opt/vikunja/vikunja Restart=on-failure [Install] WantedBy=multi-user.target
<code">sudo systemctl enable vikunja && sudo systemctl start vikunja
Step 2: Docker Compose (Alternative)
<code">mkdir -p /opt/vikunja-docker && cd /opt/vikunja-docker nano docker-compose.yml
<code">version: '3.8'
services:
vikunja:
image: vikunja/vikunja:latest
container_name: vikunja
restart: always
ports:
- "127.0.0.1:3456:3456"
environment:
VIKUNJA_SERVICE_PUBLICURL: https://tasks.yourdomain.com
VIKUNJA_SERVICE_JWTSECRET: ${JWT_SECRET}
VIKUNJA_DATABASE_TYPE: postgres
VIKUNJA_DATABASE_HOST: vikunja-db
VIKUNJA_DATABASE_DATABASE: vikunja
VIKUNJA_DATABASE_USER: vikunja
VIKUNJA_DATABASE_PASSWORD: ${POSTGRES_PASSWORD}
VIKUNJA_MAILER_HOST: smtp.mailgun.org
VIKUNJA_MAILER_PORT: 587
VIKUNJA_MAILER_USERNAME: [email protected]
VIKUNJA_MAILER_PASSWORD: ${SMTP_PASSWORD}
VIKUNJA_MAILER_FROMEMAIL: [email protected]
volumes:
- vikunja_files:/app/vikunja/files
depends_on:
vikunja-db:
condition: service_healthy
vikunja-db:
image: postgres:16-alpine
restart: always
environment:
POSTGRES_DB: vikunja
POSTGRES_USER: vikunja
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
volumes:
- vikunja_db:/var/lib/postgresql/data
healthcheck:
test: ["CMD-SHELL", "pg_isready -U vikunja"]
interval: 10s
timeout: 5s
retries: 5
volumes:
vikunja_files:
vikunja_db:
Step 3: Nginx Reverse Proxy
<code">sudo nano /etc/nginx/sites-available/vikunja
<code">server {
listen 443 ssl http2;
server_name tasks.yourdomain.com;
ssl_certificate /etc/letsencrypt/live/tasks.yourdomain.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/tasks.yourdomain.com/privkey.pem;
location / {
proxy_pass http://127.0.0.1:3456;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
<code">sudo certbot --nginx -d tasks.yourdomain.com sudo systemctl reload nginx
Step 4: CalDAV Sync
<code"># Vikunja supports CalDAV for syncing with: # - iOS Reminders / macOS Reminders # - Any CalDAV-compatible client (Thunderbird, GNOME Calendar) # CalDAV endpoint: https://tasks.yourdomain.com/dav/ # iOS Setup: # Settings → Calendar → Accounts → Add Account → Other # Add CalDAV Account # Server: tasks.yourdomain.com/dav/ # Username: your Vikunja email # Password: your Vikunja password # macOS Reminders: # Reminders → Preferences → Accounts → + → CalDAV # Same settings as above
Step 5: API Integration
<code"># Get API token: Settings → API Tokens → Create
API_TOKEN="your_vikunja_api_token"
# Create a task:
curl -X PUT https://tasks.yourdomain.com/api/v1/projects/1/tasks \
-H "Authorization: Bearer $API_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"title": "Deploy new feature",
"description": "Deploy v2.1.0 to production",
"due_date": "2025-06-15T09:00:00Z",
"priority": 4,
"labels": [{"title": "urgent"}]
}'
# List all tasks:
curl https://tasks.yourdomain.com/api/v1/tasks/all \
-H "Authorization: Bearer $API_TOKEN"
# Complete a task:
curl -X POST https://tasks.yourdomain.com/api/v1/tasks/TASK_ID \
-H "Authorization: Bearer $API_TOKEN" \
-H "Content-Type: application/json" \
-d '{"done": true}'
Getting Started
Vikunja’s single binary with SQLite uses under 100 MB RAM — it runs on the smallest Ubuntu VPS at VPS.DO. The CalDAV integration with iOS Reminders and macOS is particularly valuable: create tasks on the VPS, they appear in your native iOS/macOS apps. For individuals replacing Todoist ($4/month) or teams replacing Asana ($11/user/month), self-hosted Vikunja provides equivalent functionality at infrastructure cost.
Conclusion
Vikunja provides self-hosted task management with multiple views (list, Kanban, Gantt, calendar), CalDAV sync to native device apps, priorities, labels, due dates, and a REST API — in a single lightweight binary. For individuals and teams wanting private task management without per-seat fees, Vikunja is the most capable self-hosted option in its category.