Remix.run Logo
mediaconsumer 4 hours ago

alldebrid. their 4.0/4.1 api has all the stuff to decode magnets and browse their files. filter mkv,mp4,etc. i made a little database of imdb tt values to assist autosuggest for searching and a nsfw filter for the few friends and family using the app.

have thought about extending it to realdebrid/torbox/etc but it's just been kinda set and forget. every once in a while will add a feature... most recently i think was seeing if there was a matching srt file and feeding that along with the video file to vlc so you get subtitle support if it's not baked into the video file

mediaconsumer 3 hours ago | parent [-]

disclaimer: had opus summarize the key api endpoints and flows so anyone could whip their own up:

  ## External APIs & Endpoints
  
  ### Apibay (Search)
  - \*URL\*: `https://apibay.org/q.php?q={query}&cat=0`
  - \*Auth\*: None
  - \*Returns\*: JSON array of `{ info_hash, name, seeders, leechers, size, imdb, category }`
  
  ### AllDebrid v4 
  - \*Base\*: `https://api.alldebrid.com/v4`
  - \*Auth\*: API key as `apikey` query parameter, `agent` param required
  - \*Endpoints\*:
    - `GET /magnet/upload?magnets[]={magnet}&agent=YOURAPP&apikey={key}` — Upload magnet
    - `GET /magnet/status?id={id}&agent=YOURAPP&apikey={key}` — Poll magnet status
    - `GET /link/unlock?link={link}&agent=YOURAPP&apikey={key}` — Unlock hoster link to direct URL
  
  ### AllDebrid v4.1
  - \*Base\*: `https://api.alldebrid.com/v4.1`
  - \*Auth\*: `Authorization: Bearer {apikey}` header
  - \*Endpoints\*:
    - `POST /magnet/status` — Body: `id={magnetId}` or `status=active|ready`
    - `POST /magnet/files` — Body: `id[]={id1}&id[]={id2}...` — Get file list with download links
  
  ### VLC Media Player (Local Binary)
  - macOS: `/Applications/VLC.app/Contents/MacOS/VLC`
  - Windows: `C:\Program Files\VideoLAN\VLC\vlc.exe`
  - Linux: `vlc` (from PATH)
  - Args: `--fullscreen --no-video-title-show {url}` (optional: `--input-slave={subtitleUrl}`)
  
  ### Magnet Unlock Flow
  1. User clicks a result → `handleSelectResult(result)`
  2. \*Fast path\*: `getMagnetIdByHash(hash)` checks cache → if found, `getStatusV41({id})` + `getMagnetFiles([id])`
  3. \*Upload path\*: If not cached, `allDebrid.uploadMagnet(magnet)` → cache ID via `setMagnetId(hash, id)`
  4. If magnet not ready (still caching on AllDebrid), status modal shows progress
  5. `flattenMagnetFilesResponse()` converts nested file tree to flat `[{ filename, link }]`
  6. Fallback: Legacy `getStatus(id)` → `getFiles(link)` for each download link
  7. `unlockLinksToFiles(links)` — batch unlock, filter to video files only
  
  ### Playback Flow
  1. User clicks Play on a file → `handlePlay(url, filename, subtitleUrl?)`
  2. `window.api.play(url, subtitleUrl)` → main process resolves AllDebrid link → spawns VLC
  3. `library.recordPlay(hash, title, filename, streamUrl)` → updates or creates history entry, increments per-file `playCount`