add global music folder selector

This commit is contained in:
jeffvli
2025-11-17 01:46:04 -08:00
parent 199a67fdf3
commit a92a829ca7
28 changed files with 782 additions and 351 deletions
+51 -10
View File
@@ -2,6 +2,7 @@ import i18n from '/@/i18n/i18n';
import { JellyfinController } from '/@/renderer/api/jellyfin/jellyfin-controller';
import { NavidromeController } from '/@/renderer/api/navidrome/navidrome-controller';
import { SubsonicController } from '/@/renderer/api/subsonic/subsonic-controller';
import { mergeMusicFolderId } from '/@/renderer/api/utils-music-folder';
import { getServerById, useAuthStore } from '/@/renderer/store';
import { toast } from '/@/shared/components/toast/toast';
import {
@@ -167,7 +168,11 @@ export const controller: GeneralController = {
return apiController(
'getAlbumArtistList',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getAlbumArtistListCount(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -181,7 +186,11 @@ export const controller: GeneralController = {
return apiController(
'getAlbumArtistListCount',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getAlbumDetail(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -223,7 +232,11 @@ export const controller: GeneralController = {
return apiController(
'getAlbumList',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getAlbumListCount(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -237,7 +250,11 @@ export const controller: GeneralController = {
return apiController(
'getAlbumListCount',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getArtistList(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -251,7 +268,11 @@ export const controller: GeneralController = {
return apiController(
'getArtistList',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getArtistListCount(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -265,7 +286,11 @@ export const controller: GeneralController = {
return apiController(
'getArtistListCount',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getDownloadUrl(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -293,7 +318,11 @@ export const controller: GeneralController = {
return apiController(
'getGenreList',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getLyrics(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -461,7 +490,11 @@ export const controller: GeneralController = {
return apiController(
'getSongList',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getSongListCount(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -475,7 +508,11 @@ export const controller: GeneralController = {
return apiController(
'getSongListCount',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
getStructuredLyrics(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -601,7 +638,11 @@ export const controller: GeneralController = {
return apiController(
'search',
server.type,
)?.({ ...args, apiClientProps: { ...args.apiClientProps, server } });
)?.({
...args,
apiClientProps: { ...args.apiClientProps, server },
query: mergeMusicFolderId(args.query, server),
});
},
setRating(args) {
const server = getServerById(args.apiClientProps.serverId);
@@ -59,6 +59,14 @@ const excludeMissing = (server?: null | ServerListItemWithCredential) => {
return undefined;
};
const getLibraryId = (musicFolderId?: string | string[]): string[] | undefined => {
if (!musicFolderId) {
return undefined;
}
return Array.isArray(musicFolderId) ? musicFolderId : [musicFolderId];
};
const getArtistSongKey = (server: null | ServerListItemWithCredential) =>
hasFeature(server, ServerFeature.TRACK_ALBUM_ARTIST_SEARCH) ? 'artists_id' : 'album_artist_id';
@@ -189,6 +197,7 @@ export const NavidromeController: InternalControllerEndpoint = {
_order: sortOrderMap.navidrome[query.sortOrder],
_sort: albumArtistListSortMap.navidrome[query.sortBy],
_start: query.startIndex,
library_id: getLibraryId(query.musicFolderId),
name: query.searchTerm,
...query._custom,
role: hasFeature(apiClientProps.server, ServerFeature.BFR) ? 'albumartist' : '',
@@ -287,6 +296,7 @@ export const NavidromeController: InternalControllerEndpoint = {
artist_id: query.artistIds?.[0],
compilation: query.compilation,
genre_id: genres,
library_id: getLibraryId(query.musicFolderId),
name: query.searchTerm,
...query._custom,
starred: query.favorite,
@@ -318,6 +328,7 @@ export const NavidromeController: InternalControllerEndpoint = {
_order: sortOrderMap.navidrome[query.sortOrder],
_sort: albumArtistListSortMap.navidrome[query.sortBy],
_start: query.startIndex,
library_id: getLibraryId(query.musicFolderId),
name: query.searchTerm,
...query._custom,
role: query.role || undefined,
@@ -361,6 +372,7 @@ export const NavidromeController: InternalControllerEndpoint = {
_order: sortOrderMap.navidrome[query.sortOrder],
_sort: genreListSortMap.navidrome[query.sortBy],
_start: query.startIndex,
library_id: getLibraryId(query.musicFolderId),
name: query.searchTerm,
},
});
@@ -480,6 +492,7 @@ export const NavidromeController: InternalControllerEndpoint = {
...navidromeFeatures,
...subsonicArgs.features,
publicPlaylist: [1],
[ServerFeature.MUSIC_FOLDER_MULTISELECT]: [1],
};
return {
@@ -567,6 +580,7 @@ export const NavidromeController: InternalControllerEndpoint = {
album_id: query.albumIds,
genre_id: query.genreIds,
[getArtistSongKey(apiClientProps.server)]: query.artistIds ?? query.albumArtistIds,
library_id: getLibraryId(query.musicFolderId),
starred: query.favorite,
title: query.searchTerm,
...query._custom,
@@ -1388,7 +1388,7 @@ export const SubsonicController: InternalControllerEndpoint = {
setRating: async (args) => {
const { apiClientProps, query } = args;
const itemIds = query.item.map((item) => item.id);
const itemIds = query.id;
for (const id of itemIds) {
await ssApiClient(apiClientProps).setRating({
+24
View File
@@ -0,0 +1,24 @@
import { ServerListItemWithCredential } from '/@/shared/types/domain-types';
export const mergeMusicFolderId = <T extends { musicFolderId?: string | string[] }>(
query: T,
server: null | ServerListItemWithCredential,
): T => {
if (
!server ||
!server.musicFolderId ||
server.musicFolderId.length === 0 ||
query.musicFolderId
) {
return query;
}
// Only merge if server matches and musicFolderId is not already in query
const musicFolderId =
server.musicFolderId.length === 1 ? server.musicFolderId[0] : server.musicFolderId;
return {
...query,
musicFolderId,
};
};