Skip to content

Added sports history view and sports library view - #3526

Draft
Sportarr wants to merge 11 commits into
morpheus65535:sportarrfrom
Sportarr:sportarr-frontend-views
Draft

Added sports history view and sports library view#3526
Sportarr wants to merge 11 commits into
morpheus65535:sportarrfrom
Sportarr:sportarr-frontend-views

Conversation

@Sportarr

@Sportarr Sportarr commented Aug 13, 2026

Copy link
Copy Markdown

Finishes the operational views. History gains a Sports tab beside Episodes and Movies, and a Sports section joins Series and Movies in the sidebar, listing the leagues with their languages profile and how many of their files still want subtitles.
image

image

Both count per playable file rather than per event, because a row is one part. A card with prelims and a main card wants subtitles for both.

Two deliberate omissions

The history table has no upgradable column. Subtitle upgrades have no sports path yet, so the flag would always read false, and a column that is always empty is worse than no column.

The league list has no poster mode. Sportarr serves its artwork as complete URLs from its own host rather than through the Bazarr image proxy, so a poster card needs its own handling and is better done separately than smuggled in here.

Not in this one

The league detail view, showing the events inside a league. It needs per event subtitle actions, which means manual search, download, upload and delete endpoints that do not exist yet. Those belong together in their own change.

Testing

Ran against a live instance with a two part event synced from a Sportarr built from current source.

  • The library lists the league with its sport, profile and file progress, and the sidebar carries the Sportarr stream state
  • History lists both parts of the event with their part names, languages, real scores and dates, and the blacklist action is offered per row
  • check:ts, check, check:fmt, check:style and build all pass, and the 501 frontend tests pass

Depends on

The settings and views PR, and the API endpoints PR behind it.

I used an AI coding assistant while building this, modeled closely on your existing Sonarr integration. I directed the design, reviewed every line, and tested it against a live Bazarr instance with real data. I can explain any part of it.

@morpheus65535 morpheus65535 added the PR on Standby PR waiting an action before it get merged. label Aug 15, 2026
@Sportarr
Sportarr force-pushed the sportarr-frontend-views branch from 1c326aa to ad8ba67 Compare August 18, 2026 02:47
Mirrors store_subtitles for sports events so embedded and external
subtitles are found and stored per playable file, then computes the
missing subtitles for each one against the league's language profile.

A row is one part, so a fight card's prelims and main card each get
their own subtitles rather than sharing a set.

parse_video_metadata gains a sports_event_id parameter. Sportarr file
IDs and Sonarr episode file IDs are unrelated sequences, so caching the
sports ffprobe result under episode_file_id would write over an
unrelated episode's cache. The sports cache goes to its own table.

Indexing runs when the events sync inserts a row, and again when the
file id or the path changes. Sportarr gives a new file id when it
replaces a file, and an upgrade can keep the same path, so the id is
what proves the media changed.

The full scan task uses the sportarr.full_update settings that already
exist but had nothing reading them.
Gives sports events the same wanted list and search that series and movies
already have. An event with missing subtitles is picked up by a scheduled
search, or by a search for one league, and the result is stored, logged to
history, and reported back to Sportarr.

A sports event is scored as an episode. Sportarr gives it a season and an
episode number, and get_video already builds it as an episode, so the
episode scores and the episode minimum score apply to it unchanged. The
post-processing threshold follows the same reasoning.

Sportarr has no per event notify endpoint, so a downloaded subtitle asks it
to rescan the league folder, which is the documented way to tell it a file
changed.

Two tables come with this. Sports history is separate from series history
because a sports event id is not an episode id, and the sports blacklist has
to be its own list so blocking a bad subtitle for an event does not touch an
episode.

Changes:
- Schema: table_history_sports and table_blacklist_sports, with a migration
- sportarr/history.py, sportarr/blacklist.py, sportarr/notify.py
- pool.py: pick the blacklist by media type instead of a two way branch
- download.py, processing.py, utils.py: a sports branch beside series and
  movies
