Migrate to typescript & tauri - #1
Conversation
Introduce Tauri Rust side scaffolding for the Cupid Player app. Adds Cargo.toml and build.rs, tauri.conf.json, a small lib/main pair that runs a Tauri builder (with debug logging plugin enabled in debug builds), and a default capabilities file. Includes .gitignore and a full set of app icons (desktop, Android, iOS) and launcher resources. Bundling config maps frontend dist, resources (audio/assets), external binaries, deep link protocol (cupid), and platform bundle settings. Dependencies added: tauri, tauri-build, tauri plugins, serde, tokio, jsonwebtoken, and related crates.
Extend the Tauri backend with state, utilities and commands for streaming, Apple Music auth, window management and theming. Adds StreamCache, AppleMusicState and MaximizeState plus helpers (yt_dlp_path, EXE_SUFFIX, ASPECT) and a CACHE_TTL. Implements get_stream_url (yt-dlp invocation with 15s timeout and 25min in-memory cache), get_apple_music_token (ES256 JWT creation from .p8 key with caching), window_resize and window_maximize (aspect-preserving resizing/restore), and set_theme (load favicon as window icon). Registers tauri plugins (shell, deep_link), manages the new states and forwards deep-link URLs to the frontend.
Replace Electron-based build/dev setup with Tauri: update package.json scripts and dependencies to use cargo tauri and @tauri-apps/cli/api, adjust vite config (publicDir, host). Integrate Tauri APIs in the frontend (invoke, listen, getCurrentWindow, plugin-shell open) and update Spotify/Apple auth flows and window controls to use Tauri commands. Add deep-link plugin and capability permissions in tauri.conf.json and forward cupid:// callbacks from Rust to the renderer. Add image crate and adjust Rust icon loading to decode images with the image crate, plus minor Tauri setup changes in src-tauri (Cargo.toml). Include yt-dlp binary and add public/audio/.gitkeep; update audio path usage in player hooks.
Replace Electron tooling and dependencies with Tauri equivalents. Updates include package.json/package-lock.json to remove Electron, electron-builder and other Electron-specific dev deps and add @tauri-apps/api, @tauri-apps/cli and @tauri-apps/plugin-shell; switch some browser-oriented packages (e.g. music-metadata -> music-metadata-browser). Also update src-tauri/Cargo.toml and src-tauri/tauri.conf.json to configure the Tauri runtime. This migrates the app from an Electron-based build to Tauri for a smaller, native wrapper and simplified dev tooling.
Add reqwest (0.12 with rustls-tls, json and stream features) and futures-util (0.3) to src-tauri/Cargo.toml to enable HTTP client and async utilities in the Tauri backend. Cargo.lock was updated to record the resolved transitive dependencies.
Rename React entry and components to .tsx/.ts, convert Spotify and Apple modules to TypeScript, and add strong typings. Added src/types.ts for shared types and updated imports across App, auth, api, player, hooks and playlist. Replaced JS Spotify player wrapper with a typed player.ts, migrated MusicKit helpers to auth.ts, and updated main.tsx. Small runtime/logic cleanups and type annotations (error handling, event payloads, DOM refs, timers) and removal of the old .js/.jsx files.
Rename vite.config.js to vite.config.ts to use a TypeScript Vite config. No functional changes aside from a minor whitespace edit; existing plugins and base config are preserved to enable typed config and improved editor/tooling support.
Introduce yt-dlp management: add YtDlpState to cache a resolved binary path and helpers to compute platform asset and binary names. Implement async fetch_latest_yt_dlp_version, download_yt_dlp (emits yt-dlp-progress), resolve_yt_dlp resolution logic (managed app data, sidecar, system), and update_yt_dlp_if_needed which writes a version file and emits yt-dlp-updated. Use resolve_yt_dlp from get_stream_url and add STREAM_CACHE_TTL constant. Kick off a non-blocking startup update/download task and register YtDlpState with the app. Also include minor refactors and cleanup: compact struct initializers, improve Apple Music key lookup error message, tighten JWT/claims formatting, and simplify window resize/maximize sizing/position logic and other small formatting tweaks.
Replace Electron-focused docs with Tauri migration notes and TypeScript/Rust details. Update local audio path to public/audio and clarify MP3 metadata handling and recommended tag editors. Add OS-specific prerequisites (Node 18+, Rust, MSVC/toolchain, Xcode CLI, Linux WebKit/GTK deps). Update Spotify setup (add localhost and custom cupid:// callbacks, .env example) and Apple Music setup (move .p8 to src-tauri, provide APPLE_TEAM_ID/APPLE_KEY_ID env vars, note private-key bundling). Document yt-dlp auto-download/update behavior and fallback to system PATH. Change packaging command to npm run build, update build output/installer paths and install instructions per platform, add scripts table, and refresh the tech stack to list Tauri 2, React 18, TypeScript, Rust, and other updated deps.
Add core:window:allow-close to default capabilities. In window_resize, convert dx/dy from logical (CSS) to physical pixels by multiplying by the window scale factor and rounding to fix resize behavior on HiDPI displays. In useAudioPlayer, add an error listener to stop playback on errors and update togglePlay to set isPlaying only after audio.play() resolves (and false on rejection) to avoid incorrect playing state.
Extract core backend responsibilities into three new modules: src-tauri/src/apple.rs (Apple Music JWT caching/generation), src-tauri/src/ytdlp.rs (yt-dlp resolution, download/update, and stream URL caching), and src-tauri/src/window.rs (window resizing/maximizing and theme icon handling). Update src-tauri/src/lib.rs to import these modules, wire their state constructors, and adjust the startup background task to use the ytdlp module's updater and cached path setter. This refactor improves modularity, isolates platform/update logic, and keeps the main run() glue code smaller and clearer.
|
hey, tried testing this out and ran into a few things: spotify redirect uri the pr switches to window dragging the window isn't draggable right now. in the electron version this is done with window sizing there's extra whitespace around the pixel art, the visible frame doesn't match the actual window bounds. the electron version uses local playback local mp3 playback also seem to be working, buttons are not working as expected |
cupidbity
left a comment
There was a problem hiding this comment.
tested this out, left some notes on specific lines
| "identifier": "com.cupidbity.cupid-player", | ||
| "build": { | ||
| "frontendDist": "../dist", | ||
| "devUrl": "http://localhost:5173", |
There was a problem hiding this comment.
this is fine for the dev server but the spotify callback in auth.ts also uses localhost which spotify blocks, just making sure the callback uri specifically uses 127.0.0.1
Add backgroundColor "#00000000" to src-tauri/tauri.conf.json window settings to ensure the window is fully transparent (addresses default opaque background on some platforms).
|
@Advik-B Will test in soon. and let you know |
… URI - next/prev now always start playback, matching useSpotifyPlayer behavior and standard music player UX (navigating tracks always resumes play) - Bind Vite dev server to 127.0.0.1 to match Spotify redirect URI (Spotify disallows localhost but accepts 127.0.0.1) - Update Tauri devUrl to 127.0.0.1:5173 for consistency Also verified with 5 real tracks downloaded via yt-dlp from SoundCloud: Lovers Rock, Come Inside Of My Heart, Pluto Projector, Lovesick, Apocalypse
Fix audio playback state and dev server configuration
|
Ran claude code to figure out the playback issue, please check |
|
tested again, couple things still happening:
|
|
Since I don't have MacOS, could you please supply a screenshot? |
|
@cupidbity I am genuinely clueless rn I do NOT have a mac🥲 |
|
is it working as expected on windows? i can try to fix mac if windows is where it needs to be |
|
Yepp, it is on windows.. I even ran it side by side with your original source code |
b03cc89 to
08dbece
Compare


Title.


For some context, I am coming from this comment(s):
Basically,
yt-dlpis auto downloaded/updated on app start-up. (Note: This may cause slow start-up on the FIRST launch, however, the subsequent launches will be significantly faster)14 MBbecause the bloat has been removed. [1]This PR is in a draft since I have NOT tested out the ACTUAL music playback myself. The time is 3:15 AM for me, and I've interrupted my doomscrolling for this sidequest, and I want to go to bed.
There are already some bugfix commits.
More will follow once I wake up and have my coffee.
[1]: The windows executable. I've yet to test it for MacOS. If we bundle
yt-dlp(which I do not recommend), then its23MB