diff --git a/.gitignore b/.gitignore index b9e3fe4..2246233 100644 --- a/.gitignore +++ b/.gitignore @@ -35,5 +35,5 @@ report.[0-9]_.[0-9]_.[0-9]_.[0-9]_.json tmp -localstorage +localstorage.json downloaded \ No newline at end of file diff --git a/src/helpers/auth.ts b/src/helpers/auth.ts index f6e092d..15aafa8 100644 --- a/src/helpers/auth.ts +++ b/src/helpers/auth.ts @@ -1,4 +1,4 @@ -import "../localstorage"; +import "./localStorage"; import { init, initializeDeviceLogin, finalizeDeviceLogin, credentialsProvider } from "@tidal-music/auth"; diff --git a/src/helpers/localStorage.ts b/src/helpers/localStorage.ts new file mode 100644 index 0000000..a3ba487 --- /dev/null +++ b/src/helpers/localStorage.ts @@ -0,0 +1,29 @@ +const database = Bun.file('localStorage.json'); + +if (!await database.exists()) { + await Bun.write(database, JSON.stringify({})); +} + +let data = {}; + +data = await database.json() || {}; + +globalThis.localStorage = { + getItem: (key) => { + return data[key] || null; + }, + setItem: (key, value) => { + data[key] = value; + Bun.write(database, JSON.stringify(data)); + }, + removeItem: (key) => { + delete data[key]; + Bun.write(database, JSON.stringify(data)); + }, + clear: () => { + data = {}; + Bun.write(database, JSON.stringify(data)); + } +}; + +export { } \ No newline at end of file diff --git a/src/helpers/utils.ts b/src/helpers/utils.ts index 12f88ec..4fdc732 100644 --- a/src/helpers/utils.ts +++ b/src/helpers/utils.ts @@ -10,7 +10,7 @@ export default class { async fetchTrack(id: number) { const audio = await fetch(`https://api.tidal.com/v1/tracks/${id}/playbackinfopostpaywall/v4?audioquality=HI_RES_LOSSLESS&playbackmode=STREAM&assetpresentation=FULL`, { headers: this.authHeaders - }) + }) return await audio.json() as { trackId: number, audioPresentation: string, @@ -36,21 +36,21 @@ export default class { return await tracks.json(); } - async downloadFlac(manifestMimeType:string, manifest: string) { + async downloadFlac(manifestMimeType: string, manifest: string) { const id = Bun.nanoseconds().toString(36); if (manifestMimeType === "application/dash+xml") { await Bun.write(`tmp/${id}.mpd`, Buffer.from(manifest, "base64").toString("utf-8")) await Bun.$`mpv --ao=null --stream-record=tmp/${id}.flac --speed=100 tmp/${id}.mpd`.quiet() - + await Bun.file(`tmp/${id}.mpd`).delete(); - + const flac = Bun.file(`tmp/${id}.flac`) - + const audioBuffer = await flac.arrayBuffer(); - + await flac.delete() - + return audioBuffer; } else if (manifestMimeType === "application/vnd.tidal.bts") { const data = JSON.parse(Buffer.from(manifest, "base64").toString("utf-8")) as { @@ -61,7 +61,7 @@ export default class { } const flac = await fetch(data.urls[0]) - + return await flac.arrayBuffer(); } @@ -72,7 +72,7 @@ export default class { const trackReq = await fetch(`https://api.tidal.com/v1/tracks/${id}/?countryCode=US`, { headers: this.authHeaders }) - + const track = await trackReq.json() as { title: string, replayGain: number, @@ -95,11 +95,11 @@ export default class { cover: string, }, }; - + const alubmReq = await fetch(`https://api.tidal.com/v1/albums/${track.album.id}/?countryCode=US`, { headers: this.authHeaders }) - + const album = await alubmReq.json() as { title: string, numberOfTracks: number, @@ -112,25 +112,27 @@ export default class { } ], } - + + console.log(track) + return FlacStreamTagger.fromBuffer(Buffer.from(audioBuffer), { tagMap: { - title: track.title, - trackNumber: track.trackNumber.toString(), - discNumber: track.volumeNumber.toString(), - bpm: track.bpm.toString(), - date: track.streamStartDate, - copyright: track.copyright, - REPLAYGAIN_TRACK_GAIN: track.replayGain.toString(), - REPLAYGAIN_TRACK_PEAK: track.peak.toString(), - comment: track.url, - isrc: track.isrc, - upc: album.upc, - artist: track.artists.map((a) => a.name), - album: album.title, - albumArtist: album.artists.map((a) => a.name), - totalTracks: album.numberOfTracks.toString(), - year: album.releaseDate.split("-")[0] || "", + title: track.title, + trackNumber: track.trackNumber.toString(), + discNumber: track.volumeNumber.toString(), + bpm: (track.bpm || 0).toString(), + date: track.streamStartDate, + copyright: track.copyright, + REPLAYGAIN_TRACK_GAIN: track.replayGain.toString(), + REPLAYGAIN_TRACK_PEAK: track.peak.toString(), + comment: track.url, + isrc: track.isrc, + upc: album.upc, + artist: track.artists.map((a) => a.name), + album: album.title, + albumArtist: album.artists.map((a) => a.name), + totalTracks: album.numberOfTracks.toString(), + year: album.releaseDate.split("-")[0] || "", }, picture: { buffer: Buffer.from(await (await fetch(`https://resources.tidal.com/images/${album.cover.replaceAll("-", "/")}/1280x1280.jpg`)).arrayBuffer()),