Skip to content
tdeverxPublic

About

Self-hosted media tracker with playback, watch history, discovery and requests.

Resources

Contributing

Security policy

Stars

2 stars

Watchers

1 watching

Forks

Repository files navigation

Coast mark

Coast

A self-hosted home for what you watch, play and listen to.

Your library, progress and friends, together in one place.

Build and preview image AGPL-3.0-only

Features · Experiments · Get started · Documentation

Warning

Coast is an early preview. Updates can include breaking changes, so back up your data before upgrading. Databases from the earlier prototype are not supported.

Coast brings your media and personal tracking together without making your collection depend on one server. Browse what is available, keep a watchlist, resume an episode, and see what your friends are enjoying. Connect Jellyfin for playback and Trakt for personal tracking; add other services when you need them.

Films and TV are the core experience. Music, games and shared playback are available as optional experiments. Coast runs on your own server and stores its data there.

The Magicians show page in Coast, with its hero and Seasons row

What you can do

Find your next title

Discover trending and recent releases. For You brings together Continue, Next, favourites, recommendations and activity, with personalised rows that appear as you scroll.

Personalised rows use cached provider suggestions and your own taste signals across enabled media. Friend popularity is part of those rows; recommendations do not automatically add items to your Collection.

Keep your own collection

Track progress, history, ratings, favourites, saved titles and lists—even when a title is not currently playable. Choose what automatically joins your Collection.

Browse your libraries

Explore connected media, then narrow it down with Collection and Available filters. Both default off in Library; profile libraries show that person's Collection.

Play from Jellyfin

Watch films and episodes with resume positions, subtitles and a persistent player. Request missing media through Seerr when it is configured.

Stay connected

Add friends, send recommendations, react to activity and see taste matches. Friends and notifications open in panels so you can keep browsing.

Choose what you share

Profiles default to friends only, with public and private options. Control live activity sharing separately, and choose a private site, public profiles only, or public read-only browsing.

Manage your installation

Invite users, choose signup requirements, inspect sync jobs and review server streams and recorded sessions. Developer mode pauses automatic work while keeping manual actions available.

Use your data

Create scoped API tokens for reads and supported writes, and connect signed webhooks. Your tokens are limited to the permissions you select.

Measure performance

Run local benchmarks and compare results over time. Saved measurements help you spot changes in database and server workloads.

Sync you can follow

Settings → Jobs & schedules shows what is running, waiting, needs attention, is scheduled next, or is manual. Each task shows its last result and timing, with Run now, Retry and schedule controls where applicable. Long imports can pause at saved checkpoints so higher-priority work can proceed; initial imports take priority over routine background work. Detailed job history remains in the logs.

The optional Jellyfin companion provides server change hints, live activity and stream updates so Coast can target changed items. It also supports trailer crop analysis. Native polling remains available when the plugin is unavailable.

Experiments

Administrators enable these separately in Settings → Policies → Experimental features. They default off; disabling one hides it without deleting saved data.

Dynamic For You and personalised recommendations are standard features and no longer have experimental switches. The experiment guide explains each feature's behaviour and limits.

Music

Browse Jellyfin artists, albums and tracks; keep listening history and queues; listen while browsing. Playable albums and tracks use Play as their main card action.

Gaming

Discover games through IGDB, import Steam ownership, playtime and supported achievement progress, and track playthroughs and sessions. Steam ownership is availability evidence, not proof of a local installation.

Parties

Invite friends into a shared video or audio session with synced playback, participant controls and buffering policies. Each person needs their own permitted source; listening also requires Music.

Planning & calendar

Schedule titles and reminders. Upcoming on For You shows known releases for watchlisted titles and tracked shows.

Media detail overlay

Open the existing hero and details over the page you are browsing, with a full-page option. Its presentation is still under review.

Still being refined

Coast is actively developed. These areas have implementations, but need broader acceptance or further polish:

  • Provider and playback compatibility: real-account Trakt and Seerr journeys, reconnects, genuine sync conflicts and playback across more devices and sources.
  • Recommendations and first-run experience: better exact-next-item choices, more useful guidance during imports, and clearer empty Collections for new users.
  • Performance and recovery: continued measurement of imports, queries, rendering and resource use. Benchmarks and runtime diagnostics are available; a benchmark is not a live playback or browser performance test.
  • Social details: validate privacy, live activity and taste scores with more real accounts, and revisit what friend avatars communicate.

See release readiness and the performance guide for verification evidence. Fixture tests do not establish compatibility with every live provider or device.

Planned and under consideration

These are roadmap ideas, not available features or promises of a release date.

Planned follow-ups

  • Separate profiles under one account.
  • Playback without personal tracking.
  • Richer social recaps.
  • A dedicated pass on challenges and achievements.

Ideas to revisit

  • Profile comparison charts.
  • Collaborative lists, groups, shared queues and polls.
  • Chat or reaction overlays during parties.
  • Broader media, including books and comics.
  • More Library, search and playback conveniences.

The chart gallery in the UI preview explores designs with fictional data. The full roadmap records priorities, parked proposals, open questions and the privacy and provider requirements for future work.

Start Coast

Use Docker Desktop or another Docker installation with docker compose available. The default image includes Coast and PostgreSQL; no separate database service is required.

  1. Create a folder for your installation and open a terminal in it.

  2. Download the Compose file:

    macOS, Linux, WSL or Git Bash

    curl -fsSLo compose.yaml https://raw.githubusercontent.com/tdeverx/coast/main/compose.yaml

    Windows PowerShell

    Invoke-WebRequest https://raw.githubusercontent.com/tdeverx/coast/main/compose.yaml -OutFile compose.yaml
  3. Pull the preview image and start Coast:

    docker compose pull
    docker compose up -d --no-build
  4. Open http://localhost:3000 and create your administrator account. Enter a username, display name and matching passwords of 8–128 characters, including an uppercase letter, a lowercase letter and a special character. Email is optional for the first administrator.

The published image is ghcr.io/tdeverx/coast:preview, built for linux/amd64 and linux/arm64. Compose exposes port 3000 and uses the persistent coast-data volume for the database, encrypted service credentials, artwork and runtime state. Keep that volume when updating.

LAN access and reverse proxies

Set ORIGIN in compose.yaml to the exact address people use to open Coast, including the scheme and port. For example:

ORIGIN: http://192.168.1.20:3000

Use your server's actual LAN address, then apply the change with docker compose up -d --no-build. Other devices can open that same address.

For a public domain, terminate HTTPS at your reverse proxy and use its public address, such as ORIGIN: https://coast.example.com. Administrators can keep the website private, allow public profiles only, or enable public read-only browsing; profile privacy still applies, and public browsing does not grant playback access. See deployment for storage, proxy and external PostgreSQL configuration.

Services and new accounts

Configure shared services in Settings → Integrations. Personal service accounts are linked under Connections or during registration.

In Settings → Policies, administrators choose:

  • Registration: invite-only or open sign-ups.
  • Required connection: Jellyfin, Trakt, either, or none.

The defaults are invite-only registration with Jellyfin required. Configure an approved Jellyfin server before inviting users under that policy. Administrators create expiring, single-use codes in Settings → Accounts.

New users create their Coast username, display name and password, connect their services, and optionally upload a profile picture or choose a connected-service image. Animated GIFs keep their animation. Selected initial imports finish on a loading screen before users enter the app; failed imports offer recovery actions.

Sign-in uses Coast credentials. Jellyfin is a media connection, not a sign-in method. Trakt onboarding imports history, progress, ratings, watchlist and lists without enabling outbound synchronization. Existing Jellyfin-only accounts need an administrator to set a Coast password.

Updates

From your installation folder:

docker compose pull
docker compose up -d --no-build

Back up the database and the entire secrets/ directory together before upgrading. The credential encryption key lives in that directory; restoring the database without its original key cannot recover saved provider tokens. See backup and restore verification.

Build from source

git clone https://github.com/tdeverx/coast.git
cd coast
docker compose up --build -d

This uses the same Compose configuration and persistent volume. Set DATABASE_URL in Compose to use an existing PostgreSQL database instead of the bundled one. The database must already exist, and its account must be allowed to run migrations. Keep /data mounted for credentials, artwork and runtime state in either setup.

Connected services

Service What it adds
Jellyfin Accessible server media, playback, activity import and supported tracking reconciliation.
TMDB Film and TV metadata, discovery and background catalogue maintenance.
Trakt Account linking, tracking and list imports, live activity and independently configured exports.
Seerr Media requests and request status.
IGDB · experimental Game search, metadata and catalogue imports.
Steam · experimental Owned games, playtime and achievement progress, with ownership-based availability.

Personal tracking, profiles and lists can work without connected services when the registration policy allows it. Server availability is separate from personal membership: owning or tracking something does not make it playable. Steam ownership does not prove a game is installed locally.

Provider settings determine what is imported and exported. Trakt Collection export is opt-in and uses previews for projection changes and cleanup. Live Trakt and Seerr acceptance still needs deliberate real-account testing.

Keep API keys and passwords in Coast's settings. Do not include them in source control or bug reports. Saved provider credentials are encrypted, and Coast has no telemetry.

More detail: Collection and Library · Music · Games · Social · Provider behavior.

API access

Create scoped, expiring tokens in Settings → API access for catalogue, Collection, Library and progress reads, tracking and relationship writes, and signed webhooks. Writes require idempotency keys; tokens do not grant playback, administrator access or another user’s data. See the Public API guide for endpoints, permissions, pagination and webhook verification.

Develop Coast

Development requires Bun 1.4.3 and PostgreSQL. Create a development database, then run:

bun install --frozen-lockfile
export DATABASE_URL='postgresql://coast:password@localhost:5432/coast'
export COAST_DATA_DIR="$PWD/.data"
bun run db:migrate
bun run dev

Open the URL printed by Vite, usually http://localhost:5173. The server also listens on network interfaces for LAN testing. Use a development database rather than your deployed installation's data.

Run the local checks with:

bun run code:inventory
bun run ui:inventory:check
bun run check
bun run test
bun run build

For database regression tests, provide a PostgreSQL account allowed to create disposable databases:

export TEST_DATABASE_URL='postgresql://postgres:password@localhost:5432/postgres'
bun run test:db

The runner creates and removes an isolated database for each suite; it does not run tests against the database named in that URL. Provider fixtures do not establish live-service compatibility.

Administrators can open /ui-preview to inspect the shared typography, colors, materials, elements and components, including the material tweaker. /ui-preview?section=charts contains the non-approved chart exploration with isolated fictional data; its fictional data stays in the preview. See Chart preview, Contributing and Architecture for development conventions.

Administrators can run bounded local measurements in Settings → Benchmarking and compare compatible runs in the saved history. These measure selected database and server workloads, not browser rendering or live playback. The performance guide documents the shared optimisation patterns, isolated regression harness, measurement limits and runtime diagnostics.

Project

For bug reports, questions and feature ideas, use GitHub Issues.

Coast is licensed under AGPL-3.0-only, and contributions use the same license. Connected services are independent of Coast. Coast is not endorsed or certified by TMDB.

About

Self-hosted media tracker with playback, watch history, discovery and requests.

Resources

Contributing

Security policy

Stars

2 stars

Watchers

1 watching

Forks

Releases

Packages

Contributors

Languages