Curator
Curator is a desktop app for managing a Jellyfin-first movie and series library. You import video files into a managed pool; Curator identifies them through TMDb, names and lays them out the way Jellyfin expects, and can generate a genre-split miniDLNA tree of hardlinks for simple DLNA players — without ever duplicating the video data on disk.
Metadata (posters, plots, .nfo files) is Jellyfin's job; Curator owns the
files, their names and the library structure. Written in Rust with an egui GUI.
Concepts
-
Pool — the managed folder and the single source of truth. Curator imports, renames and removes files itself, so nothing moves behind its back. Each top-level folder is a library with a kind:
Kind Holds Layout moviemovies Title (rok) [tmdbid-N].ext, or a folder once a film has several versionsseriesseries Series (rok) [tmdbid-N]/Season NN/SxxEyy - Series.extmixedmovies and series together as above, side by side homevideofiles without a TMDb id mirrored as-is -
Pool index — Curator's own metadata (TMDb id, ČSFD link, versions, tags, library settings) lives in one
.Curator.!indexJSON file at the pool root. -
miniDLNA output — a generated tree of hardlinks into the pool, built from genres / years / countries / ratings. It is disposable: delete it and regenerate it at any time.
Features
- Import movies and episodes with a TMDb id; Czech titles come from TMDb, with ČSFD as a fallback and as a bridge for finding the right TMDb id.
- Multiple versions of one film (2D/3D, 4K, director's cut) and multi-part films and episodes, named so Jellyfin groups them.
- Subtitle sidecars follow their video through renames.
- Duplicate check, video integrity check (FFmpeg), library statistics, index/disk consistency check.
- Jellyfin integration: trigger a library scan, verify the pool against it.
- miniDLNA tree scoped per library, with "Tipy dne" and "Nově přidané" folders.
Requirements
- Rust 1.85+ (
rustup), for building ffmpeg/ffprobeonPATH— optional, for the integrity check
Configuration
Secrets and settings are read from a .env file in the working directory
(never committed):
| Variable | Purpose |
|---|---|
TMDB_API_KEY |
TMDb API key — needed to identify movies and series |
TMDB_LANGUAGE |
TMDb language, default cs-CZ |
JELLYFIN_URL |
Jellyfin server URL — optional, for the Jellyfin menu |
JELLYFIN_API_KEY |
Jellyfin API key — optional |
ENV_DEBUG |
true enables debug logging and the -DEV title |
The pool and output folders are chosen in the app (Pool menu) and stored in
the global config (~/.config/curator/.Curator.!gtag on Linux, overridable with
CURATOR_CONFIG).
Running
cargo run --release
Development
cargo fmt # format
cargo clippy -- -D warnings # lint
cargo test # unit tests + headless UI tests
cargo doc --open # API reference
cargo run --example screenshot -- out.png [--action edit] renders the window
offscreen to a PNG. Architecture and module overview: docs/.
Building
cargo build --release
The result is target/release/curator, plus target/release/tipy-dne — a
standalone "Tipy dne" refresher meant for a systemd timer (see
scripts/tipy-dne.service / .timer).