Skip to content

SAKMZ/syncwave

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

14 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

🌊 Syncwave

Self-hosted, AI-powered listening rooms β€” your own Spotify Jam.

Start a room, share one link, and listen with your friends perfectly in sync β€” shared queue, live chat, floating reactions, vote-to-skip, and an optional AI DJ. Runs anywhere Docker does.

License: MIT Next.js 15 Node 20+ Self-hosted PWA

Deploy on Railway Deploy to Render Deploy to Hostinger


What it is

Syncwave is a small self-hosted web app for listening to music together. One person spins up a room and shares the link; everyone who joins hears the same track at the same moment. Anyone can search and add to a shared queue, the room can vote to skip, and everyone can chat and react while they listen β€” all on a server you control.

Think group DJ session: a house party, a long-distance movie-night-but-for-music, a study room, a Discord community's permanent hangout.

Features

  • 🎧 Perfectly synced playback β€” a server-authoritative clock drives every client's audio position, so nobody drifts out of sync.
  • πŸ”— One-link rooms β€” create a room, share the code or URL, done. No accounts.
  • βž• Shared queue β€” anyone in the room can search and add tracks.
  • 🎚️ Familiar player β€” a Spotify / YouTube-Music-style bottom player with shuffle and repeat (off / all / one) as shared room controls, plus play/pause, skip, and a scrubber. The host drives; everyone stays in sync.
  • πŸ—³οΈ Vote-to-skip β€” the room decides when to move on; the host can always drive.
  • πŸ’¬ Live chat + πŸŽ‰ floating reactions β€” talk and drop emoji that float up the screen for everyone in real time.
  • πŸ” Guided first-run setup β€” a /setup wizard claims the instance with an admin password, then a password-protected /admin console handles YouTube access and the AI DJ. No config files to edit.
  • πŸ€– Optional AI DJ β€” an opt-in host with swappable LLM providers (OpenAI / Anthropic / local Ollama) and selectable personas. Degrades gracefully if it's off or misconfigured.
  • πŸ“Œ Permanent rooms β€” rooms and settings persist across restarts, so a room link can live forever.
  • πŸ“± Installable PWA β€” install a room to your home screen and it opens straight back into that room (per-room manifest), no code re-entry. Great for permanent community rooms. (Install requires HTTPS β€” see DEPLOY.md.)
  • πŸ“² Mobile-first UI β€” a compact app shell (fixed top bar + bottom player, tabbed Queue / Add / Chat) that fits a phone screen, plus an aurora backdrop, album-art ambient glow, and glassmorphism.
  • 🐳 One-container deploy β€” Next.js + realtime server + audio resolver in a single Docker image.

How it works

  • A Next.js front end (App Router, React 19) is the room UI and installable PWA.
  • A custom Socket.io server is the single source of truth for the playback clock, queue, chat, and reactions. Clients render their <audio> position from the server's timestamps, so playback stays locked together.
  • An audio resolver fetches each track with yt-dlp, caches it to disk, and serves it with HTTP range support. Search is powered by ytmusic-api.
  • State is durable via simple JSON files (no database to run) β€” rooms and settings survive restarts; cached audio auto-evicts 72h after its last play.

It all runs in one process / one container.

Quick start (local)

cp .env.example .env       # optional: tweak PUBLIC_URL etc.
npm install
npm run dev                # http://localhost:3000

Requires Node 20+ and ffmpeg on your PATH (yt-dlp uses it to extract audio).

Deploy

Syncwave is stateful β€” a long-lived WebSocket server, live yt-dlp processes, and a disk cache β€” so it needs an always-on host with a persistent disk. It does not run on Vercel, Netlify, or any serverless platform. Two easy paths:

πŸš‚ Fastest start β€” Railway (free $5 trial)

Deploy on Railway

The only path that gets you a live HTTPS instance without entering a card. Click β†’ GitHub Repository β†’ SAKMZ/syncwave. Railway reads railway.json and picks up the volume and env vars from render.yaml automatically. Full steps + what to check afterwards β†’

πŸš€ One click β€” Render

Deploy to Render

Render reads render.yaml and provisions the container, a persistent disk, and HTTPS for you. You get a https://…onrender.com link where Install app works right away. Needs a paid instance (~$7/mo) β€” free instances have no disk and sleep when idle, which would drop everyone in the room.

πŸ–₯️ One command β€” your own VPS

Deploy to Hostinger

More control, a much bigger audio cache, and cheaper as you grow. On any fresh Ubuntu box:

curl -fsSL https://raw.githubusercontent.com/SAKMZ/syncwave/main/scripts/install.sh | sudo bash

Add DOMAIN=music.example.com EMAIL=you@example.com to also get automatic HTTPS via Caddy. The installer handles Docker, the build, the reverse proxy, and the certificate β€” and re-running it updates in place.

Full VPS walkthrough β†’ HOSTINGER.md β€” including a post-install script that provisions the VPS with Syncwave already running, so you never have to SSH in at all.

🐳 Anywhere else β€” Docker

cp .env.example .env       # set PUBLIC_URL=https://your.domain (or http://IP:3000)
docker compose up -d --build

Data persists in two bind-mounts: ./data (rooms + settings) and ./cache (resolved audio).

Full instructions β€” reverse proxies, HTTPS, Tailscale, and YouTube cookies for datacenter IPs β€” are in DEPLOY.md.

After deploying

Open your instance and it walks you through /setup β€” set an admin password, optionally upload a YouTube cookies.txt, optionally switch on the AI DJ. Do this right away: until a password is set, anyone who can reach the URL can claim it. Rooms themselves are unaffected; the password only guards configuration.

⚠️ Where you host this decides whether music actually plays

YouTube blocks datacenter IPs, and cookies do not lift the block. Verified on Railway with valid logged-in cookies, a working JS runtime, and all five yt-dlp player clients β€” every one was refused. The same build on a home connection works with no cookies at all.

  • Home server or residential-IP VPS β†’ playback works. This is the intended way to run Syncwave.
  • Railway / Render / big-cloud VPS β†’ rooms, search, sync, and chat all work, but tracks will not resolve unless you set YTDLP_PROXY to a residential proxy.

A cookies.txt (uploaded at /admin β†’ YouTube access) still helps on borderline connections. Use a throwaway Google account β€” the file is a live login session and every track the server fetches is attributed to it. Details in DEPLOY.md.

Configuration

Copy .env.example to .env. Key settings:

Variable What it does
PUBLIC_URL Base URL of the instance. Falls back to RENDER_EXTERNAL_URL on Render.
PORT Port to listen on (default 3000).
DATA_DIR Where rooms/settings JSON lives (default ./data).
CACHE_DIR Where resolved audio is cached (default ./cache).
YTDLP_COOKIES_FILE Path to a YouTube cookies.txt (helps on datacenter IPs).

The AI DJ (provider, model, API key, persona) is configured at runtime in the in-app Setup console β€” no restart or rebuild needed.

Legal

Syncwave is a self-host tool. You run it and supply your own YouTube session; you are responsible for how you use it in your jurisdiction. Streaming audio from YouTube via unofficial tooling may violate YouTube's Terms of Service β€” do not operate a public, for-profit service on top of it.

Contributing

Issues and PRs are welcome. Good first areas: additional AI-DJ personas, alternative audio sources, theming, and accessibility. If you deploy it somewhere fun, open a discussion and say hi.

License

MIT Β© 2026 Syncwave contributors

About

🌊 Self-hosted, AI-powered listening rooms β€” your own Spotify Jam. Synced playback, shared queue, live chat, reactions, vote-skip & an optional AI DJ. One Docker container.

Topics

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages