From 1803e9dc7c3f2e51f060fda6ea9199c327a90e93 Mon Sep 17 00:00:00 2001
From: austinried <4966622+austinried@users.noreply.github.com>
Date: Sat, 19 Mar 2022 12:20:45 +0900
Subject: [PATCH] remove unused + (slightly) rework search
---
app/models/music.ts | 6 --
app/screens/Search.tsx | 42 +++++---
app/screens/SearchResultsView.tsx | 75 ++++++++++----
app/state/music.ts | 157 +-----------------------------
index.js | 6 ++
5 files changed, 93 insertions(+), 193 deletions(-)
diff --git a/app/models/music.ts b/app/models/music.ts
index 1238c7c..10d5b65 100644
--- a/app/models/music.ts
+++ b/app/models/music.ts
@@ -21,12 +21,6 @@ export interface Album extends AlbumListItem {
year?: number
}
-export interface SearchResults {
- artists: Artist[]
- albums: AlbumListItem[]
- songs: Song[]
-}
-
export interface PlaylistListItem {
itemType: 'playlist'
id: string
diff --git a/app/screens/Search.tsx b/app/screens/Search.tsx
index ab07b0e..26ba23b 100644
--- a/app/screens/Search.tsx
+++ b/app/screens/Search.tsx
@@ -5,9 +5,8 @@ import ListItem from '@app/components/ListItem'
import NothingHere from '@app/components/NothingHere'
import TextInput from '@app/components/TextInput'
import { useActiveServerRefresh } from '@app/hooks/server'
-import { ListableItem, SearchResults, Song } from '@app/models/music'
-import { selectMusic } from '@app/state/music'
-import { useStore } from '@app/state/store'
+import { Album, Artist, mapById, SearchResults, Song } from '@app/state/library'
+import { useStore, useStoreDeep } from '@app/state/store'
import { selectTrackPlayer } from '@app/state/trackplayer'
import colors from '@app/styles/colors'
import font from '@app/styles/font'
@@ -42,8 +41,27 @@ const SongItem = React.memo<{ item: Song }>(({ item }) => {
const ResultsCategory = React.memo<{
name: string
query: string
- items: ListableItem[]
-}>(({ name, query, items }) => {
+ ids: string[]
+ type: 'artist' | 'album' | 'song'
+}>(({ name, query, type, ids }) => {
+ const items: (Album | Artist | Song)[] = useStoreDeep(
+ useCallback(
+ store => {
+ switch (type) {
+ case 'album':
+ return mapById(store.entities.albums, ids)
+ case 'artist':
+ return mapById(store.entities.artists, ids)
+ case 'song':
+ return mapById(store.entities.songs, ids)
+ default:
+ return []
+ }
+ },
+ [ids, type],
+ ),
+ )
+
const navigation = useNavigation()
if (items.length === 0) {
@@ -54,8 +72,8 @@ const ResultsCategory = React.memo<{
<>
{items.map(a =>
- a.itemType === 'song' ? (
-
+ type === 'song' ? (
+
) : (
),
@@ -78,15 +96,15 @@ const Results = React.memo<{
}>(({ results, query }) => {
return (
<>
-
-
-
+
+
+
>
)
})
const Search = () => {
- const fetchSearchResults = useStore(selectMusic.fetchSearchResults)
+ const fetchSearchResults = useStore(store => store.fetchLibrarySearchResults)
const [results, setResults] = useState({ artists: [], albums: [], songs: [] })
const [refreshing, setRefreshing] = useState(false)
const [text, setText] = useState('')
@@ -118,7 +136,7 @@ const Search = () => {
() =>
debounce(async (query: string) => {
setRefreshing(true)
- setResults(await fetchSearchResults(query))
+ setResults(await fetchSearchResults({ query, albumCount: 5, artistCount: 5, songCount: 5 }))
setRefreshing(false)
}, 400),
[fetchSearchResults],
diff --git a/app/screens/SearchResultsView.tsx b/app/screens/SearchResultsView.tsx
index da53ff4..d93d480 100644
--- a/app/screens/SearchResultsView.tsx
+++ b/app/screens/SearchResultsView.tsx
@@ -1,15 +1,15 @@
import GradientFlatList from '@app/components/GradientFlatList'
import ListItem from '@app/components/ListItem'
import { useFetchPaginatedList } from '@app/hooks/list'
-import { AlbumListItem, Artist, Song } from '@app/models/music'
-import { selectMusic } from '@app/state/music'
-import { useStore } from '@app/state/store'
+import { Album, Artist, Song, mapById } from '@app/state/library'
+import { useStore, useStoreDeep } from '@app/state/store'
import { selectTrackPlayer } from '@app/state/trackplayer'
+import { Search3Params } from '@app/subsonic/params'
import { useNavigation } from '@react-navigation/native'
import React, { useCallback, useEffect } from 'react'
import { StyleSheet } from 'react-native'
-type SearchListItemType = AlbumListItem | Song | Artist
+type SearchListItemType = Album | Song | Artist
const ResultsListItem: React.FC<{ item: SearchListItemType }> = ({ item }) => {
const setQueue = useStore(selectTrackPlayer.setQueue)
@@ -40,27 +40,62 @@ const SearchResultsView: React.FC<{
type: 'album' | 'artist' | 'song'
}> = ({ query, type }) => {
const navigation = useNavigation()
- const fetchSearchResults = useStore(selectMusic.fetchSearchResults)
- const { list, refreshing, refresh, fetchNextPage } = useFetchPaginatedList(
+ const fetchSearchResults = useStore(store => store.fetchLibrarySearchResults)
+ const { list, refreshing, refresh, fetchNextPage } = useFetchPaginatedList(
useCallback(
- (size, offset) =>
- fetchSearchResults(query, type, size, offset).then(results => {
- switch (type) {
- case 'album':
- return results.albums
- case 'artist':
- return results.artists
- case 'song':
- return results.songs
- default:
- return []
- }
- }),
+ async (size, offset) => {
+ const params: Search3Params = { query }
+ if (type === 'album') {
+ params.albumCount = size
+ params.albumOffset = offset
+ } else if (type === 'artist') {
+ params.artistCount = size
+ params.artistOffset = offset
+ } else if (type === 'song') {
+ params.songCount = size
+ params.songOffset = offset
+ } else {
+ params.albumCount = 5
+ params.artistCount = 5
+ params.songCount = 5
+ }
+
+ const results = await fetchSearchResults(params)
+
+ switch (type) {
+ case 'album':
+ return results.albums
+ case 'artist':
+ return results.artists
+ case 'song':
+ return results.songs
+ default:
+ return []
+ }
+ },
[fetchSearchResults, query, type],
),
100,
)
+ const items: SearchListItemType[] = useStoreDeep(
+ useCallback(
+ store => {
+ switch (type) {
+ case 'album':
+ return mapById(store.entities.albums, list)
+ case 'artist':
+ return mapById(store.entities.artists, list)
+ case 'song':
+ return mapById(store.entities.songs, list)
+ default:
+ return []
+ }
+ },
+ [list, type],
+ ),
+ )
+
useEffect(() => {
navigation.setOptions({
title: `Search: "${query}"`,
@@ -70,7 +105,7 @@ const SearchResultsView: React.FC<{
return (
i.toString()}
onRefresh={refresh}
diff --git a/app/state/music.ts b/app/state/music.ts
index ad88302..55fbf4c 100644
--- a/app/state/music.ts
+++ b/app/state/music.ts
@@ -1,23 +1,10 @@
-import { AlbumListItem, Artist, PlaylistListItem, SearchResults, StarrableItemType } from '@app/models/music'
+import { StarrableItemType } from '@app/models/music'
import { Store } from '@app/state/store'
-import { GetAlbumList2Params, Search3Params, StarParams } from '@app/subsonic/params'
+import { StarParams } from '@app/subsonic/params'
import produce from 'immer'
import { GetState, SetState } from 'zustand'
export type MusicSlice = {
- //
- // lists-style state
- //
- fetchArtists: (size?: number, offset?: number) => Promise
- fetchPlaylists: () => Promise
- fetchAlbums: () => Promise
- fetchSearchResults: (
- query: string,
- type?: 'album' | 'song' | 'artist',
- size?: number,
- offset?: number,
- ) => Promise
-
//
// actions, etc.
//
@@ -33,11 +20,6 @@ export type MusicSlice = {
}
export const selectMusic = {
- fetchArtists: (store: MusicSlice) => store.fetchArtists,
- fetchPlaylists: (store: MusicSlice) => store.fetchPlaylists,
- fetchAlbums: (store: MusicSlice) => store.fetchAlbums,
- fetchSearchResults: (store: MusicSlice) => store.fetchSearchResults,
-
starItem: (store: MusicSlice) => store.starItem,
}
@@ -55,141 +37,6 @@ function reduceStarred(
}
export const createMusicSlice = (set: SetState, get: GetState): MusicSlice => ({
- fetchArtists: async () => {
- const client = get().client
- if (!client) {
- return []
- }
-
- try {
- const response = await client.getArtists()
- const artists = response.data.artists.map(get().mapArtistID3toArtist)
-
- set(
- produce(state => {
- state.starredArtists = reduceStarred(state.starredArtists, artists)
- }),
- )
-
- return artists
- } catch {
- return []
- }
- },
-
- fetchPlaylists: async () => {
- const client = get().client
- if (!client) {
- return []
- }
-
- try {
- const response = await client.getPlaylists()
- return response.data.playlists.map(get().mapPlaylistListItem)
- } catch {
- return []
- }
- },
-
- fetchAlbums: async (size = 500, offset = 0) => {
- const client = get().client
- if (!client) {
- return []
- }
-
- try {
- const filter = get().settings.screens.library.albums
-
- let params: GetAlbumList2Params
- switch (filter.type) {
- case 'byYear':
- params = {
- size,
- offset,
- type: filter.type,
- fromYear: filter.fromYear,
- toYear: filter.toYear,
- }
- break
- case 'byGenre':
- params = {
- size,
- offset,
- type: filter.type,
- genre: filter.genre,
- }
- break
- default:
- params = {
- size,
- offset,
- type: filter.type,
- }
- break
- }
-
- const response = await client.getAlbumList2(params)
- const albums = response.data.albums.map(get().mapAlbumID3toAlbumListItem)
-
- set(
- produce(state => {
- state.starredAlbums = reduceStarred(state.starredAlbums, albums)
- }),
- )
-
- return albums
- } catch {
- return []
- }
- },
-
- fetchSearchResults: async (query, type, size, offset) => {
- if (query.length < 2) {
- return { artists: [], albums: [], songs: [] }
- }
-
- const client = get().client
- if (!client) {
- return { artists: [], albums: [], songs: [] }
- }
-
- try {
- const params: Search3Params = { query }
- if (type === 'album') {
- params.albumCount = size
- params.albumOffset = offset
- } else if (type === 'artist') {
- params.artistCount = size
- params.artistOffset = offset
- } else if (type === 'song') {
- params.songCount = size
- params.songOffset = offset
- } else {
- params.albumCount = 5
- params.artistCount = 5
- params.songCount = 5
- }
-
- const response = await client.search3(params)
-
- const artists = response.data.artists.map(get().mapArtistID3toArtist)
- const albums = response.data.albums.map(get().mapAlbumID3toAlbumListItem)
- const songs = await get().mapChildrenToSongs(response.data.songs)
-
- set(
- produce(state => {
- state.starredSongs = reduceStarred(state.starredSongs, songs)
- state.starredArtists = reduceStarred(state.starredArtists, artists)
- state.starredAlbums = reduceStarred(state.starredAlbums, albums)
- }),
- )
-
- return { artists, albums, songs }
- } catch {
- return { artists: [], albums: [], songs: [] }
- }
- },
-
starredSongs: {},
starredAlbums: {},
starredArtists: {},
diff --git a/index.js b/index.js
index e54027b..cf705bd 100644
--- a/index.js
+++ b/index.js
@@ -6,6 +6,12 @@ enableScreens()
import { LogBox } from 'react-native'
LogBox.ignoreLogs(["The action 'POP_TO_TOP'"])
+LogBox.ignoreLogs([
+ '`new NativeEventEmitter()` was called with a non-null argument without the required `addListener` method.',
+])
+LogBox.ignoreLogs([
+ '`new NativeEventEmitter()` was called with a non-null argument without the required `removeListeners` method.',
+])
import { AppRegistry } from 'react-native'
import App from '@app/App'