mirror of
https://github.com/4gray/iptvnator.git
synced 2026-10-15 21:56:18 -08:00
fix(tmdb): resolve confirmed review findings — matching correctness, race guards, cache schema
Fixes the confirmed findings from the PR #1123 code review: - Stalker search: setSelectedContentType now runs BEFORE setSelectedItem, so the TMDB enrichment gate in the selection hook no longer sees the content type of the previously open tab (wrong/no enrichment after ITV -> search -> movie). - Title normalization is now two-tier (normalizeTitleKeys): the exact normalized form keeps a trailing year, the base form strips it and remembers the tag. Year stripping is anchored to the end of the title ("2001: A Space Odyssey" keeps its year) and language-prefix stripping is UPPERCASE-only ("It: Chapter Two" is no longer amputated). - All catalog matching (similar rail, actor pages, DB worker DB_MATCH_TITLES) compares exact forms first and only accepts year-stripped matches when the stripped tag is year-compatible (+-1) with the TMDB year — "Blade Runner" (1982) can no longer claim a catalog "Blade Runner 2049". CatalogTitleMatch carries the stripped trailingYear so the renderer can apply the guard to worker matches. - mergedBackdrops tolerates a plain-string backdrop_path; enrichment merge+patch blocks are wrapped in try/catch so a malformed provider payload can no longer become an unhandled rejection. - loadGlobalMatches (both actor routes) guards against actor->actor navigation races — a slow match for the previous person no longer overwrites the current one's results. - tmdb_metadata media_type CHECK widened to ('movie','tv','person') and person rows now use the honest 'person' type (TmdbCacheMediaType). Pre-release dev DBs with the narrow CHECK are rebuilt in place — the table is a pure cache, so the migration is a self-healing drop-and-recreate keyed off sqlite_master. Docs updated (tmdb-metadata-enrichment.md, CLAUDE.md). New regression coverage: title-normalization.util.spec.ts, two-tier cases in tmdb-similar.util.spec.ts and title-match.operations.spec.ts. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
aa92a3b826
commit
ac3a4e91f3
25 files changed
+545
-124
No files matched your search
@@ -112,7 +112,12 @@ trailer (official trailer > trailer > teaser, merged into
|
||||
`youtube_trailer` / `tmdb_trailer`); recommendations power the "Similar"
|
||||
rail. In Xtream detail views the rail shows only recommendations that
|
||||
match the provider catalog by normalized title
|
||||
(`libs/portal/xtream/feature/src/lib/tmdb-similar.util.ts`) and navigates
|
||||
(`libs/portal/xtream/feature/src/lib/tmdb-similar.util.ts`). Matching is
|
||||
two-tier (`normalizeTitleKeys`): exact normalized titles compare first
|
||||
(a trailing year in a TMDB title is part of the title — "Blade Runner
|
||||
2049"); the provider's year-stripped form only counts when its stripped
|
||||
year tag is compatible (±1) with the TMDB year, so "Blade Runner" (1982)
|
||||
never claims a catalog "Blade Runner 2049". The rail navigates
|
||||
to the matched item — the detail components re-initialize on route param
|
||||
changes (reactive `routeParams` signal) because the router reuses the
|
||||
component for detail→detail navigation. Stalker gets trailers and the
|
||||
@@ -150,8 +155,7 @@ Cast chips carry the TMDB person id (`tmdbPersonId` on
|
||||
`TmdbEnrichedCastMember`) and navigate to `actor/:personId` inside the
|
||||
current portal. The page loads `/person/{id}?append_to_response=
|
||||
combined_credits` via `TmdbEnrichmentService.getPersonDetails` (cached
|
||||
under `person:{id}`; the table's media_type CHECK only allows movie/tv, so
|
||||
person rows reuse `movie` as a namespace) and renders the shared
|
||||
under `person:{id}` with media_type `person`) and renders the shared
|
||||
`ActorViewComponent` (`libs/ui/shared-portals`).
|
||||
|
||||
Filmography has two scopes:
|
||||
@@ -166,7 +170,7 @@ Filmography has two scopes:
|
||||
`DB_MATCH_TITLES` worker request runs a trigram-FTS lookup per title
|
||||
over ALL imported Xtream playlists
|
||||
(`operations/title-match.operations.ts`), confirming candidates with
|
||||
the same normalized-title equality the renderer uses
|
||||
the same two-tier normalized-title matching the renderer uses
|
||||
(`normalizeTitle` now lives in `@iptvnator/shared/interfaces` so the
|
||||
worker and the renderer share it). Matches carry the playlist name
|
||||
(shown in the badge) and navigate into that playlist's detail view.
|
||||
@@ -179,9 +183,10 @@ Single table with two row kinds discriminated by `lookup_key` prefix:
|
||||
|
||||
```
|
||||
tmdb_metadata (
|
||||
media_type 'movie' | 'tv',
|
||||
media_type 'movie' | 'tv' | 'person',
|
||||
lookup_key 'id:<tmdbId>' -- details payload row
|
||||
'title:<normalized>|year:<y>' -- search resolution row
|
||||
'person:<personId>' -- person payload row
|
||||
language TEXT, -- TMDB language code
|
||||
tmdb_id INTEGER, -- NULL on a search row = negative cache
|
||||
payload TEXT, -- raw JSON details, NULL for search rows
|
||||
|
||||
Reference in new issue
Block a user