- get_exclusion_clause: sports tags, monitored state and excluded sports
- subtitles/wanted/sports.py and subtitles/mass_download/sports.py
- scheduler: search for missing sports events subtitles
Exposes the sports data the previous PRs build, so a UI has something to
read and act on. Five namespaces under sports, matching the shape of the
episodes and series ones.

Leagues lists the library with a file count and a missing count, sets the
languages profile, and runs the scan, search and sync actions. Events lists
one row per playable file, ordered by part so the prelims stay above the
main card. Wanted, history and blacklist mirror their episode equivalents.

The badges endpoint gains a sports count and the Sportarr stream state,
next to the existing Sonarr and Radarr ones.

Blacklisting a sports subtitle deletes it and searches again, so
delete_subtitles gets a sports branch. Sports events carry no media server
ids, so there is nothing to refresh in Plex or Jellyfin. The league rescan
covers Sportarr.

History has no upgradable flag. Subtitle upgrades have no sports path yet,
and a flag that always reads false is worse than no flag.

Changes:
- api/sports: leagues, events, wanted, history, blacklist
- api/badges: sports wanted count and the Sportarr stream state
- subtitles/tools/delete.py: sports branch
postprocess builds an image proxy URL by putting the Bazarr base URL in
front of whatever the item holds. Sonarr and Radarr give a path, so that is
correct for them. Sportarr gives a complete URL, and the prefix produced
/images/serieshttps://..., which no client can load.

Leave an image alone when it already carries a scheme.
Mirrors the series/tags endpoint so the sports library view can feed its tags filter from the full set of tags in use, the same way the series and movies views do after the mass selection rework.
Puts the sports work behind a UI. Until now the Sportarr connection could
only be configured by editing the config file, and nothing in the app showed
sports events at all.

Settings gains a Sportarr page next to Sonarr and Radarr, with the same host
fields, a connection test, the exclusion and monitoring options, and path
mappings. Path mappings need a file browser that reads the Sportarr file
system, so that endpoint comes with it.

Wanted and Blacklist gain a Sports tab. Both list one row per playable file
and name the part, because a fight card's prelims and main card are separate
files with separate subtitles and an event title alone does not tell them
apart.

The sidebar badge shows the count of wanted sports subtitles, and the
Sportarr section carries the event stream state the way Sonarr and Radarr
carry their SignalR state. A Sportarr only install now lands on the sports
wanted list rather than the settings page, since it has no series or movies
library to open.

Changes:
- Settings/Sportarr page, and sportarr support in the path mapper, the file
  browser and the URL test button
- api/files/files_sportarr.py and sportarr/filesystem.py for the browser
- Wanted/Sports and Blacklist/Sports views
- apis/raw/sports.ts and apis/hooks/sports.ts
- Types for sports leagues, events, wanted, blacklist and history
- Routes, badges and the redirector
…s hook

The mass selection rework made ItemView ask for a tags source and an on demand all items fetch. The sports hooks now provide both, shaped exactly like the series hooks the view already consumes.
Finishes the operational views. History gains a Sports tab beside Episodes
and Movies, and a Sports section joins Series and Movies in the sidebar,
listing the leagues with their languages profile and how many of their files
still want subtitles.

Both count per playable file rather than per event, because a row is one
part. A card with prelims and a main card wants subtitles for both.

The history table has no upgradable column. Subtitle upgrades have no sports
path yet, so the flag would always read false.

The league list has no poster mode. Sportarr serves its artwork as complete
URLs from its own host rather than through the Bazarr image proxy, and a
poster card for that is worth doing on its own rather than inside this.

Changes:
- pages/History/Sports for the history table
- pages/Sports for the leagues library
- Routes, the sidebar section and its stream badge
ItemView now requires an on demand all items fetch and the modify mutation, and a tags source when the tags filter is enabled. The sports library view passes all three, matching how the series and movies views consume the reworked component.
@Sportarr
Sportarr force-pushed the sportarr-frontend-views branch from ad8ba67 to 7cb837f Compare August 25, 2026 21:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

PR on Standby PR waiting an action before it get merged.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants