Skip to content

feat: get precise music title via bilibili API#68

Merged
roitium merged 2 commits into
devfrom
feat/more-precise-lyric-fetch
Oct 27, 2025
Merged

feat: get precise music title via bilibili API#68
roitium merged 2 commits into
devfrom
feat/more-precise-lyric-fetch

Conversation

@roitium
Copy link
Copy Markdown
Collaborator

@roitium roitium commented Oct 27, 2025

Closes #67

Summary by CodeRabbit

  • New Features
    • Added option to clear all saved lyrics from the developer page
    • Implemented precise lyrics search utilizing Bilibili video background music recognition results

@roitium roitium added this to BBPlayer Oct 27, 2025
@roitium roitium added the enhancement New feature or request label Oct 27, 2025
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Oct 27, 2025

Walkthrough

The changes implement a feature to fetch precise music metadata from Bilibili videos using their BGM recognition API, then use this metadata for more accurate lyric searching. New API and query endpoints are added, the lyric service is enhanced with bilibili-specific orchestration, and a UI button enables cache clearing.

Changes

Cohort / File(s) Summary
Changelog
CHANGELOG.md
Added UNRELEASED section documenting two new features: cache clearing and bilibili BGM-based lyric search.
Bilibili API & Types
src/lib/api/bilibili/api.ts, src/types/apis/bilibili.ts
Added new API method getWebPlayerInfo() to fetch web player data including BGM metadata; introduced BilibiliWebPlayerInfo type with optional bgm_info containing music ID, title, and jump URL.
Query Hooks
src/hooks/queries/bilibili/video.ts
Added new query hook useGetWebPlayerInfo() with corresponding query key generator; enabled fetching when both bvid and cid are available, with 5-minute stale time.
Lyric Service
src/lib/services/lyricService.ts
Extended getBestMatchedLyrics() to accept optional preciseKeyword parameter; added getPreciseMusicNameOnBilibiliVideo() to extract music name from bilibili metadata; added clearAllLyrics() to wipe cache; integrated bilibili-specific flow in smartFetchLyrics() to fetch and use precise music names for searching.
Test UI
src/app/test/test.tsx
Added new button "清空所有歌词缓存" triggering clearAllLyrcis() function; function wraps lyricService.clearAllLyrics() with confirmation dialog and toast notifications.

Sequence Diagram

sequenceDiagram
    participant UI as Test Page
    participant Service as LyricService
    participant API as BilibiliAPI
    participant FS as File System

    rect rgb(230, 245, 255)
    Note over UI,FS: Bilibili BGM-based Lyric Search Flow
    UI->>Service: smartFetchLyrics(bilibiliTrack)
    alt track has bvid & cid
        Service->>API: getWebPlayerInfo(bvid, cid)
        API-->>Service: BilibiliWebPlayerInfo
        Service->>Service: getPreciseMusicNameOnBilibiliVideo(bgm_info)
        Service->>Service: getBestMatchedLyrics(track, preciseName)
        Service->>FS: Fetch lyrics with precise keyword
        FS-->>Service: Lyrics data
        Service->>FS: Write results to cache
    else fallback
        Service->>Service: getBestMatchedLyrics(track)
    end
    Service-->>UI: Lyrics result
    end

    rect rgb(255, 240, 245)
    Note over UI,FS: Clear Cache Flow
    UI->>Service: clearAllLyrics()
    Service->>FS: Remove all cache entries
    FS-->>Service: Success/Failure
    Service-->>UI: Result with toast
    end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

  • src/lib/services/lyricService.ts – Requires careful review of the new async logic, bilibili-specific orchestration in smartFetchLyrics(), error handling for metadata extraction, and the contract of the modified getBestMatchedLyrics() signature
  • src/lib/api/bilibili/api.ts – Verify the endpoint path /x/player/wbi/v2 and return type handling
  • Type safety – Ensure optional chaining and null checks are properly applied in bilibili metadata access paths

Poem

