A local-first hi-fi command center for your TIDAL library.
Lossless playback · library intelligence · DJ and radio tools · desktop plus phone remote
Download · Run from source · Configuration · Phone remote · Release checklist
NOORwave is a desktop TIDAL player built around a simple idea: your streaming library should behave like a fast local music collection.
It syncs your TIDAL library into SQLite, gives you a real desktop app with tray and media-key support, adds lossless playback controls, lets you shape the queue with search, radio, automix, DJ profiles, and a phone remote, and can save tracks to disk as FLAC or MP3. Everything runs on your own machine. A small Rust server (noor-server) owns the database, audio engine, and integrations; a Tauri desktop shell (noor-app) wraps the SvelteKit UI and launches that server for you.
noorwave-reel-attach.mp4
A tour of the desktop app: Home, Library, Search, the Genre Galaxy, listening analytics, and TIDAL video.
| Area | What NOORwave does |
|---|---|
| Library | Incremental TIDAL sync, local search, artist and album pages, playlists, duplicate detection, MusicBrainz and Last.fm enrichment. |
| Downloads | Save any track, album, or playlist to disk as bit-perfect FLAC or 320 kbps MP3, tagged, into a configurable Artist/Album/NN - Title library. Selectable FLAC tier (Hi-Res or CD) and MP3 source, with batch progress, cancel, and retry. |
| Playback | Lossless TIDAL playback, DASH segment seek, gapless transitions, crossfade, queue undo, shuffle modes, Windows WASAPI exclusive output. |
| DJ and radio | Automix, Song Radio, Last.fm fallback, learned similarity, harmonic scoring, DJ profile controls, reasons on queued tracks. |
| Discovery | Sound Space, blend discovery, training intensity tiers, safety preview, live ETA, model activation guidance. |
| Desktop app | Tauri shell, tray controls, media keys, auto-updater, portable builds, Windows per-user installer. |
| Phone remote | Installable /remote PWA for transport, queue, search, library browsing, action sheets, sleep timer. |
| Video | TIDAL video search and in-app HLS playback with quality selector and autoplay. |
NOORwave is for people who like TIDAL's catalog but want a better command center around it.
- TIDAL feels local. Your saved tracks, albums, artists, playlists, and metadata live in a local database, so search and browsing do not feel trapped behind a remote app shell.
- Playback is treated as the product. Lossless streaming, DASH seek behavior, gapless transitions, crossfade, media keys, tray controls, and Windows WASAPI exclusive mode are built into the core player.
- The queue is yours. Play next, append, reorder, save, undo clear, shuffle by intent, inspect radio reasons, and keep automix from fighting your manual choices.
- DJ mode is a control surface, not a gimmick. Profiles, harmonic matching, BPM and energy awareness, transition planning, and automix controls are there for shaping a session, not just filling silence.
- The phone remote makes it practical. Open
/remotefrom a phone on the same network and drive playback, queue, search, library pages, sleep timer, and track actions from the couch. - Your music lands on disk too. Right-click any track, album, or playlist (or use the download button on the now-playing art) to save it as bit-perfect FLAC or a portable 320 kbps MP3, tagged, in a tidy
Artist/Albumfolder you pick once in Settings.
The point is not every integration NOORwave can talk to. The point is a faster, more controllable TIDAL setup for people who actively listen, build queues, and care how playback moves from one track to the next.
The latest public build is on GitHub Releases.
| Platform | Artifact | Notes |
|---|---|---|
| Windows | NOORwave-vX.Y.Z-windows-x64-setup.exe |
Per-user installer. Installs to %LOCALAPPDATA%\Programs\NOORwave. Updates in place from signed Tauri updater metadata. |
| Windows | NOORwave-vX.Y.Z-windows-x64.zip |
Portable fallback. Unzip anywhere and run NOORwave.exe. |
| macOS ARM64 | NOORwave-vX.Y.Z-macos-arm64.tar.gz |
Portable build. Gatekeeper may require xattr -cr NOORwave noor-server. |
| macOS x64 | NOORwave-vX.Y.Z-macos-x64.tar.gz |
Portable build. |
| Linux x64 | NOORwave-vX.Y.Z-linux-x64.tar.gz |
Portable build. |
Windows builds are not CA-signed today. SmartScreen or Smart App Control can warn or block the first launch on strict systems. The installed updater payload is still signed with the project's Tauri updater key.
Prerequisites:
- Rust stable
- Node 24
- pnpm 10
- A TIDAL account (you sign in from inside the app)
The fastest path is the dev launcher, which starts the backend and the frontend dev server together (Windows Terminal split panes if available):
.\scripts\dev.ps1Or run the two processes yourself:
# Backend (Axum server, SQLite, audio engine)
cargo run -p noor-server
# Frontend dev server (separate terminal)
cd frontend
pnpm install
pnpm devWhere to open it:
- Frontend dev server:
http://127.0.0.1:17601(hot reload, talks to the backend on 17600). - Backend-served UI:
http://127.0.0.1:17600(the production build thatnoor-serverserves directly).
On first run the server prints an access PIN in a startup banner ("NOOR access token: ..."). On 127.0.0.1 the UI fetches that PIN for you, so you do not need to type it. You only need it on a phone or other device. You can always read it again in Settings -> Access PIN.
For the full desktop shell (it launches noor-server for you, adds the tray, media keys, and updater):
cargo run -p noor-app| Port | What | Default | Override |
|---|---|---|---|
| Backend | noor-server HTTP + WebSocket, and the /remote PWA |
17600 |
NOOR_PORT |
| Dev server | Vite frontend during pnpm dev |
17601 |
NOOR_DEV_PORT |
Two things worth knowing:
- The backend port is baked into the frontend at build time. If you change
NOOR_PORT, rebuild the frontend (pnpm run build) so the UI points at the right port. - The dev-server port is the only origin the backend trusts for CORS in dev. Keep
NOOR_DEV_PORTin sync on both sides; it usesstrictPort, so a busy port fails loudly instead of silently drifting to an untrusted one.
By default the server listens on 127.0.0.1 (loopback only), so nothing outside your machine can reach it. To expose it on your LAN (needed for the phone remote), pick one:
- Desktop app: tray icon -> Network access (restarts the server bound to
0.0.0.0). - Standalone server: pass
--host, which forces0.0.0.0. - Either: set
NOOR_ADDR=0.0.0.0:17600.
Precedence, highest first: NOOR_ADDR > --host > the saved Network-access / host_mode setting > 127.0.0.1.
All optional. The app ships with working defaults (including built-in TIDAL credentials).
| Variable | Purpose |
|---|---|
NOOR_PORT |
Backend listen port (default 17600). Rebuild the frontend after changing. |
NOOR_DEV_PORT |
Vite dev-server port (default 17601). Trusted CORS origin in dev. |
NOOR_ADDR |
Full bind address host:port. Overrides NOOR_PORT and --host. Use 0.0.0.0:17600 for LAN. |
NOOR_DB |
Path to the SQLite database file. |
NOOR_DATA_DIR |
Base data directory (database, token) for installed builds. |
NOOR_WWW_DIR |
Directory of the built frontend to serve. |
LASTFM_API_KEY / LASTFM_API_SECRET |
Last.fm enrichment; the secret also enables scrobbling. |
TIDAL_CLIENT_ID / TIDAL_CLIENT_SECRET |
Override the built-in TIDAL app credentials. |
TIDAL_PKCE_CLIENT_ID / TIDAL_PKCE_CLIENT_SECRET |
Override the TIDAL PKCE login credentials. |
DISCOGS_TOKEN / DISCOGS_USER_AGENT |
Discogs label and release metadata. |
SPORTIFY_API_BASE_URL |
Override the Sportify metadata proxy base URL. |
A handful of cache-tuning knobs (DISCOVERY_CACHE_TTL_DAYS, RESOLVE_CACHE_TTL_DAYS, RESOLVE_RETRY_AFTER_DAYS, RESOLVE_EAGER_N, RESOLVE_BULK_CONCURRENCY) exist for advanced tuning; defaults are fine for normal use.
The remote is a small web app at /remote, served by noor-server on the same port as everything else (no extra service, no extra port). It controls transport, queue, search, and library browsing from a phone on the same network.
Setup, once per device:
- Make sure the server is reachable on your LAN. Desktop app: tray icon -> Network access. Standalone server: run with
--host. (See Bind address.) - Find the desktop's LAN IP, for example
192.168.1.42. On Windows:ipconfig. - On the phone (same Wi-Fi), open
http://<desktop-LAN-IP>:17600/remote, for examplehttp://192.168.1.42:17600/remote. - Enter the access PIN when prompted. Get the 6-digit PIN from the desktop in Settings -> Access PIN. The phone caches it, so you only enter it once.
- Optional: use your browser's "Add to Home Screen" to install it as a standalone PWA.
Notes:
- Windows may show a firewall prompt the first time the server binds to the LAN. Allow it on private networks.
- Regenerating the PIN (Settings -> Access PIN) disconnects every device; they each have to re-enter the new PIN.
- There is no QR pairing yet. You type the URL and the PIN by hand.
# Rust
cargo check -p noor-server
cargo check -p noor-app
cargo test --workspace --locked
# Frontend
cd frontend
pnpm check
pnpm test
pnpm run buildWindows portable package:
cd frontend
pnpm run build
cd ..
.\scripts\build-portable.ps1noor-app Tauri 2 desktop shell, tray, media keys, updater, sidecar manager
noor-server Rust Axum server, SQLite, playback, integrations, WebSocket events
frontend SvelteKit 2 + Svelte 5 UI, static build served by noor-server
docs Specs, release notes, inventories, design memory
scripts Build, dev launcher, smoke, probe, and data utilities
How the pieces connect:
- Sidecar model. The Tauri shell spawns
noor-serveras a child process, waits forGET /api/ping, then opens the WebView. Shutdown goes throughPOST /api/shutdownbefore a force kill. - One server, two front doors. The same
noor-serverserves the desktop UI and the LAN/remotePWA. That is why the backend stays a real HTTP server instead of collapsing into Tauri IPC. - Auth. A single shared bearer token (the access PIN) gates every protected route:
Authorization: Bearer <pin>for/api/*, and?token=<pin>for the/wsWebSocket (browsers cannot set headers on WebSocket upgrades). On loopback the UI fetches the PIN automatically; other devices enter it once. - Storage. Everything lives in one local SQLite file (
noor.db), next to the executable by default or whereverNOOR_DB/NOOR_DATA_DIRpoint.
NOORwave is usable but still moving quickly. The 0.2.0 line is focused on integrating the active product branches into one coherent build, tightening the DJ and Last.fm flows, and making the release path less fragile.
Known constraints:
- Genre Galaxy is live but still needs interaction and rendering polish.
- ACRCloud fingerprint recognition is present as a placeholder, not a finished integration.
- Linux and macOS builds are portable-only today.
- Windows exclusive-mode audio is the most tuned output path.
- This is a single-user local app, not a hosted multi-user service.
Tags drive releases. Before tagging vX.Y.Z:
- Bump only
noor-server/Cargo.toml,noor-app/Cargo.toml,noor-app/tauri.conf.json, and the matchingnoor-app/noor-serverentries inCargo.lock. - Do not run bare
cargo update. - Keep both Windows artifacts: portable zip and NSIS setup exe.
- Keep
installMode: "currentUser"in the NSIS config. - Keep the Windows SmartScreen and Smart App Control note in release copy.
- Read
.github/workflows/release.ymlbefore changing release behavior. - After CI publishes, prepend the human "What's new" section with
gh release edit vX.Y.Z --notes-file <combined.md>.
Installed Windows release-ready means a signed local cargo tauri build --bundles nsis has been tested, the .sig exists, and mutable data still lives under %LOCALAPPDATA%\NOORwave.
Use small, focused changes. Keep Rust, Svelte, and TypeScript as the first-class languages. Do not commit local databases, generated build output, secrets, private signing keys, or machine-local config.
Useful checks:
git status --short
cargo fmt --all -- --check
cd frontend
pnpm check
pnpm test
pnpm run buildNOORwave uses TIDAL's unofficial API through PKCE OAuth2. It is not affiliated with, endorsed by, or associated with TIDAL Music AS or MQA Ltd. Use it at your own discretion and risk. Credentials are stored locally and encrypted in SQLite. NOORwave is intended for personal use only.