Serein
Rust로 만든 가볍고 성능 좋은 Discord 전용 네이티브 클라이언트
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
개인 계정의 공개 저장소 소유자는 GitHub로 로그인해 운영자를 확인하고 소개를 직접 관리할 수 있습니다. 관리자 승인은 필요하지 않습니다.
로그인한 뒤 확인 파일을 만들어 이 저장소의 기본 브랜치에 30분 안에 커밋해 주세요. 다른 브랜치나 포크의 파일은 인정하지 않습니다. 파일을 올린 뒤 아래에서 확인하면 관리자 승인 없이 관리할 수 있습니다. 자격을 유지하려면 파일을 남겨 두세요.
로그인이 필요하면 로그인 화면으로 이동합니다. 로그인 후 이곳으로 돌아와 원하는 확인 버튼을 다시 눌러 주세요.
프로젝트 폴더에서 /nomorevibe verify를 실행하면 소유권을 확인하고 소개를 직접 관리할 수 있습니다.
1분 만에 확인하기Virtual watch-party: synced YouTube and Twitch, voice, chat and screen sharing in shared rooms.
저장소 README에서 가져옴
README 전체를 불러오는 중입니다.
README 전문 보기 ↗Watch together, wherever you are. Voice, chat, synced YouTube, Twitch and Kick, and screen sharing in one shared room. Installs as an app on phones and desktops.
Live at nexuslounge.party.
I built it so my friends and I could watch League of Legends Worlds together, but it's general purpose: sports, premieres, VODs, movie nights.
| Phone | Phone: streams | Phone: landscape |
|---|---|---|
| Collapsed side panel | People | Room settings |
|---|---|---|
| Playlists and queue | Landscape with chat open |
|---|---|
| Choose where video plays (TV connected) | Phone player bar: More menu | Account |
|---|---|---|
Rooms and people
Watching
127.0.0.1:11470, or any address you set); links play straight in the browser when they can, and through Stremio when they can't (insecure http redirects, formats your browser can't decode, services that block browsers), which converts them to HLS that plays everywhere. Matroska plays as it is on Chrome and Edge, and HEVC/AC3/E-AC3 are used directly where your browser decodes them. Friends without Stremio watch a live feed from the owner's browser. Friends with Stremio tap to download the torrent themselves, in sync, with no load on the owner, or paste their own link or magnet to the same video (the size and length must match). Links stay in the owner's tab and are never sent to the room or the server, expired ones can be replaced in place, and error clips from link services are flagged. Chrome and Edge ask once to let the site reach devices on your network. Subtitles (tracks inside the video, files that came with a torrent, a file from your computer, or a search by title through OpenSubtitles) are chosen per person.Playback controls
Voice and chat
Phones and tablets
Desktop
\ key) to be fully immersed. Voice controls move into the header and an unread badge keeps you posted on chat.F fullscreen, M mute, and for controllers Space/K play and pause, ←/→ skip 5 seconds, J/L skip 10 seconds. Shortcuts are ignored while typing.Any screen
/account. Terms of Service and Privacy Policy are public at /terms and /privacy (use these URLs in the Discord developer portal).flowchart LR
B[Browser<br/>Next.js app] -- HTTPS --> W[web<br/>Next.js + Auth.js]
W -- signed token --> S[server<br/>Fastify + ws]
B -- WebSocket ticket --> S
B -- WebRTC --> L[(LiveKit)]
S -- grants and tokens --> L
apps/web Next.js app (UI, Discord login via Auth.js, thin API routes)
apps/server Fastify + ws (rooms in memory, LiveKit tokens, sync WebSocket)
packages/shared zod schemas, types and the sync maths shared by both
docs/ Railway notes and screenshots
Requirements: Node 22.18+ (the server runs TypeScript directly), pnpm 10+, and Docker only if you self-host LiveKit locally.
Setup
pnpm installcp .env.example .env and fill it in (below).pnpm dev, then open http://localhost:3000.pnpm dev starts the web app (port 3000) and the server (port 4000). For local voice, run pnpm livekit in another terminal (needs Docker), or use LiveKit Cloud instead.
DISCORD_CLIENT_ID and reset/copy the Client Secret into DISCORD_CLIENT_SECRET.http://localhost:3000/api/auth/callback/discord (add your production URL the same way).AUTH_SECRET with openssl rand -base64 32..env.example): pnpm livekit runs LiveKit in dev mode with key devkey and secret secret, at ws://localhost:7880.wss://….livekit.cloud) into LIVEKIT_URL and an API key/secret pair from Settings → Keys into LIVEKIT_API_KEY / LIVEKIT_API_SECRET.| Variable | Used by | Purpose |
|---|---|---|
DISCORD_CLIENT_ID, DISCORD_CLIENT_SECRET | web | Discord OAuth |
AUTH_SECRET | web, server | Session encryption and server token signing (must match) |
AUTH_URL | web | Public URL of the web app |
LIVEKIT_URL, LIVEKIT_API_KEY, LIVEKIT_API_SECRET | server | LiveKit connection and token minting |
NEXT_PUBLIC_SERVER_WS_URL | web | WebSocket URL of the server (wss://<server>/ws); the HTTP URL is derived from it |
SERVER_WS_URL | web | Optional runtime override of the above. Next bakes NEXT_PUBLIC_* values in at build time, this one is read when the app runs |
PORT | server | Server port (default 4000) |
ADMIN_SECRET | web, server | Optional. 32+ random characters, different from AUTH_SECRET; signs admin requests and the admin session cookie |
ADMIN_DISCORD_IDS | web, server | Optional. Comma-separated Discord user IDs allowed to open /admin |
ADMIN_TOTP_SECRET | web | Optional. Base32 key for the authenticator app used to unlock /admin |
AUTH_SECRET) and call the Fastify server, which verifies it. Joining a room returns a LiveKit token plus a room-scoped ticket for the sync WebSocket.packages/shared/src/protocol.ts).position, playing and a server timestamp. Clients estimate the server clock (median of ping samples) and compute the expected position locally. Drift is the median of the last few readings, small drift is fixed by gently changing playback speed, and seeks are rare and debounced. Add ?debug to a room URL to see the live numbers.pnpm typecheck
pnpm --filter @nexus/shared test # URL parsing, drift maths, live-edge helpers, tokens, sound cues
pnpm --filter @nexus/server test # spawns the server; permissions, guest approval, removal, moderation,
# late joiners, passwords, tickets, TV pairing over real WebSockets
CI runs the same checks plus a production build on every push.
Browser end-to-end suites (Chrome plus WebKit for the iPhone-style checks) live in e2e/: rooms, voice, push to talk, fullscreen, the queue and playlists, gestures, phone layouts and "nothing covers the Twitch player".
Two services built from the Dockerfiles in apps/server and apps/web, auto-deployed from main. LiveKit must be LiveKit Cloud, since Railway doesn't support UDP. Step-by-step instructions and config templates are in docs/railway-deploy.md.
Every server deploy or restart ends all rooms, because they live in memory. Keep the server at a single instance.
Copyright (C) 2026 dsameendra
Nexus Lounge is free software under the GNU Affero General Public License v3.0 (AGPL-3.0-or-later). You can use, modify and host it, but if you run a modified version as a service, you must make your version's source available to its users under the same license. Derivative works must stay open source.
If you like it and want to help with hosting costs, you can support it on Ko-fi. It is optional, and a star on the repo helps just as much.