Compare commits

..

2 Commits

Author SHA1 Message Date
mjokfox
bce768fde3 Merge 1b4c1e1cd8 into 6e43cbb4d7 2024-05-14 13:03:11 +02:00
mjokfox
1b4c1e1cd8 Add the cors module and use it with express api 2024-05-14 12:53:39 +02:00
10 changed files with 45 additions and 73 deletions

View File

@@ -4,10 +4,6 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## [5.12.0]
- Added Shuffle and Repeat state to API response - By [ThatGravyBoat](https://github.com/ThatGravyBoat)
## [5.11.0] ## [5.11.0]
- Re-implemented the API, added support for duration/current in seconds & shuffle+repeat - Re-implemented the API, added support for duration/current in seconds & shuffle+repeat

35
package-lock.json generated
View File

@@ -1,16 +1,17 @@
{ {
"name": "tidal-hifi", "name": "tidal-hifi",
"version": "5.12.0", "version": "5.11.0",
"lockfileVersion": 3, "lockfileVersion": 3,
"requires": true, "requires": true,
"packages": { "packages": {
"": { "": {
"name": "tidal-hifi", "name": "tidal-hifi",
"version": "5.12.0", "version": "5.11.0",
"license": "MIT", "license": "MIT",
"dependencies": { "dependencies": {
"@electron/remote": "^2.1.2", "@electron/remote": "^2.1.2",
"axios": "^1.6.8", "axios": "^1.6.8",
"cors": "^2.8.5",
"discord-rpc": "^4.0.1", "discord-rpc": "^4.0.1",
"electron-store": "^8.2.0", "electron-store": "^8.2.0",
"express": "^4.19.2", "express": "^4.19.2",
@@ -21,6 +22,7 @@
}, },
"devDependencies": { "devDependencies": {
"@mastermindzh/prettier-config": "^1.0.0", "@mastermindzh/prettier-config": "^1.0.0",
"@types/cors": "^2.8.17",
"@types/discord-rpc": "^4.0.8", "@types/discord-rpc": "^4.0.8",
"@types/express": "^4.17.21", "@types/express": "^4.17.21",
"@types/node": "^20.10.6", "@types/node": "^20.10.6",
@@ -1030,6 +1032,15 @@
"@types/node": "*" "@types/node": "*"
} }
}, },
"node_modules/@types/cors": {
"version": "2.8.17",
"resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.17.tgz",
"integrity": "sha512-8CGDvrBj1zgo2qE+oS3pOCyYNqCPryMWY2bGfwA0dcfopWGgxs+78df0Rs3rc9THP4JkOhLsAa+15VdpAqkcUA==",
"dev": true,
"dependencies": {
"@types/node": "*"
}
},
"node_modules/@types/debug": { "node_modules/@types/debug": {
"version": "4.1.12", "version": "4.1.12",
"resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz", "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz",
@@ -2679,6 +2690,18 @@
"integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==",
"dev": true "dev": true
}, },
"node_modules/cors": {
"version": "2.8.5",
"resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz",
"integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==",
"dependencies": {
"object-assign": "^4",
"vary": "^1"
},
"engines": {
"node": ">= 0.10"
}
},
"node_modules/cosmiconfig": { "node_modules/cosmiconfig": {
"version": "9.0.0", "version": "9.0.0",
"resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-9.0.0.tgz", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-9.0.0.tgz",
@@ -5983,6 +6006,14 @@
"node": "*" "node": "*"
} }
}, },
"node_modules/object-assign": {
"version": "4.1.1",
"resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz",
"integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==",
"engines": {
"node": ">=0.10.0"
}
},
"node_modules/object-inspect": { "node_modules/object-inspect": {
"version": "1.13.1", "version": "1.13.1",
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz",

View File

@@ -1,6 +1,6 @@
{ {
"name": "tidal-hifi", "name": "tidal-hifi",
"version": "5.12.0", "version": "5.11.0",
"description": "Tidal on Electron with widevine(hifi) support", "description": "Tidal on Electron with widevine(hifi) support",
"main": "ts-dist/main.js", "main": "ts-dist/main.js",
"scripts": { "scripts": {
@@ -41,6 +41,7 @@
"dependencies": { "dependencies": {
"@electron/remote": "^2.1.2", "@electron/remote": "^2.1.2",
"axios": "^1.6.8", "axios": "^1.6.8",
"cors": "^2.8.5",
"discord-rpc": "^4.0.1", "discord-rpc": "^4.0.1",
"electron-store": "^8.2.0", "electron-store": "^8.2.0",
"express": "^4.19.2", "express": "^4.19.2",
@@ -51,6 +52,7 @@
}, },
"devDependencies": { "devDependencies": {
"@mastermindzh/prettier-config": "^1.0.0", "@mastermindzh/prettier-config": "^1.0.0",
"@types/cors": "^2.8.17",
"@types/discord-rpc": "^4.0.8", "@types/discord-rpc": "^4.0.8",
"@types/express": "^4.17.21", "@types/express": "^4.17.21",
"@types/node": "^20.10.6", "@types/node": "^20.10.6",

View File

@@ -5,12 +5,14 @@ import { settingsStore } from "../../scripts/settings";
import { addCurrentInfo } from "./features/current"; import { addCurrentInfo } from "./features/current";
import { addPlaybackControl } from "./features/player"; import { addPlaybackControl } from "./features/player";
import { addLegacyApi } from "./legacy"; import { addLegacyApi } from "./legacy";
import cors from "cors";
/** /**
* Function to enable TIDAL Hi-Fi's express api * Function to enable TIDAL Hi-Fi's express api
*/ */
export const startApi = (mainWindow: BrowserWindow) => { export const startApi = (mainWindow: BrowserWindow) => {
const expressApp = express(); const expressApp = express();
expressApp.use(cors());
expressApp.get("/", (req, res) => res.send("Hello World!")); expressApp.get("/", (req, res) => res.send("Hello World!"));
// add features // add features

View File

@@ -1,5 +1,4 @@
import { MediaStatus } from "./mediaStatus"; import { MediaStatus } from "./mediaStatus";
import { MediaPlayerInfo } from "./mediaPlayerInfo";
export interface MediaInfo { export interface MediaInfo {
title: string; title: string;
@@ -14,5 +13,4 @@ export interface MediaInfo {
durationInSeconds?: number; durationInSeconds?: number;
image: string; image: string;
favorite: boolean; favorite: boolean;
player: MediaPlayerInfo;
} }

View File

@@ -1,8 +0,0 @@
import { RepeatState } from "./repeatState";
import { MediaStatus } from "./mediaStatus";
export interface MediaPlayerInfo {
status: MediaStatus;
shuffle: boolean;
repeat: RepeatState;
}

View File

@@ -1,5 +0,0 @@
export enum RepeatState {
off = "off",
all = "all",
single = "single",
}

View File

@@ -433,7 +433,7 @@
<h4>TIDAL Hi-Fi</h4> <h4>TIDAL Hi-Fi</h4>
<div class="about-section__version"> <div class="about-section__version">
<a target="_blank" rel="noopener" <a target="_blank" rel="noopener"
href="https://github.com/Mastermindzh/tidal-hifi/releases/tag/5.12.0">5.12.0</a> href="https://github.com/Mastermindzh/tidal-hifi/releases/tag/5.11.0">5.11.0</a>
</div> </div>
<div class="about-section__links"> <div class="about-section__links">
<a target="_blank" rel="noopener" href="https://github.com/mastermindzh/tidal-hifi/" <a target="_blank" rel="noopener" href="https://github.com/mastermindzh/tidal-hifi/"

View File

@@ -19,7 +19,6 @@ import { downloadFile } from "./scripts/download";
import { addHotkey } from "./scripts/hotkeys"; import { addHotkey } from "./scripts/hotkeys";
import { settingsStore } from "./scripts/settings"; import { settingsStore } from "./scripts/settings";
import { setTitle } from "./scripts/window-functions"; import { setTitle } from "./scripts/window-functions";
import { RepeatState } from "./models/repeatState";
const notificationPath = `${app.getPath("userData")}/notification.jpg`; const notificationPath = `${app.getPath("userData")}/notification.jpg`;
const appName = "TIDAL Hi-Fi"; const appName = "TIDAL Hi-Fi";
@@ -30,8 +29,6 @@ let currentListenBrainzDelayId: ReturnType<typeof setTimeout>;
let scrobbleWaitingForDelay = false; let scrobbleWaitingForDelay = false;
let currentlyPlaying = MediaStatus.paused; let currentlyPlaying = MediaStatus.paused;
let currentRepeatState: RepeatState = RepeatState.off;
let currentShuffleState = false;
let currentMediaInfo: Options; let currentMediaInfo: Options;
let currentNotification: Electron.Notification; let currentNotification: Electron.Notification;
@@ -351,23 +348,6 @@ function getCurrentlyPlayingStatus() {
return status; return status;
} }
function getCurrentShuffleState() {
const shuffle = elements.get("shuffle");
return shuffle?.getAttribute("aria-checked") === "true";
}
function getCurrentRepeatState() {
const repeat = elements.get("repeat");
switch (repeat?.getAttribute("data-type")) {
case "button__repeatAll":
return RepeatState.all;
case "button__repeatSingle":
return RepeatState.single;
default:
return RepeatState.off;
}
}
/** /**
* Convert the duration from MM:SS to seconds * Convert the duration from MM:SS to seconds
* @param {*} duration * @param {*} duration
@@ -531,21 +511,14 @@ setInterval(function () {
const titleOrArtistsChanged = currentSong !== songDashArtistTitle; const titleOrArtistsChanged = currentSong !== songDashArtistTitle;
const current = elements.getText("current"); const current = elements.getText("current");
const currentStatus = getCurrentlyPlayingStatus(); const currentStatus = getCurrentlyPlayingStatus();
const shuffleState = getCurrentShuffleState();
const repeatState = getCurrentRepeatState();
const playStateChanged = currentStatus != currentlyPlaying; const playStateChanged = currentStatus != currentlyPlaying;
const shuffleStateChanged = shuffleState != currentShuffleState;
const repeatStateChanged = repeatState != currentRepeatState;
const hasStateChanged = playStateChanged || shuffleStateChanged || repeatStateChanged;
// update info if song changed or was just paused/resumed // update info if song changed or was just paused/resumed
if (titleOrArtistsChanged || hasStateChanged) { if (titleOrArtistsChanged || playStateChanged) {
if (playStateChanged) currentlyPlaying = currentStatus; if (playStateChanged) {
if (shuffleStateChanged) currentShuffleState = shuffleState; currentlyPlaying = currentStatus;
if (repeatStateChanged) currentRepeatState = repeatState; }
skipArtistsIfFoundInSkippedArtistsList(artistsArray); skipArtistsIfFoundInSkippedArtistsList(artistsArray);
const album = elements.getAlbumName(); const album = elements.getAlbumName();
@@ -564,12 +537,6 @@ setInterval(function () {
image: "", image: "",
icon: "", icon: "",
favorite: elements.isFavorite(), favorite: elements.isFavorite(),
player: {
status: currentStatus,
shuffle: shuffleState,
repeat: repeatState,
},
}; };
// update title, url and play info with new info // update title, url and play info with new info

View File

@@ -1,6 +1,5 @@
import { MediaInfo } from "../models/mediaInfo"; import { MediaInfo } from "../models/mediaInfo";
import { MediaStatus } from "../models/mediaStatus"; import { MediaStatus } from "../models/mediaStatus";
import { RepeatState } from "../models/repeatState";
export const mediaInfo = { export const mediaInfo = {
title: "", title: "",
@@ -15,12 +14,6 @@ export const mediaInfo = {
durationInSeconds: 0, durationInSeconds: 0,
image: "tidal-hifi-icon", image: "tidal-hifi-icon",
favorite: false, favorite: false,
player: {
status: MediaStatus.paused as string,
shuffle: false,
repeat: RepeatState.off as string,
}
}; };
export const updateMediaInfo = (arg: MediaInfo) => { export const updateMediaInfo = (arg: MediaInfo) => {
@@ -36,10 +29,6 @@ export const updateMediaInfo = (arg: MediaInfo) => {
mediaInfo.durationInSeconds = arg.durationInSeconds ?? 0; mediaInfo.durationInSeconds = arg.durationInSeconds ?? 0;
mediaInfo.image = propOrDefault(arg.image); mediaInfo.image = propOrDefault(arg.image);
mediaInfo.favorite = arg.favorite; mediaInfo.favorite = arg.favorite;
mediaInfo.player.status = propOrDefault(arg.player?.status);
mediaInfo.player.shuffle = arg.player.shuffle;
mediaInfo.player.repeat = propOrDefault(arg.player?.repeat);
}; };
/** /**