🐰 With BGM from videos bright,
📚 We find the lyrics just right!
🎵 Bilibili's music ID,
✨ Makes searching less of a riddle,
🗑️ And a button to clean the cache—
Clear, precise, and in a flash!

Pre-merge checks and finishing touches

❌ Failed checks (2 warnings)
Check name Status Explanation Resolution
Out of Scope Changes Check ⚠️ Warning The PR includes an out-of-scope feature not requested in issue #67: the clearAllLyrics() method in lyricService and the corresponding UI button on the test page to clear all lyric cache. While issue #67 specifically requests using Bilibili BGM metadata for more accurate lyric searches, the cache clearing functionality is an additional feature introduced in this PR. Although cache management may be a useful supporting feature, it falls outside the stated requirements of the linked issue. Consider either removing the cache clearing functionality or creating a separate PR/issue to track it. If the cache clearing is intentionally bundled as a companion feature, clarify this in the PR description and ensure it aligns with the project's PR scope policy. Alternatively, open a new issue to formally request this feature and link it to this PR.
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The PR title "feat: get precise music title via bilibili API" is clear, concise, and directly reflects the primary objective of the changeset. It accurately describes the main change—fetching precise music information via the Bilibili API to improve lyric search accuracy. The title is specific enough that a teammate reviewing the git history would understand the core purpose, and it aligns well with the linked issue #67 requirements.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feat/more-precise-lyric-fetch

Comment @coderabbitai help to get the list of available commands and usage tips.

@roitium roitium moved this to In review in BBPlayer Oct 27, 2025
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

🧹 Nitpick comments (8)
CHANGELOG.md (1)

8-14: Polish: Keep-a-Changelog casing and acronym

  • Prefer "Unreleased" (canonical casing).
  • Uppercase the acronym “BGM”.

Apply:

-## [UNRELEASED]
+## [Unreleased]
@@
-- 基于 B 站视频 bgm 识别结果精准搜索歌词
+- 基于 B 站视频 BGM 识别结果精准搜索歌词
src/types/apis/bilibili.ts (1)

346-352: Type safety: allow null and document shape

  • bgm_info can be absent or null; reflect that in the type.
  • Please verify whether the client unwraps data so that bgm_info is indeed top-level here.

Apply:

-interface BilibiliWebPlayerInfo {
-	bgm_info?: {
+interface BilibiliWebPlayerInfo {
+	bgm_info?: ({
 		music_id: number
 		music_title: string
 		jump_url: string
-	}
+	} | null)
 }

To confirm the response shape, please check the endpoint’s latest payload (fields and nesting) as Bilibili responses often differ between app/web variants.

Also applies to: 375-376

src/app/test/test.tsx (1)

116-142: Typo: rename clearAllLyrcis → clearAllLyrics for consistency

Keeps naming aligned with lyricService.clearAllLyrics() and avoids confusion.

- const clearAllLyrcis = () => {
+ const clearAllLyrics = () => {
@@
-					onPress: clearAction,
+					onPress: clearAction,
@@
-						onPress={clearAllLyrcis}
+						onPress={clearAllLyrics}

Also applies to: 188-195

src/lib/api/bilibili/api.ts (1)

752-769: New API looks good; consider cancellation support and verify payload

  • Implementation aligns with existing WBI calls. LGTM.
  • Optional: accept an AbortSignal to enable query cancellation, similar to getSearchSuggestions.
  • Please verify that /x/player/wbi/v2 returns the exact shape modeled by BilibiliWebPlayerInfo (esp. bgm_info nesting).
src/hooks/queries/bilibili/video.ts (1)

58-73: Return just what callers need via select

If consumers only care about the song metadata, select it here to minimize rerenders and downstream null checks.

 return useQuery({
   queryKey: videoDataQueryKeys.getWebPlayerInfo(bvid, cid),
   queryFn: () =>
     returnOrThrowAsync(bilibiliApi.getWebPlayerInfo(bvid!, cid!)),
   enabled,
   staleTime: 5 * 60 * 1000,
+  select: (data) => data.bgm_info ?? null,
 })
src/lib/services/lyricService.ts (3)

96-111: Bilibili-first branch looks sound; minor simplification

You can drop fromSafePromise here since getPreciseMusicNameOnBilibiliVideo never throws and always resolves to string | undefined.

- return ResultAsync.fromSafePromise(
-   this.getPreciseMusicNameOnBilibiliVideo(track.bilibiliMetadata),
- )
+ return ResultAsync.fromPromise(
+   this.getPreciseMusicNameOnBilibiliVideo(track.bilibiliMetadata),
+   (e) => e as Error,
+ )

212-233: Reuse cleanKeyword for normalization and guard against missing title

Simpler and more robust than a single-pattern regex.

- .andThen((res) => {
-   if (!res.bgm_info) return errAsync(new Error('没有获取到歌曲信息'))
-   const filteredResult = /《(.+?)》/.exec(res.bgm_info.music_title)
-   logger.debug('从 bilibili 获取到的该视频中识别到的歌曲名', {
-     music_title: res.bgm_info.music_title,
-   })
-   if (filteredResult?.[1]) {
-     return okAsync(filteredResult[1])
-   }
-   return okAsync(res.bgm_info.music_title)
- })
+ .andThen((res) => {
+   const title = res.bgm_info?.music_title
+   if (!title) return errAsync(new Error('没有获取到歌曲信息'))
+   logger.debug('从 bilibili 获取到的该视频中识别到的歌曲名', { music_title: title })
+   return okAsync(this.cleanKeyword(title))
+ })

235-258: clearAllLyrics: behavior is fine; optional telemetry

Consider emitting a metric (count of files removed) to aid support.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between d70647f and 14270f3.

📒 Files selected for processing (6)
  • CHANGELOG.md (1 hunks)
  • src/app/test/test.tsx (3 hunks)
  • src/hooks/queries/bilibili/video.ts (2 hunks)
  • src/lib/api/bilibili/api.ts (2 hunks)
  • src/lib/services/lyricService.ts (4 hunks)
  • src/types/apis/bilibili.ts (2 hunks)
🧰 Additional context used
🧬 Code graph analysis (4)
src/app/test/test.tsx (1)
src/components/modals/AlertModal.tsx (1)
  • alert (72-85)
src/hooks/queries/bilibili/video.ts (2)
src/utils/neverthrow-utils.ts (1)
  • returnOrThrowAsync (8-21)
src/lib/api/bilibili/api.ts (1)
  • bilibiliApi (772-772)
src/lib/api/bilibili/api.ts (3)
src/types/apis/bilibili.ts (1)
  • BilibiliWebPlayerInfo (375-375)
src/lib/api/bilibili/wbi.ts (1)
  • getWbiEncodedParams (123-128)
src/lib/api/bilibili/client.ts (1)
  • bilibiliApiClient (145-145)
src/lib/services/lyricService.ts (2)
src/types/core/media.ts (2)
  • Track (63-63)
  • BilibiliTrack (38-54)
src/lib/api/bilibili/api.ts (1)
  • bilibiliApi (772-772)
🔇 Additional comments (1)
src/lib/services/lyricService.ts (1)

41-53: Optional parameter is backward-compatible; random selection is a known pre-existing issue

Both callers work correctly:

  • Line 104: Passes musicName from bilibili metadata extraction
  • Line 112: Omits second argument, using default behavior

Random selection at lines 56-57 (with FIXME comment) is pre-existing, not introduced in this change. Flag for follow-up refactor to truly implement "best matched" semantics rather than random selection.

@roitium roitium merged commit 4269662 into dev Oct 27, 2025
3 checks passed
@github-project-automation github-project-automation Bot moved this from In review to Done in BBPlayer Oct 27, 2025
@roitium roitium deleted the feat/more-precise-lyric-fetch branch October 27, 2025 13:58
@coderabbitai coderabbitai Bot mentioned this pull request Jan 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

[Feature] 基于 BiliBili BGM 识别结果搜索歌词

1 participant