gerdur 0.0.0-probe → 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. package/CHANGELOG.md +10 -0
  2. package/LICENSE +0 -0
  3. package/README.md +231 -1
  4. package/dist/package.json +90 -0
  5. package/dist/src/gerdur.d.ts +2 -0
  6. package/dist/src/gerdur.js +345 -0
  7. package/dist/src/hoenir.d.ts +2 -0
  8. package/dist/src/hoenir.js +345 -0
  9. package/dist/src/index.d.ts +62 -0
  10. package/dist/src/index.js +101 -0
  11. package/dist/src/kyrie.d.ts +2 -0
  12. package/dist/src/kyrie.js +345 -0
  13. package/dist/src/lib/api-download.d.ts +54 -0
  14. package/dist/src/lib/api-download.js +89 -0
  15. package/dist/src/lib/arl-setup.d.ts +82 -0
  16. package/dist/src/lib/arl-setup.js +274 -0
  17. package/dist/src/lib/auto-updater.d.ts +2 -0
  18. package/dist/src/lib/auto-updater.js +70 -0
  19. package/dist/src/lib/config.d.ts +53 -0
  20. package/dist/src/lib/config.js +164 -0
  21. package/dist/src/lib/decrypt-pool.d.ts +2 -0
  22. package/dist/src/lib/decrypt-pool.js +122 -0
  23. package/dist/src/lib/decrypt-worker.d.ts +1 -0
  24. package/dist/src/lib/decrypt-worker.js +17 -0
  25. package/dist/src/lib/decrypt.d.ts +3 -0
  26. package/dist/src/lib/decrypt.js +114 -0
  27. package/dist/src/lib/download-track.d.ts +24 -0
  28. package/dist/src/lib/download-track.js +163 -0
  29. package/dist/src/lib/email-login.d.ts +16 -0
  30. package/dist/src/lib/email-login.js +111 -0
  31. package/dist/src/lib/session.d.ts +84 -0
  32. package/dist/src/lib/session.js +118 -0
  33. package/dist/src/lib/signale.d.ts +15 -0
  34. package/dist/src/lib/signale.js +20 -0
  35. package/dist/src/lib/update-check.d.ts +2 -0
  36. package/dist/src/lib/update-check.js +30 -0
  37. package/dist/src/lib/util.d.ts +17 -0
  38. package/dist/src/lib/util.js +94 -0
  39. package/dist/src/q-fi.d.ts +2 -0
  40. package/dist/src/q-fi.js +345 -0
  41. package/package.json +88 -5
  42. package/setup-termux.js +41 -0
package/CHANGELOG.md ADDED
@@ -0,0 +1,10 @@
1
+ # Changelog
2
+
3
+ ## 1.0.0 - 2026-08-30
4
+
5
+ Initial public release.
6
+
7
+ - CLI for downloading tracks, albums, artists and playlists from Deezer, with Spotify and Tidal links resolved via ISRC / UPC matching.
8
+ - Quality selection: MP3 128, MP3 320, FLAC. Automatic MP3 / FLAC tagging with cover art and lyrics.
9
+ - Side-effect-free programmatic API (`createSession`, `getTrackBuffer`, `downloadTrackToFile`, re-exported `gerdur-core` query functions).
10
+ - `gerdur.config.json` (project-local or `~/.config/gerdur/`), `GERDUR_ARL` / `GERDUR_EMAIL` / `GERDUR_PASSWORD` env vars, guided first-run arl setup.
package/LICENSE ADDED
File without changes
package/README.md CHANGED
@@ -1,3 +1,233 @@
1
1
  # gerdur
2
2
 
