diff --git a/src/components/BecauseYouLikeRail.tsx b/src/components/BecauseYouLikeRail.tsx index 59dc5a1c..4813dcf9 100644 --- a/src/components/BecauseYouLikeRail.tsx +++ b/src/components/BecauseYouLikeRail.tsx @@ -1,4 +1,4 @@ -import { getArtist, getArtistInfo } from '@/features/artist'; +import { getArtist, getArtistInfo } from '@/lib/api/subsonicArtists'; import { filterAlbumsToActiveLibrary } from '@/lib/api/subsonicLibrary'; import { resolveAlbum, resolveMediaServerId } from '@/features/offline'; import type { SubsonicAlbum } from '@/lib/api/subsonicTypes'; diff --git a/src/components/QueuePanel.tsx b/src/components/QueuePanel.tsx index f9b833af..fa71130b 100644 --- a/src/components/QueuePanel.tsx +++ b/src/components/QueuePanel.tsx @@ -1,5 +1,5 @@ import { Play } from 'lucide-react'; -import { updatePlaylist } from '@/features/playlist'; +import { updatePlaylist } from '@/lib/api/subsonicPlaylists'; import { resolvePlaylist, resolveMediaServerId } from '@/features/offline'; import { songToTrack } from '../utils/playback/songToTrack'; import type { Track } from '../store/playerStoreTypes'; diff --git a/src/components/contextMenu/AddToPlaylistSubmenu.tsx b/src/components/contextMenu/AddToPlaylistSubmenu.tsx index b8a2b7a6..98e0d216 100644 --- a/src/components/contextMenu/AddToPlaylistSubmenu.tsx +++ b/src/components/contextMenu/AddToPlaylistSubmenu.tsx @@ -1,7 +1,7 @@ import React, { useEffect, useLayoutEffect, useMemo, useRef, useState } from 'react'; import { useTranslation } from 'react-i18next'; import { ListMusic, Plus } from 'lucide-react'; -import { getPlaylist, updatePlaylist } from '@/features/playlist'; +import { getPlaylist, updatePlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { usePlaylistStore } from '@/features/playlist'; import { showToast } from '../../utils/ui/toast'; diff --git a/src/components/contextMenu/MultiAlbumToPlaylistSubmenu.tsx b/src/components/contextMenu/MultiAlbumToPlaylistSubmenu.tsx index a1acb3ec..9c2272f0 100644 --- a/src/components/contextMenu/MultiAlbumToPlaylistSubmenu.tsx +++ b/src/components/contextMenu/MultiAlbumToPlaylistSubmenu.tsx @@ -39,7 +39,7 @@ export function MultiAlbumToPlaylistSubmenu({ albumIds, onDone, triggerId: _trig }, [albumIds]); const handleAddWithToast = async (pl: SubsonicPlaylist, songIds: string[]) => { - const { updatePlaylist } = await import('@/features/playlist'); + const { updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { @@ -125,7 +125,7 @@ export function MultiAlbumToPlaylistSubmenu({ albumIds, onDone, triggerId: _trig const handleCreate = async () => { const name = newName.trim() || t('playlists.unnamed'); try { - const { createPlaylist } = await import('@/features/playlist'); + const { createPlaylist } = await import('@/lib/api/subsonicPlaylists'); const pl = await createPlaylist(name, songIds); if (pl?.id) { usePlaylistStore.getState().touchPlaylist(pl.id); diff --git a/src/components/contextMenu/MultiArtistToPlaylistSubmenu.tsx b/src/components/contextMenu/MultiArtistToPlaylistSubmenu.tsx index 90d1820e..096c8f32 100644 --- a/src/components/contextMenu/MultiArtistToPlaylistSubmenu.tsx +++ b/src/components/contextMenu/MultiArtistToPlaylistSubmenu.tsx @@ -2,7 +2,7 @@ import React, { useEffect, useLayoutEffect, useRef, useState } from 'react'; import { useTranslation } from 'react-i18next'; import { ListMusic, Plus } from 'lucide-react'; import { resolveAlbum, resolveArtist, resolveMediaServerId, resolvePlaylist } from '@/features/offline'; -import { getPlaylists } from '@/features/playlist'; +import { getPlaylists } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { usePlaylistStore } from '@/features/playlist'; import { showToast } from '../../utils/ui/toast'; @@ -53,7 +53,7 @@ export function MultiArtistToPlaylistSubmenu({ artistIds, onDone, triggerId: _tr }, [artistIds]); const handleAddWithToast = async (pl: SubsonicPlaylist, songIds: string[]) => { - const { updatePlaylist } = await import('@/features/playlist'); + const { updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { @@ -139,7 +139,7 @@ export function MultiArtistToPlaylistSubmenu({ artistIds, onDone, triggerId: _tr const handleCreate = async () => { const name = newName.trim() || t('playlists.unnamed'); try { - const { createPlaylist } = await import('@/features/playlist'); + const { createPlaylist } = await import('@/lib/api/subsonicPlaylists'); const pl = await createPlaylist(name, songIds); if (pl?.id) { usePlaylistStore.getState().touchPlaylist(pl.id); diff --git a/src/components/contextMenu/PlaylistContextItems.tsx b/src/components/contextMenu/PlaylistContextItems.tsx index aa259015..efb345f0 100644 --- a/src/components/contextMenu/PlaylistContextItems.tsx +++ b/src/components/contextMenu/PlaylistContextItems.tsx @@ -65,7 +65,7 @@ export default function PlaylistContextItems(props: ContextMenuItemsProps) {
handleAction(async () => { const { showToast } = await import('../../utils/ui/toast'); - const { deletePlaylist } = await import('@/features/playlist'); + const { deletePlaylist } = await import('@/lib/api/subsonicPlaylists'); const { removeId } = usePlaylistStore.getState(); try { await deletePlaylist(playlist.id); @@ -113,7 +113,7 @@ export default function PlaylistContextItems(props: ContextMenuItemsProps) { {offlinePolicy.canEditPlaylist && (
handleAction(async () => { const { showToast } = await import('../../utils/ui/toast'); - const { deletePlaylist } = await import('@/features/playlist'); + const { deletePlaylist } = await import('@/lib/api/subsonicPlaylists'); const { removeId } = usePlaylistStore.getState(); const deletedIds: string[] = []; for (const pl of selectedPlaylists) { diff --git a/src/components/contextMenu/PlaylistToPlaylistSubmenus.tsx b/src/components/contextMenu/PlaylistToPlaylistSubmenus.tsx index 4dadfb3a..f090aa3e 100644 --- a/src/components/contextMenu/PlaylistToPlaylistSubmenus.tsx +++ b/src/components/contextMenu/PlaylistToPlaylistSubmenus.tsx @@ -41,7 +41,7 @@ export function SinglePlaylistToPlaylistSubmenu({ playlist, onDone, triggerId }: const handleCreate = async () => { if (!newName.trim()) return; - const { createPlaylist } = await import('@/features/playlist'); + const { createPlaylist } = await import('@/lib/api/subsonicPlaylists'); try { const newPl = await createPlaylist(newName.trim(), []); if (newPl?.id) { @@ -55,7 +55,7 @@ export function SinglePlaylistToPlaylistSubmenu({ playlist, onDone, triggerId }: }; const handleAddToNewPlaylist = async (targetId: string, targetName: string) => { - const { getPlaylist, updatePlaylist } = await import('@/features/playlist'); + const { getPlaylist, updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { @@ -73,7 +73,7 @@ export function SinglePlaylistToPlaylistSubmenu({ playlist, onDone, triggerId }: }; const handleAdd = async (targetId: string, targetName: string) => { - const { getPlaylist, updatePlaylist } = await import('@/features/playlist'); + const { getPlaylist, updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { @@ -180,7 +180,7 @@ export function MultiPlaylistToPlaylistSubmenu({ playlists, onDone, triggerId }: const handleCreate = async () => { if (!newName.trim()) return; - const { createPlaylist } = await import('@/features/playlist'); + const { createPlaylist } = await import('@/lib/api/subsonicPlaylists'); try { const newPl = await createPlaylist(newName.trim(), []); if (newPl?.id) { @@ -194,7 +194,7 @@ export function MultiPlaylistToPlaylistSubmenu({ playlists, onDone, triggerId }: }; const handleMergeToNewPlaylist = async (targetId: string, targetName: string) => { - const { getPlaylist, updatePlaylist } = await import('@/features/playlist'); + const { getPlaylist, updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { @@ -223,7 +223,7 @@ export function MultiPlaylistToPlaylistSubmenu({ playlists, onDone, triggerId }: }; const handleMerge = async (targetId: string, targetName: string) => { - const { getPlaylist, updatePlaylist } = await import('@/features/playlist'); + const { getPlaylist, updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { diff --git a/src/components/contextMenu/SongContextItems.tsx b/src/components/contextMenu/SongContextItems.tsx index c6f40c58..9632bb01 100644 --- a/src/components/contextMenu/SongContextItems.tsx +++ b/src/components/contextMenu/SongContextItems.tsx @@ -178,7 +178,7 @@ export default function SongContextItems(props: ContextMenuItemsProps) {
{offlinePolicy.canEditPlaylist && playlistId && playlistSongIndex !== undefined && (
handleAction(async () => { - const { updatePlaylist } = await import('@/features/playlist'); + const { updatePlaylist } = await import('@/lib/api/subsonicPlaylists'); const { showToast } = await import('../../utils/ui/toast'); const touchPlaylist = usePlaylistStore.getState().touchPlaylist; try { diff --git a/src/components/queuePanel/LoadPlaylistModal.tsx b/src/components/queuePanel/LoadPlaylistModal.tsx index 9929ffb1..0c7e94c5 100644 --- a/src/components/queuePanel/LoadPlaylistModal.tsx +++ b/src/components/queuePanel/LoadPlaylistModal.tsx @@ -1,7 +1,7 @@ import { useEffect, useState } from 'react'; import { Play, X, Trash2, ListPlus } from 'lucide-react'; import { useTranslation } from 'react-i18next'; -import { getPlaylists, deletePlaylist } from '@/features/playlist'; +import { getPlaylists, deletePlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; interface Props { diff --git a/src/features/album/index.ts b/src/features/album/index.ts index c063e08e..86f6153c 100644 --- a/src/features/album/index.ts +++ b/src/features/album/index.ts @@ -11,7 +11,6 @@ * sync, core), the album context-menu items (context-menu subsystem), the * shared `TracklistColumnPicker` (also used by favorites), and `cover/*`. */ -export * from './api/subsonicAlbumInfo'; export * from './hooks/useAlbumBrowseData'; export * from './hooks/useAlbumBrowseFilters'; export * from './hooks/useAlbumBrowseScrollReset'; diff --git a/src/features/album/pages/AlbumDetail.tsx b/src/features/album/pages/AlbumDetail.tsx index efed065f..884f6e1b 100644 --- a/src/features/album/pages/AlbumDetail.tsx +++ b/src/features/album/pages/AlbumDetail.tsx @@ -2,7 +2,7 @@ import { buildDownloadUrl } from '@/lib/api/subsonicStreamUrl'; import { setRating, star, unstar } from '@/lib/api/subsonicStarRating'; import { queueSongStar, queueSongRating } from '@/store/pendingStarSync'; import { getAlbumForServer } from '@/lib/api/subsonicLibrary'; -import { getArtistInfo } from '@/features/artist'; +import { getArtistInfo } from '@/lib/api/subsonicArtists'; import type { SubsonicSong } from '@/lib/api/subsonicTypes'; import { songToTrack } from '@/utils/playback/songToTrack'; import { shuffleArray } from '@/utils/playback/shuffleArray'; diff --git a/src/features/artist/hooks/useArtistDetailData.test.ts b/src/features/artist/hooks/useArtistDetailData.test.ts index 7b1179db..26df1ce4 100644 --- a/src/features/artist/hooks/useArtistDetailData.test.ts +++ b/src/features/artist/hooks/useArtistDetailData.test.ts @@ -15,10 +15,10 @@ import { MemoryRouter } from 'react-router-dom'; import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest'; import type { SubsonicArtistInfo } from '@/lib/api/subsonicTypes'; -vi.mock('@/features/artist/api/subsonicArtists'); +vi.mock('@/lib/api/subsonicArtists'); vi.mock('@/lib/api/subsonicSearch'); -import { getArtist, getArtistInfo, getTopSongs } from '@/features/artist/api/subsonicArtists'; +import { getArtist, getArtistInfo, getTopSongs } from '@/lib/api/subsonicArtists'; import { search } from '@/lib/api/subsonicSearch'; import { useArtistDetailData } from '@/features/artist/hooks/useArtistDetailData'; diff --git a/src/features/artist/hooks/useArtistDetailData.ts b/src/features/artist/hooks/useArtistDetailData.ts index dc0f054c..91b2ceb5 100644 --- a/src/features/artist/hooks/useArtistDetailData.ts +++ b/src/features/artist/hooks/useArtistDetailData.ts @@ -1,7 +1,7 @@ import { useEffect, useState } from 'react'; import { useSearchParams } from 'react-router-dom'; import { search } from '@/lib/api/subsonicSearch'; -import { getArtist, getArtistForServer, getArtistInfo, getTopSongs } from '@/features/artist/api/subsonicArtists'; +import { getArtist, getArtistForServer, getArtistInfo, getTopSongs } from '@/lib/api/subsonicArtists'; import type { SubsonicAlbum, SubsonicArtist, SubsonicArtistInfo, SubsonicSong, } from '@/lib/api/subsonicTypes'; diff --git a/src/features/artist/hooks/useArtistInfoBatch.ts b/src/features/artist/hooks/useArtistInfoBatch.ts index 33d1cc16..0385626e 100644 --- a/src/features/artist/hooks/useArtistInfoBatch.ts +++ b/src/features/artist/hooks/useArtistInfoBatch.ts @@ -1,5 +1,5 @@ import { useEffect, useMemo, useState } from 'react'; -import { getArtistInfoForServer } from '@/features/artist/api/subsonicArtists'; +import { getArtistInfoForServer } from '@/lib/api/subsonicArtists'; import type { SubsonicArtistInfo, SubsonicOpenArtistRef } from '@/lib/api/subsonicTypes'; import { makeCache } from '@/utils/cache/nowPlayingCache'; diff --git a/src/features/artist/hooks/useArtistsBrowseCatalog.ts b/src/features/artist/hooks/useArtistsBrowseCatalog.ts index 3276b66a..267174e8 100644 --- a/src/features/artist/hooks/useArtistsBrowseCatalog.ts +++ b/src/features/artist/hooks/useArtistsBrowseCatalog.ts @@ -1,4 +1,4 @@ -import { getArtists } from '@/features/artist/api/subsonicArtists'; +import { getArtists } from '@/lib/api/subsonicArtists'; import type { SubsonicArtist } from '@/lib/api/subsonicTypes'; import { useCallback, useEffect, useRef, useState } from 'react'; import { dedupeById } from '@/utils/dedupeById'; diff --git a/src/features/artist/index.ts b/src/features/artist/index.ts index 7cca687a..ec53dacf 100644 --- a/src/features/artist/index.ts +++ b/src/features/artist/index.ts @@ -11,7 +11,6 @@ * `*ContextItems`/`*ToPlaylistSubmenu` items (the cross-cutting context-menu * subsystem, shared with album), and `PlaylistArtistCell` (playlist). */ -export * from './api/subsonicArtists'; export * from './hooks/useArtistDetailData'; export * from './hooks/useArtistInfoBatch'; export * from './hooks/useArtistOfflineState'; diff --git a/src/features/artist/utils/runArtistDetailActions.ts b/src/features/artist/utils/runArtistDetailActions.ts index 2fba18d4..9fef7871 100644 --- a/src/features/artist/utils/runArtistDetailActions.ts +++ b/src/features/artist/utils/runArtistDetailActions.ts @@ -1,6 +1,6 @@ import type React from 'react'; import type { TFunction } from 'i18next'; -import { uploadArtistImage } from '@/features/playlist'; +import { uploadArtistImage } from '@/lib/api/subsonicPlaylists'; import { setRating, star, unstar } from '@/lib/api/subsonicStarRating'; import type { SubsonicArtist } from '@/lib/api/subsonicTypes'; import { useAuthStore } from '@/store/authStore'; diff --git a/src/features/artist/utils/runArtistDetailPlay.ts b/src/features/artist/utils/runArtistDetailPlay.ts index 3f79f1d5..ed89c629 100644 --- a/src/features/artist/utils/runArtistDetailPlay.ts +++ b/src/features/artist/utils/runArtistDetailPlay.ts @@ -1,5 +1,5 @@ import type { TFunction } from 'i18next'; -import { getSimilarSongs2, getTopSongs } from '@/features/artist/api/subsonicArtists'; +import { getSimilarSongs2, getTopSongs } from '@/lib/api/subsonicArtists'; import type { SubsonicAlbum, SubsonicArtist, SubsonicSong } from '@/lib/api/subsonicTypes'; import type { Track } from '@/store/playerStoreTypes'; import { songToTrack } from '@/utils/playback/songToTrack'; diff --git a/src/features/deviceSync/hooks/useDeviceSyncBrowser.ts b/src/features/deviceSync/hooks/useDeviceSyncBrowser.ts index ead13a41..c407aa75 100644 --- a/src/features/deviceSync/hooks/useDeviceSyncBrowser.ts +++ b/src/features/deviceSync/hooks/useDeviceSyncBrowser.ts @@ -1,6 +1,6 @@ import { useCallback, useEffect, useState } from 'react'; -import { getPlaylists } from '@/features/playlist'; -import { getArtists, getArtist } from '@/features/artist'; +import { getPlaylists } from '@/lib/api/subsonicPlaylists'; +import { getArtists, getArtist } from '@/lib/api/subsonicArtists'; import { getAlbumList } from '@/lib/api/subsonicLibrary'; import { search as searchSubsonic } from '@/lib/api/subsonicSearch'; import type { diff --git a/src/features/favorites/hooks/useFavoritesData.ts b/src/features/favorites/hooks/useFavoritesData.ts index d04ca2bc..ca2c0e5f 100644 --- a/src/features/favorites/hooks/useFavoritesData.ts +++ b/src/features/favorites/hooks/useFavoritesData.ts @@ -1,5 +1,5 @@ import { useEffect, useMemo, useState } from 'react'; -import { getInternetRadioStations } from '@/features/radio'; +import { getInternetRadioStations } from '@/lib/api/subsonicRadio'; import { getStarred } from '@/lib/api/subsonicStarRating'; import type { InternetRadioStation, SubsonicAlbum, SubsonicArtist, SubsonicSong, diff --git a/src/features/nowPlaying/components/NowPlayingInfo.tsx b/src/features/nowPlaying/components/NowPlayingInfo.tsx index e2458e3a..d88061a3 100644 --- a/src/features/nowPlaying/components/NowPlayingInfo.tsx +++ b/src/features/nowPlaying/components/NowPlayingInfo.tsx @@ -1,5 +1,5 @@ import { getSongForServer } from '@/lib/api/subsonicLibrary'; -import { getArtistInfoForServer } from '@/features/artist'; +import { getArtistInfoForServer } from '@/lib/api/subsonicArtists'; import type { SubsonicArtistInfo, SubsonicSong } from '@/lib/api/subsonicTypes'; import React, { useEffect, useLayoutEffect, useMemo, useRef, useState } from 'react'; import { useTranslation } from 'react-i18next'; diff --git a/src/features/nowPlaying/hooks/useNowPlayingFetchers.test.ts b/src/features/nowPlaying/hooks/useNowPlayingFetchers.test.ts index 78ba3959..a37471f9 100644 --- a/src/features/nowPlaying/hooks/useNowPlayingFetchers.test.ts +++ b/src/features/nowPlaying/hooks/useNowPlayingFetchers.test.ts @@ -13,7 +13,7 @@ import { renderHook, act, waitFor } from '@testing-library/react'; import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest'; import type { SubsonicArtistInfo, SubsonicSong, SubsonicAlbum, SubsonicArtist } from '@/lib/api/subsonicTypes'; -vi.mock('@/features/artist'); +vi.mock('@/lib/api/subsonicArtists'); vi.mock('@/lib/api/subsonicLibrary'); vi.mock('@/api/bandsintown'); vi.mock('@/utils/network/subsonicNetworkGuard', () => ({ @@ -21,7 +21,7 @@ vi.mock('@/utils/network/subsonicNetworkGuard', () => ({ })); import { shouldAttemptSubsonicForServer } from '@/utils/network/subsonicNetworkGuard'; -import { getArtistForServer, getArtistInfoForServer, getTopSongsForServer } from '@/features/artist'; +import { getArtistForServer, getArtistInfoForServer, getTopSongsForServer } from '@/lib/api/subsonicArtists'; import { getAlbumForServer, getSongForServer } from '@/lib/api/subsonicLibrary'; import { fetchBandsintownEvents } from '@/api/bandsintown'; import { useNowPlayingFetchers, type NowPlayingFetchersDeps } from '@/features/nowPlaying/hooks/useNowPlayingFetchers'; diff --git a/src/features/nowPlaying/hooks/useNowPlayingFetchers.ts b/src/features/nowPlaying/hooks/useNowPlayingFetchers.ts index 6e392c08..f7cd1c2d 100644 --- a/src/features/nowPlaying/hooks/useNowPlayingFetchers.ts +++ b/src/features/nowPlaying/hooks/useNowPlayingFetchers.ts @@ -1,5 +1,5 @@ import { useEffect, useState } from 'react'; -import { getArtistInfoForServer } from '@/features/artist'; +import { getArtistInfoForServer } from '@/lib/api/subsonicArtists'; import type { SubsonicAlbum, SubsonicArtistInfo, SubsonicSong } from '@/lib/api/subsonicTypes'; import { resolveNpAlbum, resolveNpDiscography, resolveNpSongMeta, resolveNpTopSongs } from '@/features/nowPlaying/utils/nowPlayingMetadataResolve'; import { fetchBandsintownEvents, type BandsintownEvent } from '@/api/bandsintown'; diff --git a/src/features/nowPlaying/utils/nowPlayingMetadataResolve.test.ts b/src/features/nowPlaying/utils/nowPlayingMetadataResolve.test.ts index 7e435d73..39f3031e 100644 --- a/src/features/nowPlaying/utils/nowPlayingMetadataResolve.test.ts +++ b/src/features/nowPlaying/utils/nowPlayingMetadataResolve.test.ts @@ -9,7 +9,7 @@ import { describe, it, expect, beforeEach, vi } from 'vitest'; import { onInvoke } from '@/test/mocks/tauri'; import { useLibraryIndexStore } from '@/store/libraryIndexStore'; import type { LibraryAdvancedSearchResponse } from '@/lib/api/library'; -import * as subsonicArtists from '@/features/artist'; +import * as subsonicArtists from '@/lib/api/subsonicArtists'; import * as subsonicLibrary from '@/lib/api/subsonicLibrary'; // Network reachability is decided by the guard; mock it so we can test both arms. diff --git a/src/features/nowPlaying/utils/nowPlayingMetadataResolve.ts b/src/features/nowPlaying/utils/nowPlayingMetadataResolve.ts index 48fa3d1c..69c076a4 100644 --- a/src/features/nowPlaying/utils/nowPlayingMetadataResolve.ts +++ b/src/features/nowPlaying/utils/nowPlayingMetadataResolve.ts @@ -17,7 +17,7 @@ * is intentionally absent here. */ import { libraryGetTrack, libraryGetTracksByAlbum } from '@/lib/api/library'; -import { getArtistForServer, getTopSongsForServer } from '@/features/artist'; +import { getArtistForServer, getTopSongsForServer } from '@/lib/api/subsonicArtists'; import { getAlbumForServer, getSongForServer } from '@/lib/api/subsonicLibrary'; import type { SubsonicAlbum, SubsonicSong } from '@/lib/api/subsonicTypes'; import { shouldAttemptSubsonicForServer } from '@/utils/network/subsonicNetworkGuard'; diff --git a/src/features/offline/store/offlineStore.ts b/src/features/offline/store/offlineStore.ts index eda3a61c..67b7d7c8 100644 --- a/src/features/offline/store/offlineStore.ts +++ b/src/features/offline/store/offlineStore.ts @@ -1,7 +1,7 @@ import { libraryUpsertSongsFromApi } from '@/lib/api/library'; import { buildStreamUrl } from '@/lib/api/subsonicStreamUrl'; import { getAlbum } from '@/lib/api/subsonicLibrary'; -import { getArtist } from '@/features/artist'; +import { getArtist } from '@/lib/api/subsonicArtists'; import type { SubsonicSong } from '@/lib/api/subsonicTypes'; import { create } from 'zustand'; import { persist, createJSONStorage } from 'zustand/middleware'; diff --git a/src/features/offline/utils/favoritesOfflineSync.test.ts b/src/features/offline/utils/favoritesOfflineSync.test.ts index 55003e88..298f5dbf 100644 --- a/src/features/offline/utils/favoritesOfflineSync.test.ts +++ b/src/features/offline/utils/favoritesOfflineSync.test.ts @@ -28,7 +28,7 @@ vi.mock('@/lib/api/subsonicLibrary', () => ({ getAlbumForServer: vi.fn(async () => ({ songs: [] })), })); -vi.mock('@/features/artist', () => ({ +vi.mock('@/lib/api/subsonicArtists', () => ({ getArtistForServer: vi.fn(async () => ({ albums: [] })), })); diff --git a/src/features/offline/utils/favoritesOfflineSync.ts b/src/features/offline/utils/favoritesOfflineSync.ts index 7f42c95c..ca494d91 100644 --- a/src/features/offline/utils/favoritesOfflineSync.ts +++ b/src/features/offline/utils/favoritesOfflineSync.ts @@ -1,7 +1,7 @@ import { libraryUpsertSongsFromApi } from '@/lib/api/library'; import { librarySqlServerId } from '@/api/coverCache'; import { getAlbumForServer } from '@/lib/api/subsonicLibrary'; -import { getArtistForServer } from '@/features/artist'; +import { getArtistForServer } from '@/lib/api/subsonicArtists'; import { getStarredForServer } from '@/lib/api/subsonicStarRating'; import { buildStreamUrlForServer } from '@/lib/api/subsonicStreamUrl'; import type { SubsonicSong } from '@/lib/api/subsonicTypes'; diff --git a/src/features/offline/utils/offlineMediaResolve.test.ts b/src/features/offline/utils/offlineMediaResolve.test.ts index c619257b..fa3e8487 100644 --- a/src/features/offline/utils/offlineMediaResolve.test.ts +++ b/src/features/offline/utils/offlineMediaResolve.test.ts @@ -53,11 +53,11 @@ vi.mock('@/lib/api/subsonicLibrary', () => ({ getAlbumForServer: (serverId: string, albumId: string) => getAlbumForServerMock(serverId, albumId), })); -vi.mock('@/features/artist', () => ({ +vi.mock('@/lib/api/subsonicArtists', () => ({ getArtistForServer: (serverId: string, artistId: string) => getArtistForServerMock(serverId, artistId), })); -vi.mock('@/features/playlist', () => ({ +vi.mock('@/lib/api/subsonicPlaylists', () => ({ getPlaylistForServer: (serverId: string, playlistId: string) => getPlaylistForServerMock(serverId, playlistId), })); diff --git a/src/features/offline/utils/offlineMediaResolve.ts b/src/features/offline/utils/offlineMediaResolve.ts index 0e05172c..0cb6940c 100644 --- a/src/features/offline/utils/offlineMediaResolve.ts +++ b/src/features/offline/utils/offlineMediaResolve.ts @@ -1,6 +1,6 @@ import { getAlbumForServer } from '@/lib/api/subsonicLibrary'; -import { getArtistForServer } from '@/features/artist'; -import { getPlaylistForServer } from '@/features/playlist'; +import { getArtistForServer } from '@/lib/api/subsonicArtists'; +import { getPlaylistForServer } from '@/lib/api/subsonicPlaylists'; import type { SubsonicAlbum, SubsonicArtist, diff --git a/src/features/offline/utils/pinnedOfflineSync.test.ts b/src/features/offline/utils/pinnedOfflineSync.test.ts index db6c1303..3db73221 100644 --- a/src/features/offline/utils/pinnedOfflineSync.test.ts +++ b/src/features/offline/utils/pinnedOfflineSync.test.ts @@ -29,7 +29,7 @@ vi.mock('@/utils/network/activeServerReachability', () => ({ onActiveServerBecameReachable: () => () => {}, })); -vi.mock('@/features/playlist/api/subsonicPlaylists', () => ({ +vi.mock('@/lib/api/subsonicPlaylists', () => ({ getPlaylistForServer: (serverId: string, id: string) => getPlaylistMock(serverId, id), })); @@ -38,7 +38,7 @@ vi.mock('@/lib/api/subsonicLibrary', () => ({ filterSongsToServerLibrary: (songs: SubsonicSong[]) => filterSongsMock(songs), })); -vi.mock('@/features/artist', () => ({ +vi.mock('@/lib/api/subsonicArtists', () => ({ getArtistForServer: (serverId: string, artistId: string) => getArtistForServerMock(serverId, artistId), })); diff --git a/src/features/offline/utils/pinnedOfflineSync.ts b/src/features/offline/utils/pinnedOfflineSync.ts index 8cc93573..dc128f4f 100644 --- a/src/features/offline/utils/pinnedOfflineSync.ts +++ b/src/features/offline/utils/pinnedOfflineSync.ts @@ -1,7 +1,7 @@ import { libraryGetTracksByAlbum, subscribeLibrarySyncIdle } from '@/lib/api/library'; import { getAlbumForServer, filterSongsToServerLibrary } from '@/lib/api/subsonicLibrary'; -import { getPlaylistForServer } from '@/features/playlist'; -import { getArtistForServer } from '@/features/artist'; +import { getPlaylistForServer } from '@/lib/api/subsonicPlaylists'; +import { getArtistForServer } from '@/lib/api/subsonicArtists'; import type { SubsonicSong } from '@/lib/api/subsonicTypes'; import { invoke } from '@tauri-apps/api/core'; import { useAuthStore } from '@/store/authStore'; diff --git a/src/features/offline/utils/resumeIncompleteOfflinePins.ts b/src/features/offline/utils/resumeIncompleteOfflinePins.ts index c2ace389..62d1d4ad 100644 --- a/src/features/offline/utils/resumeIncompleteOfflinePins.ts +++ b/src/features/offline/utils/resumeIncompleteOfflinePins.ts @@ -1,5 +1,5 @@ import { libraryGetTracksBatchChunked } from '@/lib/api/library'; -import { getPlaylist } from '@/features/playlist'; +import { getPlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicSong } from '@/lib/api/subsonicTypes'; import { useAuthStore } from '@/store/authStore'; import type { OfflineAlbumMeta } from '@/features/offline/store/offlineStore'; diff --git a/src/features/orbit/utils/cleanup.test.ts b/src/features/orbit/utils/cleanup.test.ts index 328d6d6d..2e08a4a7 100644 --- a/src/features/orbit/utils/cleanup.test.ts +++ b/src/features/orbit/utils/cleanup.test.ts @@ -19,7 +19,7 @@ const { authState, orbitState } = vi.hoisted(() => ({ orbitState: { sessionId: null as string | null }, })); -vi.mock('@/features/playlist', () => ({ getPlaylists, deletePlaylist })); +vi.mock('@/lib/api/subsonicPlaylists', () => ({ getPlaylists, deletePlaylist })); vi.mock('@/store/authStore', () => ({ useAuthStore: { getState: () => ({ diff --git a/src/features/orbit/utils/cleanup.ts b/src/features/orbit/utils/cleanup.ts index 12a3ef19..4add5342 100644 --- a/src/features/orbit/utils/cleanup.ts +++ b/src/features/orbit/utils/cleanup.ts @@ -1,4 +1,4 @@ -import { deletePlaylist, getPlaylists } from '@/features/playlist'; +import { deletePlaylist, getPlaylists } from '@/lib/api/subsonicPlaylists'; import { useAuthStore } from '@/store/authStore'; import { useOrbitStore } from '@/features/orbit/store/orbitStore'; import { ORBIT_PLAYLIST_PREFIX, parseOrbitState } from '@/features/orbit/api/orbit'; diff --git a/src/features/orbit/utils/guest.ts b/src/features/orbit/utils/guest.ts index 8b1a4e7a..d16fa330 100644 --- a/src/features/orbit/utils/guest.ts +++ b/src/features/orbit/utils/guest.ts @@ -1,4 +1,4 @@ -import { createPlaylist, deletePlaylist, getPlaylist, getPlaylists, updatePlaylist } from '@/features/playlist'; +import { createPlaylist, deletePlaylist, getPlaylist, getPlaylists, updatePlaylist } from '@/lib/api/subsonicPlaylists'; import { getSong } from '@/lib/api/subsonicLibrary'; import { songToTrack } from '@/utils/playback/songToTrack'; import { useAuthStore } from '@/store/authStore'; diff --git a/src/features/orbit/utils/host.test.ts b/src/features/orbit/utils/host.test.ts index 291048e8..fe03cbeb 100644 --- a/src/features/orbit/utils/host.test.ts +++ b/src/features/orbit/utils/host.test.ts @@ -24,7 +24,7 @@ vi.mock('@/features/orbit/utils/remote', () => ({ vi.mock('@/features/orbit/store/orbitStore', () => ({ useOrbitStore: { getState: () => orbitStore } })); vi.mock('@/store/authStore', () => ({ useAuthStore: { getState: () => ({}) } })); vi.mock('@/store/playerStore', () => ({ usePlayerStore: { getState: () => ({ enqueue: vi.fn() }) } })); -vi.mock('@/features/playlist', () => ({ createPlaylist: vi.fn(), deletePlaylist: vi.fn() })); +vi.mock('@/lib/api/subsonicPlaylists', () => ({ createPlaylist: vi.fn(), deletePlaylist: vi.fn() })); vi.mock('@/lib/api/subsonicLibrary', () => ({ getSong: vi.fn() })); vi.mock('@/utils/playback/songToTrack', () => ({ songToTrack: vi.fn() })); diff --git a/src/features/orbit/utils/host.ts b/src/features/orbit/utils/host.ts index d987b7b6..ad6eb799 100644 --- a/src/features/orbit/utils/host.ts +++ b/src/features/orbit/utils/host.ts @@ -1,4 +1,4 @@ -import { createPlaylist, deletePlaylist } from '@/features/playlist'; +import { createPlaylist, deletePlaylist } from '@/lib/api/subsonicPlaylists'; import { getSong } from '@/lib/api/subsonicLibrary'; import { songToTrack } from '@/utils/playback/songToTrack'; import { useAuthStore } from '@/store/authStore'; diff --git a/src/features/orbit/utils/moderation.ts b/src/features/orbit/utils/moderation.ts index 36f58707..a37c588b 100644 --- a/src/features/orbit/utils/moderation.ts +++ b/src/features/orbit/utils/moderation.ts @@ -1,4 +1,4 @@ -import { deletePlaylist, getPlaylists } from '@/features/playlist'; +import { deletePlaylist, getPlaylists } from '@/lib/api/subsonicPlaylists'; import { useOrbitStore } from '@/features/orbit/store/orbitStore'; import { orbitOutboxPlaylistName, type OrbitState } from '@/features/orbit/api/orbit'; import { writeOrbitState } from '@/features/orbit/utils/remote'; diff --git a/src/features/orbit/utils/remote.ts b/src/features/orbit/utils/remote.ts index 448af079..2ba6520b 100644 --- a/src/features/orbit/utils/remote.ts +++ b/src/features/orbit/utils/remote.ts @@ -1,4 +1,4 @@ -import { getPlaylist, getPlaylists, updatePlaylistMeta } from '@/features/playlist'; +import { getPlaylist, getPlaylists, updatePlaylistMeta } from '@/lib/api/subsonicPlaylists'; import { orbitSessionPlaylistName, parseOrbitState, diff --git a/src/features/orbit/utils/sweep.ts b/src/features/orbit/utils/sweep.ts index 369fb1ab..2921e692 100644 --- a/src/features/orbit/utils/sweep.ts +++ b/src/features/orbit/utils/sweep.ts @@ -1,4 +1,4 @@ -import { getPlaylist, getPlaylists, updatePlaylist } from '@/features/playlist'; +import { getPlaylist, getPlaylists, updatePlaylist } from '@/lib/api/subsonicPlaylists'; import { type OrbitOutboxMeta } from '@/features/orbit/api/orbit'; import { parseOutboxPlaylistName } from '@/features/orbit/utils/helpers'; import { type OutboxSnapshot } from '@/features/orbit/utils/stateMath'; diff --git a/src/features/playlist/hooks/usePlaylistsLibraryScopeCounts.ts b/src/features/playlist/hooks/usePlaylistsLibraryScopeCounts.ts index 3fe51bb9..9efb20bd 100644 --- a/src/features/playlist/hooks/usePlaylistsLibraryScopeCounts.ts +++ b/src/features/playlist/hooks/usePlaylistsLibraryScopeCounts.ts @@ -1,6 +1,6 @@ import { useEffect, useState } from 'react'; import { filterSongsToActiveLibrary } from '@/lib/api/subsonicLibrary'; -import { getPlaylist } from '@/features/playlist/api/subsonicPlaylists'; +import { getPlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { useOfflineBrowseContext } from '@/features/offline'; diff --git a/src/features/playlist/index.ts b/src/features/playlist/index.ts index 7bec89ea..e4924ba6 100644 --- a/src/features/playlist/index.ts +++ b/src/features/playlist/index.ts @@ -10,7 +10,6 @@ * `playlistDetailHelpers` (shared with offline + favorites; keeping it here * would create a playlist⟷offline barrel cycle → lib/shared in M4). */ -export * from './api/subsonicPlaylists'; export * from './hooks/usePlaylistBulkPlayCallbacks'; export * from './hooks/usePlaylistCovers'; export * from './hooks/usePlaylistDerived'; diff --git a/src/features/playlist/pages/PlaylistDetail.tsx b/src/features/playlist/pages/PlaylistDetail.tsx index 1cb840fb..f371d1f2 100644 --- a/src/features/playlist/pages/PlaylistDetail.tsx +++ b/src/features/playlist/pages/PlaylistDetail.tsx @@ -1,4 +1,4 @@ -import { updatePlaylist } from '@/features/playlist/api/subsonicPlaylists'; +import { updatePlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist, SubsonicSong } from '@/lib/api/subsonicTypes'; import React, { useEffect, useState, useCallback, useMemo } from 'react'; import { useParams, useNavigate, useLocation } from 'react-router-dom'; diff --git a/src/features/playlist/store/playlistStore.ts b/src/features/playlist/store/playlistStore.ts index 78f2e618..4bbc8dd0 100644 --- a/src/features/playlist/store/playlistStore.ts +++ b/src/features/playlist/store/playlistStore.ts @@ -1,8 +1,8 @@ -import { getPlaylists } from '@/features/playlist/api/subsonicPlaylists'; +import { getPlaylists } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { create } from 'zustand'; import { persist } from 'zustand/middleware'; -import { createPlaylist as apiCreatePlaylist } from '@/features/playlist/api/subsonicPlaylists'; +import { createPlaylist as apiCreatePlaylist } from '@/lib/api/subsonicPlaylists'; import { useAuthStore } from '@/store/authStore'; import { isOfflineBrowseActive } from '@/features/offline'; import { fetchOfflineBrowsablePlaylists } from '@/features/offline'; diff --git a/src/features/playlist/utils/playPlaylistById.ts b/src/features/playlist/utils/playPlaylistById.ts index 362965e6..fe136adb 100644 --- a/src/features/playlist/utils/playPlaylistById.ts +++ b/src/features/playlist/utils/playPlaylistById.ts @@ -1,4 +1,4 @@ -import { getPlaylist } from '@/features/playlist/api/subsonicPlaylists'; +import { getPlaylist } from '@/lib/api/subsonicPlaylists'; import { songToTrack } from '@/utils/playback/songToTrack'; import { usePlayerStore } from '@/store/playerStore'; import { playPlaylistAll } from '@/features/playlist/utils/playlistBulkPlayActions'; diff --git a/src/features/playlist/utils/runPlaylistLoad.ts b/src/features/playlist/utils/runPlaylistLoad.ts index 37927548..abf73749 100644 --- a/src/features/playlist/utils/runPlaylistLoad.ts +++ b/src/features/playlist/utils/runPlaylistLoad.ts @@ -1,5 +1,5 @@ import type React from 'react'; -import { getPlaylist } from '@/features/playlist/api/subsonicPlaylists'; +import { getPlaylist } from '@/lib/api/subsonicPlaylists'; import { filterSongsToActiveLibrary } from '@/lib/api/subsonicLibrary'; import type { SubsonicPlaylist, SubsonicSong } from '@/lib/api/subsonicTypes'; import { useAuthStore } from '@/store/authStore'; diff --git a/src/features/playlist/utils/runPlaylistSaveMeta.ts b/src/features/playlist/utils/runPlaylistSaveMeta.ts index e846a375..c1f24244 100644 --- a/src/features/playlist/utils/runPlaylistSaveMeta.ts +++ b/src/features/playlist/utils/runPlaylistSaveMeta.ts @@ -1,5 +1,5 @@ import type { TFunction } from 'i18next'; -import { getPlaylist, updatePlaylistMeta, uploadPlaylistCoverArt } from '@/features/playlist/api/subsonicPlaylists'; +import { getPlaylist, updatePlaylistMeta, uploadPlaylistCoverArt } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { showToast } from '@/utils/ui/toast'; diff --git a/src/features/playlist/utils/runPlaylistsActions.ts b/src/features/playlist/utils/runPlaylistsActions.ts index af453611..e2b352f8 100644 --- a/src/features/playlist/utils/runPlaylistsActions.ts +++ b/src/features/playlist/utils/runPlaylistsActions.ts @@ -1,6 +1,6 @@ import type React from 'react'; import type { TFunction } from 'i18next'; -import { deletePlaylist, getPlaylist, updatePlaylist } from '@/features/playlist/api/subsonicPlaylists'; +import { deletePlaylist, getPlaylist, updatePlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { usePlaylistStore } from '@/features/playlist/store/playlistStore'; import { showToast } from '@/utils/ui/toast'; diff --git a/src/features/radio/components/RadioDirectoryModal.tsx b/src/features/radio/components/RadioDirectoryModal.tsx index da925f0b..de37adcc 100644 --- a/src/features/radio/components/RadioDirectoryModal.tsx +++ b/src/features/radio/components/RadioDirectoryModal.tsx @@ -5,7 +5,7 @@ import { Cast, Check, Loader2, Plus, X } from 'lucide-react'; import { createInternetRadioStation, fetchUrlBytes, getInternetRadioStations, getTopRadioStations, searchRadioBrowser, uploadRadioCoverArtBytes, -} from '@/features/radio/api/subsonicRadio'; +} from '@/lib/api/subsonicRadio'; import { type InternetRadioStation, type RadioBrowserStation, RADIO_PAGE_SIZE, } from '@/lib/api/subsonicTypes'; diff --git a/src/features/radio/index.ts b/src/features/radio/index.ts index 6102acbf..7438203b 100644 --- a/src/features/radio/index.ts +++ b/src/features/radio/index.ts @@ -8,7 +8,6 @@ * playback/audio core — the player core drives them, so they are not part of * this UI feature. */ -export { getInternetRadioStations } from './api/subsonicRadio'; export { useRadioMetadata } from './hooks/useRadioMetadata'; export type { RadioMetadata } from './hooks/useRadioMetadata'; export { useRadioMprisSync } from './hooks/useRadioMprisSync'; diff --git a/src/features/radio/pages/InternetRadio.tsx b/src/features/radio/pages/InternetRadio.tsx index 828c7644..38debe11 100644 --- a/src/features/radio/pages/InternetRadio.tsx +++ b/src/features/radio/pages/InternetRadio.tsx @@ -1,4 +1,4 @@ -import { getInternetRadioStations, createInternetRadioStation, updateInternetRadioStation, deleteInternetRadioStation, uploadRadioCoverArt, deleteRadioCoverArt } from '@/features/radio/api/subsonicRadio'; +import { getInternetRadioStations, createInternetRadioStation, updateInternetRadioStation, deleteInternetRadioStation, uploadRadioCoverArt, deleteRadioCoverArt } from '@/lib/api/subsonicRadio'; import { type InternetRadioStation } from '@/lib/api/subsonicTypes'; import React, { useEffect, useState, useMemo, useCallback } from 'react'; import { Plus, Search } from 'lucide-react'; diff --git a/src/features/stats/pages/Statistics.tsx b/src/features/stats/pages/Statistics.tsx index d65ce88d..f5931bd8 100644 --- a/src/features/stats/pages/Statistics.tsx +++ b/src/features/stats/pages/Statistics.tsx @@ -1,4 +1,4 @@ -import { fetchStatisticsFormatSample, fetchStatisticsLibraryAggregates, fetchStatisticsOverview } from '@/features/stats/api/subsonicStatistics'; +import { fetchStatisticsFormatSample, fetchStatisticsLibraryAggregates, fetchStatisticsOverview } from '@/lib/api/subsonicStatistics'; import { getAlbumList } from '@/lib/api/subsonicLibrary'; import type { SubsonicAlbum, SubsonicGenre } from '@/lib/api/subsonicTypes'; import React, { useEffect, useState } from 'react'; diff --git a/src/hooks/tauriBridge/useCliBridge.ts b/src/hooks/tauriBridge/useCliBridge.ts index 32ff20e5..e26411b4 100644 --- a/src/hooks/tauriBridge/useCliBridge.ts +++ b/src/hooks/tauriBridge/useCliBridge.ts @@ -2,7 +2,7 @@ import { useEffect } from 'react'; import { listen } from '@tauri-apps/api/event'; import { invoke } from '@tauri-apps/api/core'; import type { NavigateFunction } from 'react-router-dom'; -import { getSimilarSongs } from '@/features/artist'; +import { getSimilarSongs } from '@/lib/api/subsonicArtists'; import { getMusicFolders } from '@/lib/api/subsonicLibrary'; import { search as subsonicSearch } from '@/lib/api/subsonicSearch'; import { filterSongsForLuckyMixRatings, getMixMinRatingsConfigFromAuth } from '../../utils/mix/mixRatingFilter'; diff --git a/src/hooks/usePendingSmartPolling.ts b/src/hooks/usePendingSmartPolling.ts index 6421310d..04bfd152 100644 --- a/src/hooks/usePendingSmartPolling.ts +++ b/src/hooks/usePendingSmartPolling.ts @@ -1,6 +1,6 @@ import { useEffect } from 'react'; import type React from 'react'; -import { getPlaylist } from '@/features/playlist'; +import { getPlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { usePlaylistStore } from '@/features/playlist'; import type { PendingSmartPlaylist } from '@/features/playlist'; diff --git a/src/hooks/useSmartCoverCollage.ts b/src/hooks/useSmartCoverCollage.ts index 978d3155..4ea0c4fd 100644 --- a/src/hooks/useSmartCoverCollage.ts +++ b/src/hooks/useSmartCoverCollage.ts @@ -1,6 +1,6 @@ import { useEffect, useState } from 'react'; import { filterSongsToActiveLibrary } from '@/lib/api/subsonicLibrary'; -import { getPlaylist } from '@/features/playlist'; +import { getPlaylist } from '@/lib/api/subsonicPlaylists'; import type { SubsonicPlaylist } from '@/lib/api/subsonicTypes'; import { isSmartPlaylistName } from '@/features/playlist'; diff --git a/src/lib/api/subsonic.async.test.ts b/src/lib/api/subsonic.async.test.ts index 6c168c41..a804b417 100644 --- a/src/lib/api/subsonic.async.test.ts +++ b/src/lib/api/subsonic.async.test.ts @@ -27,11 +27,11 @@ vi.mock('@/utils/network/subsonicNetworkGuard', () => ({ import axios from 'axios'; import { pingWithCredentials, pingWithCredentialsForProfile, ping } from '@/lib/api/subsonic'; -import { getAlbumInfo2 } from '@/features/album'; +import { getAlbumInfo2 } from '@/lib/api/subsonicAlbumInfo'; import { getStarred } from '@/lib/api/subsonicStarRating'; import { search } from '@/lib/api/subsonicSearch'; import { getAlbum, getMusicDirectory, getMusicFolders, getMusicIndexes, getRandomSongs, getSong } from '@/lib/api/subsonicLibrary'; -import { getArtists, getTopSongs } from '@/features/artist'; +import { getArtists, getTopSongs } from '@/lib/api/subsonicArtists'; import { useAuthStore } from '@/store/authStore'; import { resetAuthStore } from '@/test/helpers/storeReset'; diff --git a/src/features/album/api/subsonicAlbumInfo.ts b/src/lib/api/subsonicAlbumInfo.ts similarity index 100% rename from src/features/album/api/subsonicAlbumInfo.ts rename to src/lib/api/subsonicAlbumInfo.ts diff --git a/src/features/artist/api/subsonicArtists.router.test.ts b/src/lib/api/subsonicArtists.router.test.ts similarity index 97% rename from src/features/artist/api/subsonicArtists.router.test.ts rename to src/lib/api/subsonicArtists.router.test.ts index 76b53c51..51b757b4 100644 --- a/src/features/artist/api/subsonicArtists.router.test.ts +++ b/src/lib/api/subsonicArtists.router.test.ts @@ -14,7 +14,7 @@ vi.mock('@/lib/api/subsonicLibrary', () => ({ })); import { api } from '@/lib/api/subsonicClient'; -import { fetchSimilarTracksRouted } from '@/features/artist/api/subsonicArtists'; +import { fetchSimilarTracksRouted } from '@/lib/api/subsonicArtists'; import { useAuthStore } from '@/store/authStore'; const SID = 'srv-router'; diff --git a/src/features/artist/api/subsonicArtists.ts b/src/lib/api/subsonicArtists.ts similarity index 100% rename from src/features/artist/api/subsonicArtists.ts rename to src/lib/api/subsonicArtists.ts diff --git a/src/features/playlist/api/subsonicPlaylists.ts b/src/lib/api/subsonicPlaylists.ts similarity index 100% rename from src/features/playlist/api/subsonicPlaylists.ts rename to src/lib/api/subsonicPlaylists.ts diff --git a/src/features/radio/api/subsonicRadio.ts b/src/lib/api/subsonicRadio.ts similarity index 100% rename from src/features/radio/api/subsonicRadio.ts rename to src/lib/api/subsonicRadio.ts diff --git a/src/lib/api/subsonicRatings.test.ts b/src/lib/api/subsonicRatings.test.ts index f47074c2..e3c29c81 100644 --- a/src/lib/api/subsonicRatings.test.ts +++ b/src/lib/api/subsonicRatings.test.ts @@ -1,12 +1,12 @@ import { beforeEach, describe, expect, it, vi } from 'vitest'; -vi.mock('@/features/artist', () => ({ getArtist: vi.fn() })); +vi.mock('@/lib/api/subsonicArtists', () => ({ getArtist: vi.fn() })); vi.mock('@/lib/api/subsonicLibrary', () => ({ getAlbum: vi.fn() })); vi.mock('@/utils/network/subsonicNetworkGuard', () => ({ shouldAttemptSubsonicForActiveServer: vi.fn(() => true), })); -import { getArtist } from '@/features/artist'; +import { getArtist } from '@/lib/api/subsonicArtists'; import { invalidateEntityUserRatingCaches, prefetchArtistUserRatings } from '@/lib/api/subsonicRatings'; beforeEach(() => { diff --git a/src/lib/api/subsonicRatings.ts b/src/lib/api/subsonicRatings.ts index 885cac56..943a4e6e 100644 --- a/src/lib/api/subsonicRatings.ts +++ b/src/lib/api/subsonicRatings.ts @@ -1,4 +1,4 @@ -import { getArtist } from '@/features/artist'; +import { getArtist } from '@/lib/api/subsonicArtists'; import { getAlbum } from '@/lib/api/subsonicLibrary'; import { shouldAttemptSubsonicForActiveServer } from '@/utils/network/subsonicNetworkGuard'; diff --git a/src/features/stats/api/subsonicStatistics.ts b/src/lib/api/subsonicStatistics.ts similarity index 98% rename from src/features/stats/api/subsonicStatistics.ts rename to src/lib/api/subsonicStatistics.ts index 1b0b351a..47911926 100644 --- a/src/features/stats/api/subsonicStatistics.ts +++ b/src/lib/api/subsonicStatistics.ts @@ -1,6 +1,6 @@ import { useAuthStore } from '@/store/authStore'; import { genreTagsFor } from '@/utils/library/genreTags'; -import { getArtists } from '@/features/artist'; +import { getArtists } from '@/lib/api/subsonicArtists'; import { getAlbumList, getRandomSongs } from '@/lib/api/subsonicLibrary'; import type { StatisticsFormatSample, diff --git a/src/pages/ComposerDetail.tsx b/src/pages/ComposerDetail.tsx index 16234bb4..71a2f7d7 100644 --- a/src/pages/ComposerDetail.tsx +++ b/src/pages/ComposerDetail.tsx @@ -1,5 +1,5 @@ import { star, unstar } from '@/lib/api/subsonicStarRating'; -import { getArtist, getArtistInfo } from '@/features/artist'; +import { getArtist, getArtistInfo } from '@/lib/api/subsonicArtists'; import type { SubsonicArtist, SubsonicAlbum, SubsonicArtistInfo } from '@/lib/api/subsonicTypes'; import { useEffect, useState, useMemo } from 'react'; import { useParams, useNavigate } from 'react-router-dom'; diff --git a/src/pages/Home.tsx b/src/pages/Home.tsx index 15acd962..7354923e 100644 --- a/src/pages/Home.tsx +++ b/src/pages/Home.tsx @@ -1,4 +1,4 @@ -import { getArtists } from '@/features/artist'; +import { getArtists } from '@/lib/api/subsonicArtists'; import { getAlbumList, getRandomSongs } from '@/lib/api/subsonicLibrary'; import type { SubsonicAlbum, SubsonicArtist, SubsonicSong } from '@/lib/api/subsonicTypes'; import { runLocalRandomSongs } from '../utils/library/browseTextSearch'; diff --git a/src/store/nextAction.ts b/src/store/nextAction.ts index a9699ef3..6438f4b6 100644 --- a/src/store/nextAction.ts +++ b/src/store/nextAction.ts @@ -1,4 +1,4 @@ -import { getSimilarSongs2, getTopSongs } from '@/features/artist'; +import { getSimilarSongs2, getTopSongs } from '@/lib/api/subsonicArtists'; import { invoke } from '@tauri-apps/api/core'; import { buildInfiniteQueueCandidates } from '../utils/playback/buildInfiniteQueueCandidates'; import { songToTrack } from '../utils/playback/songToTrack'; diff --git a/src/store/nextActionOrbitRadio.test.ts b/src/store/nextActionOrbitRadio.test.ts index 101342d1..6ddcebff 100644 --- a/src/store/nextActionOrbitRadio.test.ts +++ b/src/store/nextActionOrbitRadio.test.ts @@ -7,7 +7,7 @@ const { inOrbit, getSimilarSongs2, getTopSongs } = vi.hoisted(() => ({ getTopSongs: vi.fn(() => Promise.resolve([])), })); -vi.mock('@/features/artist', () => ({ getSimilarSongs2, getTopSongs })); +vi.mock('@/lib/api/subsonicArtists', () => ({ getSimilarSongs2, getTopSongs })); vi.mock('@tauri-apps/api/core', () => ({ invoke: vi.fn(() => Promise.resolve()) })); vi.mock('@/features/orbit', () => ({ isInOrbitSession: () => inOrbit.value })); vi.mock('./authStore', () => ({ diff --git a/src/store/playerStore.persistence.test.ts b/src/store/playerStore.persistence.test.ts index bb44f8e9..5eaaedfe 100644 --- a/src/store/playerStore.persistence.test.ts +++ b/src/store/playerStore.persistence.test.ts @@ -43,11 +43,11 @@ vi.mock('@/lib/api/subsonicLibrary', () => ({ getSong: vi.fn(async () => null), getRandomSongs: vi.fn(async () => []), })); -vi.mock('@/features/artist', () => ({ +vi.mock('@/lib/api/subsonicArtists', () => ({ getSimilarSongs2: vi.fn(async () => []), getTopSongs: vi.fn(async () => []), })); -vi.mock('@/features/album', () => ({ +vi.mock('@/lib/api/subsonicAlbumInfo', () => ({ getAlbumInfo2: vi.fn(async () => null), })); vi.mock('@/lib/api/subsonicScrobble', () => ({ diff --git a/src/utils/componentHelpers/contextMenuActions.ts b/src/utils/componentHelpers/contextMenuActions.ts index 6271036b..2e23b132 100644 --- a/src/utils/componentHelpers/contextMenuActions.ts +++ b/src/utils/componentHelpers/contextMenuActions.ts @@ -1,6 +1,6 @@ import { join } from '@tauri-apps/api/path'; import { invoke } from '@tauri-apps/api/core'; -import { getSimilarSongs2, fetchSimilarTracksRouted, getTopSongs } from '@/features/artist'; +import { getSimilarSongs2, fetchSimilarTracksRouted, getTopSongs } from '@/lib/api/subsonicArtists'; import { filterSongsForLuckyMixRatings, getMixMinRatingsConfigFromAuth } from '../mix/mixRatingFilter'; import { buildDownloadUrl } from '@/lib/api/subsonicStreamUrl'; import { useAuthStore } from '../../store/authStore'; diff --git a/src/utils/mix/luckyMix.ts b/src/utils/mix/luckyMix.ts index adcb18fa..7c7e801e 100644 --- a/src/utils/mix/luckyMix.ts +++ b/src/utils/mix/luckyMix.ts @@ -1,4 +1,4 @@ -import { fetchSimilarTracksRouted } from '@/features/artist'; +import { fetchSimilarTracksRouted } from '@/lib/api/subsonicArtists'; import { filterSongsToActiveLibrary, getRandomSongs } from '@/lib/api/subsonicLibrary'; import type { SubsonicAlbum, SubsonicSong } from '@/lib/api/subsonicTypes'; import type { QueueItemRef } from '../../store/playerStoreTypes'; diff --git a/src/utils/mix/luckyMixHelpers.ts b/src/utils/mix/luckyMixHelpers.ts index 5a41d136..47af8da1 100644 --- a/src/utils/mix/luckyMixHelpers.ts +++ b/src/utils/mix/luckyMixHelpers.ts @@ -1,4 +1,4 @@ -import { getTopSongs } from '@/features/artist'; +import { getTopSongs } from '@/lib/api/subsonicArtists'; import { filterSongsToActiveLibrary, getAlbumList, getRandomSongs } from '@/lib/api/subsonicLibrary'; import { resolveAlbumForActiveServer } from '@/features/offline'; import type { SubsonicAlbum, SubsonicSong } from '@/lib/api/subsonicTypes'; diff --git a/src/utils/playback/buildInfiniteQueueCandidates.test.ts b/src/utils/playback/buildInfiniteQueueCandidates.test.ts index bed28bb9..d450b87e 100644 --- a/src/utils/playback/buildInfiniteQueueCandidates.test.ts +++ b/src/utils/playback/buildInfiniteQueueCandidates.test.ts @@ -6,7 +6,7 @@ * refactor (2026-05-12). This test pins the artist-first / random-fallback * order, the dedup contract against existingIds, and the autoAdded flag. */ -import { getSimilarSongs2, getTopSongs } from '@/features/artist'; +import { getSimilarSongs2, getTopSongs } from '@/lib/api/subsonicArtists'; import { getRandomSongs } from '@/lib/api/subsonicLibrary'; import type { Track } from '../../store/playerStoreTypes'; import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest'; @@ -14,7 +14,7 @@ import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest'; // Mock only the artist Subsonic API submodule (the pre-move target was // `api/subsonicArtists`); the barrel re-exports it, so consumers still get the // stubs while `coerceOpenArtistRefs` (used by songToTrack) stays real. -vi.mock('@/features/artist/api/subsonicArtists', () => ({ +vi.mock('@/lib/api/subsonicArtists', () => ({ getSimilarSongs2: vi.fn(), getTopSongs: vi.fn(), })); diff --git a/src/utils/playback/buildInfiniteQueueCandidates.ts b/src/utils/playback/buildInfiniteQueueCandidates.ts index cce683f0..99aabb19 100644 --- a/src/utils/playback/buildInfiniteQueueCandidates.ts +++ b/src/utils/playback/buildInfiniteQueueCandidates.ts @@ -1,4 +1,4 @@ -import { getSimilarSongs2, getTopSongs } from '@/features/artist'; +import { getSimilarSongs2, getTopSongs } from '@/lib/api/subsonicArtists'; import { getRandomSongs } from '@/lib/api/subsonicLibrary'; import type { Track } from '../../store/playerStoreTypes'; import { diff --git a/src/utils/share/enqueueShareSearchPayload.test.ts b/src/utils/share/enqueueShareSearchPayload.test.ts index 8300308c..dee9be2c 100644 --- a/src/utils/share/enqueueShareSearchPayload.test.ts +++ b/src/utils/share/enqueueShareSearchPayload.test.ts @@ -27,7 +27,7 @@ vi.mock('@/lib/api/subsonicLibrary', () => ({ getSong: mocks.getSong, })); -vi.mock('@/features/artist', () => ({ +vi.mock('@/lib/api/subsonicArtists', () => ({ getArtist: mocks.getArtist, }));