diff --git a/projects/website/src/common/beatsaver-utils.ts b/projects/website/src/common/beatsaver-utils.ts new file mode 100644 index 0000000..93ff8c6 --- /dev/null +++ b/projects/website/src/common/beatsaver-utils.ts @@ -0,0 +1,37 @@ +import BeatSaverMap from "@/common/database/types/beatsaver-map"; +import { db } from "@/common/database/database"; +import { beatsaverService } from "@ssr/common/service/impl/beatsaver"; + +/** + * Gets the map that match the query. + * + * @param query the query to search for + * @returns the map that match the query, or undefined if no map were found + */ +export async function lookupBeatSaverMap(query: string): Promise { + let map = await db.beatSaverMaps.get(query); + // The map is cached + if (map != undefined) { + return map; + } + + const response = await beatsaverService.lookupMap(query); + // Map not found + if (response == undefined) { + return undefined; + } + + const bsr = response.id; + if (bsr == undefined) { + return undefined; + } + + // Save map the the db + await db.beatSaverMaps.add({ + hash: query, + bsr: bsr, + fullData: response, + }); + map = await db.beatSaverMaps.get(query); + return map; +} diff --git a/projects/website/src/components/leaderboard/leaderboard-data.tsx b/projects/website/src/components/leaderboard/leaderboard-data.tsx index 921cd5c..22460a4 100644 --- a/projects/website/src/components/leaderboard/leaderboard-data.tsx +++ b/projects/website/src/components/leaderboard/leaderboard-data.tsx @@ -3,11 +3,12 @@ import LeaderboardScores from "@/components/leaderboard/leaderboard-scores"; import { LeaderboardInfo } from "@/components/leaderboard/leaderboard-info"; import { useQuery } from "@tanstack/react-query"; -import { useEffect, useState } from "react"; +import { useCallback, useEffect, useState } from "react"; import BeatSaverMap from "@/common/database/types/beatsaver-map"; import ScoreSaberLeaderboardScoresPageToken from "@ssr/common/types/token/scoresaber/score-saber-leaderboard-scores-page-token"; import ScoreSaberLeaderboardToken from "@ssr/common/types/token/scoresaber/score-saber-leaderboard-token"; import { scoresaberService } from "@ssr/common/service/impl/scoresaber"; +import { lookupBeatSaverMap } from "@/common/beatsaver-utils"; type LeaderboardDataProps = { /** @@ -38,15 +39,14 @@ export function LeaderboardData({ initialPage, initialScores, initialLeaderboard staleTime: 30 * 1000, // Cache data for 30 seconds }); - // todo: fix - // const fetchBeatSaverData = useCallback(async () => { - // const beatSaverMap = await beatsaverService.lookupMap(initialLeaderboard.songHash); - // setBeatSaverMap(beatSaverMap); - // }, [initialLeaderboard.songHash]); - // - // useEffect(() => { - // fetchBeatSaverData(); - // }, [fetchBeatSaverData]); + const fetchBeatSaverData = useCallback(async () => { + const beatSaverMap = await lookupBeatSaverMap(initialLeaderboard.songHash); + setBeatSaverMap(beatSaverMap); + }, [initialLeaderboard.songHash]); + + useEffect(() => { + fetchBeatSaverData(); + }, [fetchBeatSaverData]); /** * When the leaderboard changes, update the previous and current leaderboards. diff --git a/projects/website/src/components/score/score.tsx b/projects/website/src/components/score/score.tsx index ec2ed9e..d1096b6 100644 --- a/projects/website/src/components/score/score.tsx +++ b/projects/website/src/components/score/score.tsx @@ -2,7 +2,7 @@ import BeatSaverMap from "@/common/database/types/beatsaver-map"; import LeaderboardScores from "@/components/leaderboard/leaderboard-scores"; -import { useState } from "react"; +import { useCallback, useEffect, useState } from "react"; import ScoreButtons from "./score-buttons"; import ScoreSongInfo from "./score-info"; import ScoreRankInfo from "./score-rank-info"; @@ -10,6 +10,7 @@ import ScoreStats from "./score-stats"; import { motion } from "framer-motion"; import ScoreSaberPlayer from "@ssr/common/types/player/impl/scoresaber-player"; import ScoreSaberPlayerScoreToken from "@ssr/common/types/token/scoresaber/score-saber-player-score-token"; +import { lookupBeatSaverMap } from "@/common/beatsaver-utils"; type Props = { /** @@ -28,15 +29,14 @@ export default function Score({ player, playerScore }: Props) { const [beatSaverMap, setBeatSaverMap] = useState(); const [isLeaderboardExpanded, setIsLeaderboardExpanded] = useState(false); - // todo: fix - // const fetchBeatSaverData = useCallback(async () => { - // const beatSaverMap = await beatsaverService.lookupMap(leaderboard.songHash); - // setBeatSaverMap(beatSaverMap); - // }, [leaderboard.songHash]); - // - // useEffect(() => { - // fetchBeatSaverData(); - // }, [fetchBeatSaverData]); + const fetchBeatSaverData = useCallback(async () => { + const beatSaverMap = await lookupBeatSaverMap(leaderboard.songHash); + setBeatSaverMap(beatSaverMap); + }, [leaderboard.songHash]); + + useEffect(() => { + fetchBeatSaverData(); + }, [fetchBeatSaverData]); const page = Math.floor(score.rank / 12) + 1; return (