3
- Name probe. Real release to follow.
3
+ <img src="https://raw.githubusercontent.com/soulwax/gerdur/main/.github/assets/logo.png" alt="gerdur logo" width="200" height="200" style="display: block; margin-left: auto; margin-right: auto;" />
4
+
5
+ > A component of the darkfloor streaming stack.
6
+ > Source: <https://github.com/soulwax/gerdur>
7
+
8
+ ![Screenshot](https://raw.githubusercontent.com/soulwax/gerdur/main/.github/assets/screenshot.png)
9
+
10
+ **gerdur is a program for downloading music from streaming music services. Remember that the artists and studios put a lot of work into making music — purchase the original music to support them.**
11
+
12
+ ## Why *gerdur*?
13
+
14
+ **Gerðr** is a jötunn — in the old poems, *the fairest of all beings*, the glow of her arms lighting sea and sky. Freyr sees her from Odin's watchtower, falls ill with longing, and sends his servant Skírnir riding through a wall of fire to win her back. Her name is *garðr*: the enclosure, the walled yard, the tended garden — the same root as English *garden* and *garth*, and the *-grad* of Slavic city-names.
15
+
16
+ A track behind a service is Gerðr — walled off, worth the crossing. **gerdur** is what rides through the fire and brings it home into your own *garðr*: decrypted, tagged, and yours to keep.
17
+
18
+ ## Features
19
+
20
+ - *Supports downloading tracks, albums, artists, and playlists*
21
+ - *Allows music quality selection (**128 kbps**, **320 kbps** and **FLAC**)*
22
+ - *Auto tagging **MP3** & **FLAC** (including album cover and lyrics)*
23
+ - *Support downloading from both links and via searching*
24
+
25
+ ## Supported Sites
26
+
27
+ ### *Deezer*, *Spotify* and *Tidal*
28
+
29
+ - *Tracks*
30
+ - *Albums*
31
+ - *Audiobook*
32
+ - *Playlists*
33
+ - *Artists*
34
+
35
+ > Note that Spotify and Tidal tracks will be sourced from Deezer using ISRC matching and UPC for albums. Also Spotify artist tracks are limited upto 10 items.
36
+
37
+ ## Install
38
+
39
+ ### *Method 1*
40
+
41
+ First install `nodejs` following [this tutorial](https://nodejs.org/en/download/package-manager/)
42
+
43
+ Once `nodejs` installation is complete run this command.
44
+
45
+ npm i -g gerdur # may require sudo on linux and macOS
46
+
47
+ or if you are using yarn
48
+
49
+ yarn global add gerdur
50
+
51
+ or pnpm
52
+
53
+ pnpm add -g gerdur
54
+
55
+ Now you can run using command `gerdur` to start.
56
+
57
+ ### First run — getting your `arl`
58
+
59
+ `gerdur` logs in to Deezer using an `arl` cookie. On the **first interactive run** (just
60
+ running `gerdur` with no `--headless`/scripting flags), if you have not configured an `arl`
61
+ yet, `gerdur` walks you through it: it prints where to find the cookie and prompts you to
62
+ paste it, then saves it for you. It will also offer to re-enter the `arl` if login fails
63
+ because the cookie has expired.
64
+
65
+ To get your `arl` manually:
66
+
67
+ 1. Open [https://www.deezer.com](https://www.deezer.com) in your browser and log in.
68
+ 2. Open DevTools (`F12`) → **Application** → **Cookies** → `deezer.com`.
69
+ 3. Copy the value of the `arl` cookie (a long hex string).
70
+
71
+ You can set or update it any time without the prompt:
72
+
73
+ gerdur --set-arl <your_arl>
74
+
75
+ Or run the guided setup at any time:
76
+
77
+ gerdur setup # same as: gerdur --setup
78
+
79
+ #### Log in with email & password
80
+
81
+ `gerdur` can fetch your `arl` automatically from your Deezer email and password, so you
82
+ never have to open DevTools. The guided setup offers it as the first option:
83
+
84
+ gerdur setup
85
+
86
+ Only the fetched `arl` is stored; your password is never written to disk unless you
87
+ explicitly opt in when prompted. For headless use, supply `GERDUR_EMAIL` and
88
+ `GERDUR_PASSWORD` env vars and `gerdur` will log in automatically when no `arl` is set:
89
+
90
+ GERDUR_EMAIL=you@example.com GERDUR_PASSWORD=secret gerdur -q 320 -u <url>
91
+
92
+ > Login uses Deezer's mobile OAuth flow. If it ever fails (bad credentials or a change
93
+ > on Deezer's side), `gerdur` falls back to asking you to paste an `arl`.
94
+
95
+ ### Zero-config usage (env var & global config)
96
+
97
+ `gerdur` works from **any directory** without a per-folder config file:
98
+
99
+ - Set the `GERDUR_ARL` environment variable and `gerdur` will use it (it takes precedence over
100
+ the config file, and is never written to disk). Handy for CI, containers, and one-offs:
101
+
102
+ GERDUR_ARL=<your_arl> gerdur -q 320 -u <url>
103
+
104
+ - When you save an `arl` (via `setup` or `--set-arl`) and there is no `gerdur.config.json` in
105
+ the current directory, `gerdur` stores it in a **global** location
106
+ (`$XDG_CONFIG_HOME/gerdur/gerdur.config.json`, or `~/.config/gerdur/gerdur.config.json`) so it is
107
+ reused everywhere. A `gerdur.config.json` in the current directory still takes precedence.
108
+
109
+ > Scripted, headless (`-d`), and non-interactive (piped) runs never prompt — they behave
110
+ > exactly as before and simply use the configured `arl` (or `GERDUR_ARL`).
111
+
112
+ ### *Method 2*
113
+
114
+ Download pre-built binary from [here](https://github.com/soulwax/gerdur/releases) and then double click on Windows to run. For Linux and macOS user, first open your choice of terminal and the execute with `./gerdur`
115
+
116
+ ## CLI Parameters
117
+
118
+ All options are optional. You can suppress prompts via providing `quality` and `url` if you are using scripts. You can also use config file. Read the docs [here](https://github.com/soulwax/gerdur/blob/main/docs/config.md) for more info.
119
+
120
+ | Parameter | Short | Supported values | Description |
121
+ | :-------------------- | :-------------: | :---------------------------------------------------------------------------------------------------------------------: | :-------------------------------------------------------------------------------------------------------------------------------------------: |
122
+ | `--quality` | `-q` | 128/320/flac | The quality of the files to download |
123
+ | `--output` | `-o` | Output file format according to `saveLayout`. See more [here](https://github.com/soulwax/gerdur/blob/main/docs/config.md) | The path to download the files to |
124
+ | `--url` | `-u or nothing` | album/artist/playlist/track url | Downloads from url |
125
+ | `--input-file` | `-i` | Downloads all urls listed in text file. Example: `gerdur -i links.txt` | Downloads from url |
126
+ | `--concurrency` | `-c` 1 to 50 | Downloads X songs at a time | |
127
+ | `--set-arl` | `-a` | `arl` string | Set arl cookies |
128
+ | `--setup` | `-s` | *Nothing* | Run guided setup to enter your `arl` cookie. Also available as `gerdur setup`. |
129
+ | `--overwrite` | `-w` | *Nothing* | Re-download and overwrite existing files (default is to skip them). |
130
+ | `--experimental-login`| *None* | *Nothing* | Enable experimental email/password login to fetch an `arl` (often blocked by Deezer; falls back to arl paste). |
131
+ | `--headless` | `-d` | *Nothing* | Run in headless mode. You must provide both `--url` and `--quality` if you run in headless mode. This mode is meant for scripting automation. |
132
+ | `--resolve-full-path` | `-rfp` | *Nothing* | Create playlist file with absolute path location |
133
+ | `--create-playlist` | `-cp` | *Nothing* | Create playlist for albums and artists |
134
+ | `--config-file` | `-conf` | Config location. Example: `gerdur -conf my-gerdur.config.json` | Specify custom location to config file |
135
+ | `--update` | `-U` | *Nothing* | Download new update (binary only) |
136
+ | `--help` | `-h` | *Nothing* | Shows the CLI help |
137
+
138
+ ## Search Parameters
139
+
140
+ | Prefix | Description |
141
+ | :---------: | :-------------: |
142
+ | `artist:` | Search artist |
143
+ | `album:` | Search album |
144
+ | `playlist:` | Search playlist |
145
+
146
+ ## Programmatic API
147
+
148
+ When installed as a dependency, `gerdur` exposes a side-effect-free API
149
+ (importing it does **not** print the banner or parse CLI args, and nothing logs to the
150
+ console — progress is delivered via callbacks). CommonJS and ESM both work.
151
+
152
+ > **Full reference:** [docs/api.md](https://github.com/soulwax/gerdur/blob/main/docs/api.md) ·
153
+ > **Runnable examples:** [examples/](https://github.com/soulwax/gerdur/tree/main/examples)
154
+
155
+ ### High-level: sessions
156
+
157
+ The quickest path from credentials to files. `createSession` logs in (with an `arl` or
158
+ email/password), verifies the session, and returns helpers for querying and downloading:
159
+
160
+ ```ts
161
+ import {createSession} from 'gerdur';
162
+
163
+ const session = await createSession({email: 'you@example.com', password: 'secret'});
164
+ // ...or: createSession({arl: '...'})
165
+
166
+ // Resolve any Deezer / Spotify / Tidal URL and download it:
167
+ await session.downloadUrl('https://deezer.com/album/302127', 'flac', {
168
+ output: 'Music/{ALB_TITLE}/{SNG_TITLE}',
169
+ concurrency: 4,
170
+ onProgress: ({index, total, track, result}) =>
171
+ console.log(`${index + 1}/${total} ${track.SNG_TITLE} -> ${result?.path ?? 'unavailable'}`),
172
+ });
173
+
174
+ // Or work with the pieces:
175
+ const {tracks} = await session.parseUrl('https://deezer.com/track/3135556');
176
+ const found = await session.search('daft punk', ['TRACK'], 10);
177
+ const results = await session.downloadTracks(tracks, '320', {output: '{ART_NAME} - {SNG_TITLE}'});
178
+ ```
179
+
180
+ Session methods: `parseUrl`, `search`, `getUser`, `getTrackBuffer`, `downloadTrack`,
181
+ `downloadTracks`, `downloadUrl`. Every download call is silent; `downloadTracks` /
182
+ `downloadUrl` accept `concurrency` and an `onProgress` callback and return one
183
+ `{path, written} | null` per track.
184
+
185
+ ### Low-level: primitives
186
+
187
+ ```ts
188
+ import {getArl, initDeezerApi, getTrackInfo, getTrackBuffer, downloadTrackToFile} from 'gerdur';
189
+
190
+ const arl = await getArl('you@example.com', 'secret'); // throws LoginError on failure
191
+ await initDeezerApi(arl);
192
+
193
+ const track = await getTrackInfo('3135556');
194
+
195
+ // Get the tagged audio as a Buffer without touching the disk:
196
+ const mp3 = await getTrackBuffer(track, '320');
197
+
198
+ // ...or write it straight to a file:
199
+ const {path, written} = (await downloadTrackToFile(track, 'flac', {output: '{ART_NAME} - {SNG_TITLE}'}))!;
200
+ ```
201
+
202
+ ### Re-exported query functions
203
+
204
+ So you don't need `gerdur-core` as a second dependency (call after `initDeezerApi`
205
+ or `createSession`):
206
+
207
+ `parseInfo`, `searchMusic`, `getUser`, `getTrackInfo`, `getAlbumInfo`, `getAlbumTracks`,
208
+ `getPlaylistInfo`, `getPlaylistTracks`, `getArtistInfo`, `getDiscography`, `getLyrics`,
209
+ `getTrackDownloadUrl`, `GeoBlocked`.
210
+
211
+ ### Auth & config helpers
212
+
213
+ ```ts
214
+ import {loginWithEmail, LoginError, Config, globalConfigPath} from 'gerdur';
215
+
216
+ const result = await loginWithEmail('you@example.com', 'password');
217
+ if (result.ok) console.log(result.arl);
218
+ else console.error(result.reason, result.message); // 'wrong-credentials' | 'no-arl' | 'network' | 'unknown'
219
+
220
+ const conf = new Config(); // same config file the CLI uses
221
+ conf.set('cookies.arl', result.ok ? result.arl : '');
222
+ ```
223
+
224
+ Passwords passed to these functions are used only to authenticate and are never written
225
+ to disk or logged; only the resulting `arl` is returned or stored.
226
+
227
+ ### Disclaimer
228
+
229
+ > I am not responsible in any way for the usage of others.
230
+
231
+ ---
232
+
233
+ > Made with :heart: by the Bluesix Team. If you want to contribute, please read the [contributing guidelines](.github/CONTRIBUTING.md) first.
@@ -0,0 +1,90 @@
1
+ {
2
+ "name": "gerdur",
3
+ "version": "1.0.0",
4
+ "description": "The crucial streaming module for dabox systems.",
5
+ "author": "Christian",
6
+ "license": "SEE LICENSE IN LICENSE",
7
+ "scripts": {
8
+ "lint": "eslint .",
9
+ "prepublishOnly": "eslint . && tsc",
10
+ "prebuild": "eslint .",
11
+ "build": "tsc",
12
+ "postinstall": "node setup-termux.js",
13
+ "dev": "ts-node src/gerdur.ts",
14
+ "test": "node scripts/run-ava.cjs"
15
+ },
16
+ "bin": {
17
+ "gerdur": "dist/src/gerdur.js"
18
+ },
19
+ "main": "dist/src/index.js",
20
+ "types": "dist/src/index.d.ts",
21
+ "exports": {
22
+ ".": {
23
+ "types": "./dist/src/index.d.ts",
24
+ "default": "./dist/src/index.js"
25
+ },
26
+ "./package.json": "./package.json"
27
+ },
28
+ "files": [
29
+ "dist/**/*",
30
+ "setup-termux.js",
31
+ "CHANGELOG.md"
32
+ ],
33
+ "repository": {
34
+ "type": "git",
35
+ "url": "git+https://github.com/soulwax/gerdur.git"
36
+ },
37
+ "homepage": "https://github.com/soulwax/gerdur#readme",
38
+ "bugs": {
39
+ "url": "https://github.com/soulwax/gerdur/issues"
40
+ },
41
+ "publishConfig": {
42
+ "access": "public"
43
+ },
44
+ "engines": {
45
+ "node": ">=12"
46
+ },
47
+ "dependencies": {
48
+ "adm-zip": "^0.5.16",
49
+ "chalk": "^4.1.2",
50
+ "commander": "^9.5.0",
51
+ "gerdur-core": "^1.0.0",
52
+ "dot-prop": "^6.0.1",
53
+ "egoroof-blowfish": "^4.0.2",
54
+ "got": "^11.8.6",
55
+ "gradient-string": "^2.0.2",
56
+ "log-update": "^4.0.0",
57
+ "p-queue": "^6.6.2",
58
+ "prompts": "^2.4.2",
59
+ "true-case-path": "^2.2.1",
60
+ "update-check": "^1.5.4"
61
+ },
62
+ "devDependencies": {
63
+ "@types/adm-zip": "^0.4.34",
64
+ "@types/gradient-string": "^1.1.6",
65
+ "@types/node": "^17.0.45",
66
+ "@types/prompts": "^2.4.9",
67
+ "@typescript-eslint/eslint-plugin": "^5.62.0",
68
+ "@typescript-eslint/parser": "^5.62.0",
69
+ "ava": "^4.3.3",
70
+ "eslint": "^8.57.1",
71
+ "eslint-plugin-prettier": "^4.2.5",
72
+ "prettier": "^2.8.8",
73
+ "ts-node": "^10.9.2",
74
+ "typescript": "^4.9.5"
75
+ },
76
+ "ava": {
77
+ "extensions": [
78
+ "ts"
79
+ ],
80
+ "files": [
81
+ "!dist"
82
+ ],
83
+ "require": [
84
+ "ts-node/register"
85
+ ],
86
+ "timeout": "5m",
87
+ "serial": true,
88
+ "verbose": true
89
+ }
90
+ }
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env node
2
+ export {};