2023-06-08 03:40:34 -07:00
|
|
|
import {
|
|
|
|
|
InternetProviderLyricResponse,
|
|
|
|
|
InternetProviderLyricSearchResponse,
|
|
|
|
|
LyricSearchQuery,
|
|
|
|
|
QueueSong,
|
|
|
|
|
} from '/@/renderer/api/types';
|
|
|
|
|
import { query as queryGenius, getSearchResults as searchGenius } from './genius';
|
|
|
|
|
import { query as queryNetease, getSearchResults as searchNetease } from './netease';
|
2023-05-28 14:31:49 -07:00
|
|
|
import { LyricSource } from '../../../../renderer/types';
|
|
|
|
|
import { ipcMain } from 'electron';
|
|
|
|
|
import { store } from '../settings/index';
|
|
|
|
|
|
2023-06-08 03:40:34 -07:00
|
|
|
type SongFetcher = (params: LyricSearchQuery) => Promise<InternetProviderLyricResponse | null>;
|
|
|
|
|
type SearchFetcher = (
|
|
|
|
|
params: LyricSearchQuery,
|
|
|
|
|
) => Promise<InternetProviderLyricSearchResponse[] | null>;
|
2023-06-04 23:15:36 -07:00
|
|
|
|
|
|
|
|
type CachedLyrics = Record<LyricSource, InternetProviderLyricResponse>;
|
2023-05-28 14:31:49 -07:00
|
|
|
|
|
|
|
|
const FETCHERS: Record<LyricSource, SongFetcher> = {
|
|
|
|
|
[LyricSource.GENIUS]: queryGenius,
|
|
|
|
|
[LyricSource.NETEASE]: queryNetease,
|
|
|
|
|
};
|
|
|
|
|
|
2023-06-08 03:40:34 -07:00
|
|
|
const SEARCH_FETCHERS: Record<LyricSource, SearchFetcher> = {
|
|
|
|
|
[LyricSource.GENIUS]: searchGenius,
|
|
|
|
|
[LyricSource.NETEASE]: searchNetease,
|
|
|
|
|
};
|
|
|
|
|
|
2023-06-04 23:15:36 -07:00
|
|
|
const MAX_CACHED_ITEMS = 10;
|
|
|
|
|
|
|
|
|
|
const lyricCache = new Map<string, CachedLyrics>();
|
|
|
|
|
|
2023-06-05 02:45:27 -07:00
|
|
|
const getRemoteLyrics = async (song: QueueSong) => {
|
2023-05-28 14:31:49 -07:00
|
|
|
const sources = store.get('lyrics', []) as LyricSource[];
|
|
|
|
|
|
2023-06-04 23:15:36 -07:00
|
|
|
const cached = lyricCache.get(song.id);
|
|
|
|
|
|
|
|
|
|
if (cached) {
|
|
|
|
|
for (const source of sources) {
|
|
|
|
|
const data = cached[source];
|
2023-06-05 02:45:27 -07:00
|
|
|
if (data) return data;
|
2023-06-04 23:15:36 -07:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2023-06-05 02:45:27 -07:00
|
|
|
let lyricsFromSource = null;
|
|
|
|
|
|
2023-05-28 14:31:49 -07:00
|
|
|
for (const source of sources) {
|
2023-06-08 03:40:34 -07:00
|
|
|
const params = { artist: song.artistName, name: song.name };
|
|
|
|
|
const response = await FETCHERS[source](params);
|
|
|
|
|
|
2023-06-05 02:45:27 -07:00
|
|
|
if (response) {
|
2023-06-04 23:15:36 -07:00
|
|
|
const newResult = cached
|
|
|
|
|
? {
|
|
|
|
|
...cached,
|
2023-06-05 02:45:27 -07:00
|
|
|
[source]: response,
|
2023-06-04 23:15:36 -07:00
|
|
|
}
|
2023-06-05 02:45:27 -07:00
|
|
|
: ({ [source]: response } as CachedLyrics);
|
2023-06-04 23:15:36 -07:00
|
|
|
|
|
|
|
|
if (lyricCache.size === MAX_CACHED_ITEMS && cached === undefined) {
|
|
|
|
|
const toRemove = lyricCache.keys().next().value;
|
|
|
|
|
lyricCache.delete(toRemove);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
lyricCache.set(song.id, newResult);
|
|
|
|
|
|
2023-06-05 02:45:27 -07:00
|
|
|
lyricsFromSource = response;
|
2023-05-28 14:31:49 -07:00
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
2023-06-05 02:45:27 -07:00
|
|
|
|
|
|
|
|
return lyricsFromSource;
|
|
|
|
|
};
|
|
|
|
|
|
2023-06-08 03:40:34 -07:00
|
|
|
const searchRemoteLyrics = async (params: LyricSearchQuery) => {
|
|
|
|
|
const sources = store.get('lyrics', []) as LyricSource[];
|
|
|
|
|
|
|
|
|
|
const results: Record<LyricSource, InternetProviderLyricSearchResponse[]> = {
|
|
|
|
|
[LyricSource.GENIUS]: [],
|
|
|
|
|
[LyricSource.NETEASE]: [],
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
for (const source of sources) {
|
|
|
|
|
const response = await SEARCH_FETCHERS[source](params);
|
|
|
|
|
|
|
|
|
|
if (response) {
|
|
|
|
|
response.forEach((result) => {
|
|
|
|
|
results[source].push(result);
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return results;
|
|
|
|
|
};
|
|
|
|
|
|
2023-06-05 02:45:27 -07:00
|
|
|
ipcMain.handle('lyric-fetch-manual', async (_event, song: QueueSong) => {
|
|
|
|
|
const lyric = await getRemoteLyrics(song);
|
|
|
|
|
return lyric;
|
2023-05-28 14:31:49 -07:00
|
|
|
});
|
2023-06-08 03:40:34 -07:00
|
|
|
|
|
|
|
|
ipcMain.handle('lyric-search', async (_event, params: LyricSearchQuery) => {
|
|
|
|
|
const lyricResults = await searchRemoteLyrics(params);
|
|
|
|
|
return lyricResults;
|
|
|
|
|
});
|