diff --git a/src/core/music/utils.ts b/src/core/music/utils.ts index c3703af..31c87b0 100644 --- a/src/core/music/utils.ts +++ b/src/core/music/utils.ts @@ -8,6 +8,7 @@ import { import { langS2T, toNewMusicInfo, toOldMusicInfo } from '@/utils' import { assertApiSupport } from '@/utils/tools' import settingState from '@/store/setting/state' +import { requestMsg } from '@/utils/message' const getOtherSourcePromises = new Map() @@ -184,6 +185,7 @@ export const getOnlineOtherSourceMusicUrl = async({ musicInfos, quality, onToggl return { musicInfo, url, quality: type, isFromCache: false } // eslint-disable-next-line @typescript-eslint/promise-function-async }).catch((err: any) => { + if (err.message == requestMsg.tooManyRequests) throw err console.log(err) return getOnlineOtherSourceMusicUrl({ musicInfos, quality, onToggleSource, isRefresh, retryedSource }) }) @@ -217,7 +219,7 @@ export const handleGetOnlineMusicUrl = async({ musicInfo, quality, onToggleSourc return { musicInfo, url, quality: type, isFromCache: false } }).catch(async(err: any) => { console.log(err) - if (!allowToggleSource) throw err + if (!allowToggleSource || err.message == requestMsg.tooManyRequests) throw err onToggleSource() // eslint-disable-next-line @typescript-eslint/promise-function-async return await getOtherSource(musicInfo).then(otherSource => { diff --git a/src/core/player/player.ts b/src/core/player/player.ts index f95850c..23062a5 100644 --- a/src/core/player/player.ts +++ b/src/core/player/player.ts @@ -60,12 +60,36 @@ const { addDelayNextTimeout: addLoadTimeout, clearDelayNextTimeout: clearLoadTim * 检查音乐信息是否已更改 */ const diffCurrentMusicInfo = (curMusicInfo: LX.Music.MusicInfo | LX.Download.ListItem): boolean => { - return curMusicInfo !== playerState.playMusicInfo.musicInfo || playerState.isPlay + // return curMusicInfo !== playerState.playMusicInfo.musicInfo || playerState.isPlay + return curMusicInfo.id != global.lx.gettingUrlId || curMusicInfo.id != playerState.playMusicInfo.musicInfo?.id || playerState.isPlay } +let cancelDelayRetry: (() => void) | null = null +const delayRetry = async(musicInfo: LX.Music.MusicInfo | LX.Download.ListItem, isRefresh = false): Promise => { + // if (cancelDelayRetry) cancelDelayRetry() + return new Promise((resolve, reject) => { + const time = getRandom(2, 6) + setStatusText(global.i18n.t('player__geting_url_delay_retry', { time })) + const tiemout = setTimeout(() => { + getMusicPlayUrl(musicInfo, isRefresh, true).then((result) => { + cancelDelayRetry = null + resolve(result) + }).catch(async(err: any) => { + cancelDelayRetry = null + reject(err) + }) + }, time * 1000) + cancelDelayRetry = () => { + clearTimeout(tiemout) + cancelDelayRetry = null + resolve(null) + } + }) +} const getMusicPlayUrl = async(musicInfo: LX.Music.MusicInfo | LX.Download.ListItem, isRefresh = false, isRetryed = false): Promise => { // this.musicInfo.url = await getMusicPlayUrl(targetSong, type) setStatusText(global.i18n.t('player__geting_url')) + addLoadTimeout() // const type = getPlayType(settingState.setting['player.isPlayHighQuality'], musicInfo) @@ -86,6 +110,8 @@ const getMusicPlayUrl = async(musicInfo: LX.Music.MusicInfo | LX.Download.ListIt diffCurrentMusicInfo(musicInfo) || err.message == requestMsg.cancelRequest) return null + if (err.message == requestMsg.tooManyRequests) return delayRetry(musicInfo, isRefresh) + if (!isRetryed) return getMusicPlayUrl(musicInfo, isRefresh, true) throw err @@ -93,7 +119,9 @@ const getMusicPlayUrl = async(musicInfo: LX.Music.MusicInfo | LX.Download.ListIt } export const setMusicUrl = (musicInfo: LX.Music.MusicInfo | LX.Download.ListItem, isRefresh?: boolean) => { - addLoadTimeout() + // addLoadTimeout() + if (!diffCurrentMusicInfo(musicInfo)) return + if (cancelDelayRetry) cancelDelayRetry() global.lx.gettingUrlId = musicInfo.id void getMusicPlayUrl(musicInfo, isRefresh).then((url) => { if (!url) return @@ -171,8 +199,7 @@ const handlePlay = async() => { const playMusicInfo = playerState.playMusicInfo const musicInfo = playMusicInfo.musicInfo - if (!musicInfo || global.lx.gettingUrlId == musicInfo.id) return - global.lx.gettingUrlId &&= '' + if (!musicInfo) return await setStop() global.app_event.pause() diff --git a/src/lang/en_us.json b/src/lang/en_us.json index df6a786..813f9a7 100644 --- a/src/lang/en_us.json +++ b/src/lang/en_us.json @@ -129,6 +129,7 @@ "player__end": "finished playing", "player__error": "Audio loading error, switch to next track after 5 seconds", "player__geting_url": "Acquiring the song link...", + "player__geting_url_delay_retry": "The server is busy, try again in {time} seconds...", "player__loading": "Music loading...", "player__refresh_url": "The URL has expired, refreshing the URL...", "quality_high_quality": "HQ", @@ -270,8 +271,8 @@ "setting_sync_history_empty": "Nothing here", "setting_sync_history_title": "Connection history", "setting_sync_host_label": "Synchronization service address", - "setting_sync_host_value_tip": "http://IP:Port", "setting_sync_host_value_error_tip": "The address needs to start with http:// or https://!", + "setting_sync_host_value_tip": "http://IP:Port", "setting_sync_port_label": "Synchronization service port number", "setting_sync_port_tip": "Please enter the synchronization service port number", "setting_sync_status": "Status: {status}", diff --git a/src/lang/zh_cn.json b/src/lang/zh_cn.json index f6b4568..6b0df94 100644 --- a/src/lang/zh_cn.json +++ b/src/lang/zh_cn.json @@ -129,6 +129,7 @@ "player__end": "播放完毕", "player__error": "音频加载出错,5 秒后切换下一首", "player__geting_url": "歌曲链接获取中...", + "player__geting_url_delay_retry": "服务器繁忙,{time}秒后重试...", "player__loading": "音乐加载中...", "player__refresh_url": "URL过期,正在刷新URL...", "quality_high_quality": "HQ", @@ -270,8 +271,8 @@ "setting_sync_history_empty": "这里啥也没有😮", "setting_sync_history_title": "连接历史", "setting_sync_host_label": "同步服务地址", - "setting_sync_host_value_tip": "http://IP地址:端口号", "setting_sync_host_value_error_tip": "地址需要以 http:// 或者 https:// 开头!", + "setting_sync_host_value_tip": "http://IP地址:端口号", "setting_sync_port_label": "同步服务端口号", "setting_sync_port_tip": "请输入同步服务端口号", "setting_sync_status": "状态:{status}", diff --git a/src/screens/SonglistDetail/listAction.ts b/src/screens/SonglistDetail/listAction.ts index 6b1c57e..dfb8d8b 100644 --- a/src/screens/SonglistDetail/listAction.ts +++ b/src/screens/SonglistDetail/listAction.ts @@ -7,17 +7,19 @@ import syncSourceList from '@/core/syncSourceList' import { confirmDialog, toast } from '@/utils/tools' import { type Source } from '@/store/songlist/state' +const getListId = (id: string, source: LX.OnlineSource) => `${source}__${id}` -export const handlePlay = async(listId: string, source: Source, list?: LX.Music.MusicInfoOnline[], index = 0) => { +export const handlePlay = async(id: string, source: Source, list?: LX.Music.MusicInfoOnline[], index = 0) => { + const listId = getListId(id, source) let isPlayingList = false // console.log(list) - if (!list?.length) list = (await getListDetail(listId, source, 1)).list + if (!list?.length) list = (await getListDetail(id, source, 1)).list if (list?.length) { await setTempList(listId, [...list]) void playList(LIST_IDS.TEMP, index) isPlayingList = true } - const fullList = await getListDetailAll(source, listId) + const fullList = await getListDetailAll(source, id) if (!fullList.length) return if (isPlayingList) { if (listState.tempListMeta.id == listId) { @@ -29,7 +31,9 @@ export const handlePlay = async(listId: string, source: Source, list?: LX.Music. } } -export const handleCollect = async(listId: string, source: Source, name: string) => { +export const handleCollect = async(id: string, source: Source, name: string) => { + const listId = getListId(id, source) + const targetList = listState.userList.find(l => l.id == listId) if (targetList) { const confirm = await confirmDialog({ @@ -42,13 +46,13 @@ export const handleCollect = async(listId: string, source: Source, name: string) return } - const list = await getListDetailAll(source, listId) + const list = await getListDetailAll(source, id) await createList({ name, id: listId, list, source, - sourceListId: listId, + sourceListId: id, }) toast(global.i18n.t('collect_success')) } diff --git a/src/utils/message.ts b/src/utils/message.ts index f1d15b8..6dec705 100644 --- a/src/utils/message.ts +++ b/src/utils/message.ts @@ -5,4 +5,5 @@ export const requestMsg = { // unachievable: '哦No😱...接口无法访问了!已帮你切换到临时接口,重试下看能不能播放吧~', notConnectNetwork: '无法连接到服务器', cancelRequest: '取消http请求', + tooManyRequests: '服务器繁忙', } as const diff --git a/src/utils/musicSdk/bd/api-test.js b/src/utils/musicSdk/bd/api-test.js index ceffc28..370328d 100644 --- a/src/utils/musicSdk/bd/api-test.js +++ b/src/utils/musicSdk/bd/api-test.js @@ -10,8 +10,12 @@ const api_test = { headers, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(requestMsg.fail)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(requestMsg.fail)) + } }) return requestObj }, diff --git a/src/utils/musicSdk/kg/api-test.js b/src/utils/musicSdk/kg/api-test.js index b5f96d3..9557aa6 100644 --- a/src/utils/musicSdk/kg/api-test.js +++ b/src/utils/musicSdk/kg/api-test.js @@ -10,8 +10,12 @@ const api_test = { headers, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(requestMsg.fail)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(requestMsg.fail)) + } }) return requestObj }, diff --git a/src/utils/musicSdk/kw/api-temp.js b/src/utils/musicSdk/kw/api-temp.js index 2f7948e..1f0f4bd 100644 --- a/src/utils/musicSdk/kw/api-temp.js +++ b/src/utils/musicSdk/kw/api-temp.js @@ -1,4 +1,5 @@ import { httpFetch } from '../../request' +import { requestMsg } from '../../message' import { headers, timeout } from '../options' const api_temp = { @@ -9,8 +10,12 @@ const api_temp = { timeout, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(body.msg)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(body.msg)) + } }) return requestObj }, diff --git a/src/utils/musicSdk/kw/api-test.js b/src/utils/musicSdk/kw/api-test.js index 7b49fca..5890f6d 100644 --- a/src/utils/musicSdk/kw/api-test.js +++ b/src/utils/musicSdk/kw/api-test.js @@ -21,8 +21,12 @@ const api_test = { headers, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(requestMsg.fail)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(requestMsg.fail)) + } }) return requestObj }, diff --git a/src/utils/musicSdk/mg/api-test.js b/src/utils/musicSdk/mg/api-test.js index 30199d0..9ec644b 100644 --- a/src/utils/musicSdk/mg/api-test.js +++ b/src/utils/musicSdk/mg/api-test.js @@ -10,8 +10,12 @@ const api_test = { headers, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(requestMsg.fail)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(requestMsg.fail)) + } }) return requestObj }, diff --git a/src/utils/musicSdk/tx/api-test.js b/src/utils/musicSdk/tx/api-test.js index 8d09441..d275eac 100644 --- a/src/utils/musicSdk/tx/api-test.js +++ b/src/utils/musicSdk/tx/api-test.js @@ -10,8 +10,12 @@ const api_messoer = { headers, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(requestMsg.fail)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(requestMsg.fail)) + } }) return requestObj }, diff --git a/src/utils/musicSdk/wy/api-test.js b/src/utils/musicSdk/wy/api-test.js index 3190c8c..b345272 100644 --- a/src/utils/musicSdk/wy/api-test.js +++ b/src/utils/musicSdk/wy/api-test.js @@ -10,8 +10,12 @@ const api_test = { headers, family: 4, }) - requestObj.promise = requestObj.promise.then(({ body }) => { - return body.code === 0 ? Promise.resolve({ type, url: body.data }) : Promise.reject(new Error(requestMsg.fail)) + requestObj.promise = requestObj.promise.then(({ statusCode, body }) => { + if (statusCode == 429) return Promise.reject(new Error(requestMsg.tooManyRequests)) + switch (body.code) { + case 0: return Promise.resolve({ type, url: body.data }) + default: return Promise.reject(new Error(requestMsg.fail)) + } }) return requestObj },