diff --git a/server/src/server/router/api/v1/games/_game/_playtype/charts/router.ts b/server/src/server/router/api/v1/games/_game/_playtype/charts/router.ts index 080cafa25..fe57a18c1 100644 --- a/server/src/server/router/api/v1/games/_game/_playtype/charts/router.ts +++ b/server/src/server/router/api/v1/games/_game/_playtype/charts/router.ts @@ -22,39 +22,29 @@ router.get("/", async (req, res) => { let songIDs = undefined; - let songs; - if (IsString(req.query.search)) { - songs = await SearchGameSongs(game, req.query.search, 100); + const songs = await SearchGameSongs(game, req.query.search, 100); songIDs = songs.map((e) => e.id); } const skip = 0; const limit = 100; - let charts; + const charts = await FindChartsOnPopularity( + game, + playtype, + songIDs, + skip, + limit, + "personal-bests" + ); - if (IsString(req.query.search)) { - charts = await db.charts[game].find({ - songID: { $in: songIDs }, - }); - } else { - charts = await FindChartsOnPopularity( - game, - playtype, - songIDs, - skip, - limit, - "personal-bests" - ); - - // @optimisable - // could use songIDs from above instead of refetching - // but this is not very expensive. - songs = await db.songs[game].find({ - id: { $in: charts.map((e) => e.songID) }, - }); - } + // @optimisable + // could use songIDs from above instead of refetching + // but this is not very expensive. + const songs = await db.songs[game].find({ + id: { $in: charts.map((e) => e.songID) }, + }); return res.status(200).json({ success: true, diff --git a/server/src/utils/queries/charts.ts b/server/src/utils/queries/charts.ts index 7d5802af7..0e39fedf0 100644 --- a/server/src/utils/queries/charts.ts +++ b/server/src/utils/queries/charts.ts @@ -278,11 +278,13 @@ export async function FindChartsOnPopularity( // magnitude faster. // Not entirely sure why, but $lookup is incredibly inefficient, // and you should just avoid it. - const chartSet = await db.charts[game].find(matchQuery, { projection: { chartID: 1 } }); + const charts = (await db.charts[game].find(matchQuery)) as unknown as (ChartDocument & { + __playcount: integer; + })[]; const scoreCounts = (await db[scoreCollection].aggregate([ { - $match: { chartID: { $in: chartSet.map((e) => e.chartID) } }, + $match: { chartID: { $in: charts.map((e) => e.chartID) } }, }, { $group: { @@ -303,10 +305,6 @@ export async function FindChartsOnPopularity( }, ])) as { _id: string; count: integer }[]; - const charts = (await db.charts[game].find({ - chartID: { $in: scoreCounts.map((e) => e._id) }, - })) as unknown as (ChartDocument & { __playcount: integer })[]; - const scoreCountMap = new Map(); for (const sc of scoreCounts) { @@ -314,8 +312,8 @@ export async function FindChartsOnPopularity( } for (const chart of charts) { - chart.__playcount = scoreCountMap.get(chart.chartID); + chart.__playcount = scoreCountMap.get(chart.chartID) ?? 0; } - return charts.sort((a, b) => b.__playcount - a.__playcount); + return charts.sort((a, b) => b.__playcount - a.__playcount).slice(skip, skip + limit); }