mirror of
https://github.com/unshackle-dl/unshackle.git
synced 2026-11-12 20:15:10 +00:00
fix(services): match service aliases without case
Uppercase entries in ALIASES never resolved, because get_tag lowercased the input but not the alias. Match real tags first so a service's own tag cannot be taken by another service's alias.
This commit is contained in:
@@ -95,13 +95,13 @@ Declared at class level to configure framework behaviour:
|
||||
|
||||
| Variable | Type | Purpose |
|
||||
|---|---|---|
|
||||
| `ALIASES` | `tuple[str, ...]` | Extra tags that resolve to this service (e.g. `("EX", "DOMAIN")`). Default `()`. |
|
||||
| `GEOFENCE` | `tuple[str, ...]` | IP region codes the service requires. Empty = no geofence. The **first** entry is treated as the main region for auto-proxy. |
|
||||
| `ALIASES` | `tuple[str, ...]` | Extra tags that resolve to this service (e.g. `("EX", "DOMAIN")`). Case does not matter. Default `()`. |
|
||||
| `GEOFENCE` | `tuple[str, ...]` | IP region codes the service requires. Empty = no geofence. unshackle treats the **first** entry as the main region for auto-proxy. |
|
||||
| `VAULT_TAG` | `Optional[str]` | Overrides the key-vault namespace so sibling services can share one vault. Default `None` (use the service's own tag). |
|
||||
| `AUTH_METHODS` | `Optional[tuple[str, ...]]` | Auth methods accepted (`"cookies"` / `"credentials"`). When `None`, the REST `/services` endpoint infers them from `authenticate()`. |
|
||||
| `NO_SUBTITLES` | `bool` | Set `True` on a service with no subtitle tracks to skip subtitle handling entirely. |
|
||||
| `ANIME` | `bool` | Set `True` when the catalogue is anime, so metadata lookups prefer AniList. A title's own `anime` flag overrides it. |
|
||||
| `DAILY` | `bool` | Set `True` when the catalogue is daily/date-based (talk shows, news, sports), so episodes are named by air date. A title's own `daily` flag overrides it. |
|
||||
| `DAILY` | `bool` | Set `True` when the catalogue is daily/date-based (talk shows, news, sports), so unshackle names episodes by air date. A title's own `daily` flag overrides it. |
|
||||
|
||||
!!! note "`NO_SUBTITLES` is a convention, not a base-class attribute"
|
||||
`dl.py` uses `hasattr` to find `NO_SUBTITLES`, and the `Service` base class
|
||||
|
||||
@@ -61,12 +61,12 @@ Declared at the top of your service class, these are static descriptors:
|
||||
|
||||
| Class variable | Type | Purpose |
|
||||
|---|---|---|
|
||||
| `ALIASES` | `tuple[str, ...]` | Alternate tags the service answers to (resolved by `Services.get_tag`). |
|
||||
| `GEOFENCE` | `tuple[str, ...]` | ISO region codes the service requires; empty means no geofence. The first entry is treated as the "main region" for automatic proxy selection. |
|
||||
| `ALIASES` | `tuple[str, ...]` | Alternate tags the service answers to, in any case (resolved by `Services.get_tag`). |
|
||||
| `GEOFENCE` | `tuple[str, ...]` | ISO region codes the service requires; empty means no geofence. unshackle treats the first entry as the "main region" for automatic proxy selection. |
|
||||
| `VAULT_TAG` | `Optional[str]` | Overrides the key-vault namespace; defaults to the service's own tag. |
|
||||
| `AUTH_METHODS` | `Optional[tuple[str, ...]]` | Accepted auth methods (`"cookies"` / `"credentials"`). When `None`, the REST `/services` endpoint infers them from `authenticate()`. |
|
||||
| `ANIME` | `bool` | The catalogue is anime, so metadata lookups prefer AniList. A title's own `anime` flag overrides it. |
|
||||
| `DAILY` | `bool` | The catalogue is daily/date-based, so episodes are named by air date. A title's own `daily` flag overrides it. |
|
||||
| `DAILY` | `bool` | The catalogue is daily/date-based, so unshackle names episodes by air date. A title's own `daily` flag overrides it. |
|
||||
|
||||
### Required methods
|
||||
|
||||
@@ -141,7 +141,7 @@ families, one per media kind:
|
||||
All items subclass `Title`, which carries the shared identity: a **unique `id`**, the
|
||||
originating `service` class, an optional original `language`, arbitrary `data`, and a
|
||||
freshly-constructed `self.tracks = Tracks()` that `get_tracks` will fill. Collections
|
||||
are sorted lists, so titles stay in a stable order.
|
||||
use sorted lists, so titles stay in a stable order.
|
||||
|
||||
!!! warning "The unique ID is validated"
|
||||
`Title.__init__` rejects a falsy `id_`, and rejects any ID shorter than 4 characters
|
||||
@@ -330,7 +330,7 @@ in `unshackle.core.manifests`. Each parser has the same three-part contract:
|
||||
### The parser contract
|
||||
|
||||
1. **Construct**: `DASH.from_url(url, session=...)` or `DASH.from_text(text, url)`
|
||||
(and likewise for `HLS` / `ISM`). A `url` is always required, even for `from_text`,
|
||||
(and likewise for `HLS` / `ISM`). Always pass a `url`, even to `from_text`,
|
||||
because the parser needs it to make relative segment paths absolute.
|
||||
2. **`to_tracks(...)`**: parses the manifest into a `Tracks` container of `Video`,
|
||||
`Audio`, and `Subtitle` objects, each carrying descriptor-specific state.
|
||||
|
||||
Reference in New Issue
Block a user