Previously, forced subtitles were incorrectly included when they matched
languages in the lang configuration, even without the --forced-subs flag.
This caused forced subs to appear when using language configs or the -l
parameter, which violated the expected behavior.
Fixes#24
When attaching fonts for ASS/SSA subtitles, the Attachment class was being
called with positional arguments instead of keyword arguments. This caused
the font Path object to be incorrectly interpreted, leading to an error:
"Invalid URL 'Arial (arial)': No scheme supplied."
Changed Attachment(font, name) to Attachment(path=font, name=name) to
explicitly pass arguments by keyword, ensuring proper parameter handling.
Revert the warnings filter added in 2d5e807 as it didn't work as expected to suppress the tinycss SyntaxWarning. Also fix isort order in prd.py for pyplayready imports.
New --exact-lang CLI flag that enables exact language code matching instead of fuzzy matching. This allows users to get specific regional variants without matching all related variants.
Examples:
- `-l es-419` normally matches all Spanish (es-ES, es-419, es-MX)
- `-l es-419 --exact-lang` matches ONLY es-419 (Latin American Spanish)
Fixes language detection issue where specific variants like es-419 (Latin American Spanish) would match all Spanish variants instead of just close regional variants.
Add --no-mux command-line option to allow downloading individual track
files without muxing them into a container file (.mkv/.mka/.mks).
This addresses use cases where users want to download tracks separately,
such as:
- Downloading only subtitles as individual .srt/.vtt files
- Keeping audio/video/subtitle tracks as separate files
- Converting subtitle formats without creating container files
When --no-mux is used:
- Tracks are saved as individual files with descriptive suffixes
- Video tracks: filename.{codec}.ext
- Audio tracks: filename.{language}.{codec}.ext
- Subtitle tracks: filename.{language}.forced.sdh.ext (as applicable)
- Folder structure respects --no-folder flag
Resolves#21
- Add pysubs2 as default conversion method for 'auto' mode
- Add support for MicroDVD (.sub), MPL2 (.mpl2), and TMP (.tmp) formats
- Implement convert_with_pysubs2() method with fallback to standard conversion
- Update from_mime() to handle new subtitle format types
- Map all supported formats to pysubs2 format identifiers
- Update docstrings to reflect new capabilities
Move warnings.filterwarnings() to the very top of __main__.py before any
other imports to ensure it takes effect before tinycss is loaded during
module discovery. This fixes the SyntaxWarning from the unmaintained
tinycss package (a dependency of subby).
refs #20
- Upgrade pyplayready from >=0.6.0 to >=0.6.3
- Upgrade subby to 0.3.23 (commit 5a925c36) for lxml 6.x compatibility
- Upgrade lxml from 5.4.0 to 6.0.2
- Fix pyplayready exception imports to use root-level imports (compatible with both 0.6.0 and 0.6.3)
- Suppress SyntaxWarning from unmaintained tinycss dependency
The pyplayready package changed its API between versions:
- v0.6.0: exceptions in pyplayready.exceptions module
- v0.6.3: exceptions in pyplayready.misc.exceptions module
Using root-level imports (from pyplayready import ...) works with both versions.
ref #20
- Update lxml dependency to allow version 6.x (required by subby 0.3.23)
- Fix pyplayready exception import path (moved to misc.exceptions in 0.6.3)
fixes#17
Add new session utility with curl_cffi support for anti-bot protection
Update all manifest parsers (DASH, HLS, ISM, M3U8) to accept curl_cffi sessions
Add browser impersonation support (Chrome, Firefox, Safari)
Fix cookie handling compatibility between requests and curl_cffi
Suppress HTTPS proxy warnings for better UX
Maintain full backward compatibility with requests.Session
Creates a copy of the CDM dictionary before modification to prevent the original configuration from being mutated, allowing the same CDM to be selected multiple times within a session without errors.
Implements dynamic CDM selection based on video track resolution to optimize
CDM usage. Automatically selects appropriate security level (L3/SL2K for ≤1080p, L1/SL3K for >1080p) based on content requirements.
Key Features:
- Quality-based CDM configuration with threshold operators (>=, >, <=, <)
- Pre-selection based on highest quality across all video tracks
- Maintains backward compatibility with existing CDM configurations
- Single CDM per session to avoid inefficient switching
- Fix 'NoneType' object is not iterable error in decrypt_labs_remote_cdm
- Fix vault count display showing 0/3 instead of actual successful vault count
- Add intelligent embedded audio language detection at mux stage
- Automatically set audio language metadata when no separate audio tracks exist
- Respect user flags (-V, --no-audio) to avoid unnecessary processing
- Smart video track selection based on title language with fallbacks
- Improved default track selection to prioritize title language matches
- Enhanced FFmpeg repackaging with audio stream metadata injection
- Works automatically for all services without service-specific code
Fixed DecryptLabsRemoteCDM sending 'generic' instead of proper service names and added case-insensitive vault lookups for SQLite/MySQL vaults. Also added local vault integration to DecryptLabsRemoteCDM
- Added DRM system detection method to distinguish Widevine and PlayReady CDMs
- Implemented create_drm method to instantiate appropriate DRM objects based on system
- Updated track hydration to add all tracks on first profile/range, only videos otherwise
- Changed get_playready_license to reuse Widevine license retrieval method
- Replaced direct Widevine instantiations with create_drm calls for DRM object creation
- Added conditional debug logs for unavailable audio and subtitle tracks when hydrating
- Cleaned up DRM imports and type annotations for drm_system attribute in Netflix class
- Replace silent log of error with raising an exception
- Ensure errors in MSL response messages do not go unnoticed
- Prevent continuation on critical MSL response errors
- Improve error handling robustness in MSL class
- Update version from 1.4.4 to 1.4.5 in core/__init__.py
- Add comprehensive changelog entry for v1.4.5 with all changes since 1.4.4
- Include enhanced CDM support, caching improvements, and bug fixes
- Add support for processing multiple video ranges in parallel
- Handle HYBRID range by fetching HDR10 and DV profiles separately
- Introduce get_profiles_for_range method to retrieve profiles for given range
- Refactor profile fetching logic with detailed logging and error handling
- Validate all requested video ranges are supported by the current codec
- Allow H.264 codec only with SDR range and enforce checks for multiple ranges
- Improve track hydration logic to avoid duplicates across ranges and profiles
- Add logging for multi-range processing and profile fetching details
- Updated HTTP request timeout from 1 to 3 seconds in get_ip_info function
- Improved reliability of external IP info retrieval by allowing longer response time
- Import HTTPAdapter from requests.adapters
- Configure session adapters for http and https with max_retries=3
- Add timeout of 1 second to the get request in get_ip_info
- Ensure retries and timeout improve request reliability and responsiveness
- Always send get_cached_keys_if_exists=True for L1/L2 devices to leverage
- the API's automatic caching optimization. This reduces unnecessary license
- requests by prioritizing cached keys for these security levels.
- Use default Widevine common privacy certificate when no service certificate is provided for L1 devices
- Add get_widevine_service_certificate method to EXAMPLE service for config-based certificates
- Improve certificate handling with more descriptive return messages
Remove decrypt_labs_session_id and challenge from session when cached keys exist but there are missing kids, ensuring clean state for subsequent requests.
Remove decrypt_labs_session_id and challenge from session when cached keys exist but there are missing kids, ensuring clean state for subsequent requests.