Getting Started
From zero to running in five minutes. AppKask ships as a single binary with Docker Compose support.
Quick Start
Option 1: Docker Compose (Recommended)
# Clone the repository
git clone https://github.com/jueewo/appkask.git
cd appkask
# Start everything
docker compose up -d
# Open in browser
open http://localhost:3000
The first run will:
- Create the SQLite database (
media.db) - Apply all migrations automatically
- Create the storage directory structure
- Start the web server on port 3000
Option 2: Build from Source
# Prerequisites: Rust toolchain, FFmpeg, Ghostscript, cwebp
cargo build --release
# Configure
cp .env.example .env
# Edit .env with your settings
# Run
./target/release/video-server
First Steps After Login
- Enable emergency login (development): Set
ENABLE_EMERGENCY_LOGIN=truein.env - Create a workspace: Click “New Workspace” and give it a name
- Create a folder: Navigate into your workspace, create a folder
- Assign a type: Click the folder settings icon, choose “media-server”
- Upload media: The folder now shows an upload interface — drag and drop your files
- Share: Click “Share” to generate an access code — send the link to anyone
Environment Variables
# Required
DATABASE_URL=sqlite:media.db
STORAGE_DIR=./storage
# Authentication (OIDC)
OIDC_ISSUER=https://auth.example.com
OIDC_CLIENT_ID=your_client_id
OIDC_CLIENT_SECRET=your_secret
OIDC_REDIRECT_URI=http://localhost:3000/auth/callback
# Development
ENABLE_EMERGENCY_LOGIN=true
# Production
RUN_MODE=production Architecture
The Stack
| Layer | Technology |
|---|---|
| Language | Rust (stable) |
| Web Framework | Axum 0.8 |
| Templates | Askama 0.13 (SSR, type-safe) |
| Database | SQLite via sqlx (compile-time checked) |
| Sessions | tower-sessions 0.14 + SQLite store |
| Auth | OIDC (Casdoor recommended) |
| CSS | TailwindCSS v4 + DaisyUI |
| Video | FFmpeg (HLS) + MediaMTX (RTMP) |
| Observability | OpenTelemetry 0.31 + OTLP/gRPC |
Workspace Crate Architecture
AppKask is a Cargo workspace with 34 crates organized by domain:
crates/
common/ # Shared types, storage, database
media-core/ # Media detection, EXIF extraction
media-manager/ # Upload, serve, search, CRUD
video-manager/ # HLS transcoding (8-stage pipeline)
access-control/ # 4-layer permission model
access-codes/ # Shareable access links
access-groups/ # Team roles and invitations
user-auth/ # OIDC + session management
workspace-manager/ # Workspace browser and folder types
vault-manager/ # Storage vault isolation
site-generator/ # Astro site generation
course/ # Course viewer + presentations
...and 22 more
The Dual-Use Pattern
Every app crate implements the FolderTypeRenderer trait for embedded mode (inside workspace browser) and exports a Router for standalone mode (own URL). Same logic, same templates, two deployment modes.
Storage Layout
storage/
workspaces/{workspace_id}/ # File browser content
folder-a/ # Regular folder
media-gallery/ # Typed folder (media-server)
vaults/{vault_id}/ # Media pipeline storage
media/
images/{slug}.webp
videos/{slug}/index.m3u8
documents/{filename}
thumbnails/
images/{slug}_thumb.webp
videos/{slug}_thumb.webp
Rate Limiting
Three tiers based on resource intensity:
| Tier | Limit | Endpoints |
|---|---|---|
| Default | 60 RPM | Most API endpoints |
| Upload | 15 RPM | File upload, transcoding |
| Serving | 300 RPM | Media delivery, thumbnails |
Pull the latest Docker image and restart. Database migrations are applied automatically on startup. Your data and storage are preserved via Docker volumes.
Copy two things: the
media.db SQLite file and the storage/ directory. That's your entire platform state. No external services to coordinate. Yes. AppKask works behind nginx, Caddy, or Traefik. Set
RUN_MODE=production to enforce HTTPS security checks. WebSocket endpoints need proxy WebSocket support enabled. Configure OIDC_ISSUER, OIDC_CLIENT_ID, OIDC_CLIENT_SECRET, and OIDC_REDIRECT_URI environment variables. AppKask supports any OIDC provider — Casdoor is recommended for self-hosted setups.
Required in PATH: ffmpeg and ffprobe (video), gs / Ghostscript (PDF thumbnails), cwebp (WebP conversion). Optional: mediamtx (RTMP live streaming).