mirror of
https://github.com/ytdl-org/youtube-dl
synced 2025-01-01 00:50:09 +09:00
Compare commits
14 Commits
eae19a4473
...
755f186e21
Author | SHA1 | Date | |
---|---|---|---|
|
755f186e21 | ||
|
2240a1dc4d | ||
|
03d3af9768 | ||
|
5ce9527e16 | ||
|
c527f5ada0 | ||
|
ace52668f0 | ||
|
9c33eb027e | ||
|
679b711395 | ||
|
1727541315 | ||
|
45b0a0d11b | ||
|
e665fcd4da | ||
|
aae737d4af | ||
|
92a6de861e | ||
|
5ff881aee6 |
6
.github/ISSUE_TEMPLATE/1_broken_site.md
vendored
6
.github/ISSUE_TEMPLATE/1_broken_site.md
vendored
@ -18,7 +18,7 @@ title: ''
|
|||||||
|
|
||||||
<!--
|
<!--
|
||||||
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
||||||
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.12. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.14. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
||||||
- Make sure that all provided video/audio/playlist URLs (if any) are alive and playable in a browser.
|
- Make sure that all provided video/audio/playlist URLs (if any) are alive and playable in a browser.
|
||||||
- Make sure that all URLs and arguments with special characters are properly quoted or escaped as explained in http://yt-dl.org/escape.
|
- Make sure that all URLs and arguments with special characters are properly quoted or escaped as explained in http://yt-dl.org/escape.
|
||||||
- Search the bugtracker for similar issues: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
- Search the bugtracker for similar issues: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
||||||
@ -26,7 +26,7 @@ Carefully read and work through this check list in order to prevent the most com
|
|||||||
-->
|
-->
|
||||||
|
|
||||||
- [ ] I'm reporting a broken site support
|
- [ ] I'm reporting a broken site support
|
||||||
- [ ] I've verified that I'm running youtube-dl version **2020.12.12**
|
- [ ] I've verified that I'm running youtube-dl version **2020.12.14**
|
||||||
- [ ] I've checked that all provided URLs are alive and playable in a browser
|
- [ ] I've checked that all provided URLs are alive and playable in a browser
|
||||||
- [ ] I've checked that all URLs and arguments with special characters are properly quoted or escaped
|
- [ ] I've checked that all URLs and arguments with special characters are properly quoted or escaped
|
||||||
- [ ] I've searched the bugtracker for similar issues including closed ones
|
- [ ] I've searched the bugtracker for similar issues including closed ones
|
||||||
@ -41,7 +41,7 @@ Add the `-v` flag to your command line you run youtube-dl with (`youtube-dl -v <
|
|||||||
[debug] User config: []
|
[debug] User config: []
|
||||||
[debug] Command-line args: [u'-v', u'http://www.youtube.com/watch?v=BaW_jenozKcj']
|
[debug] Command-line args: [u'-v', u'http://www.youtube.com/watch?v=BaW_jenozKcj']
|
||||||
[debug] Encodings: locale cp1251, fs mbcs, out cp866, pref cp1251
|
[debug] Encodings: locale cp1251, fs mbcs, out cp866, pref cp1251
|
||||||
[debug] youtube-dl version 2020.12.12
|
[debug] youtube-dl version 2020.12.14
|
||||||
[debug] Python version 2.7.11 - Windows-2003Server-5.2.3790-SP2
|
[debug] Python version 2.7.11 - Windows-2003Server-5.2.3790-SP2
|
||||||
[debug] exe versions: ffmpeg N-75573-g1d0487f, ffprobe N-75573-g1d0487f, rtmpdump 2.4
|
[debug] exe versions: ffmpeg N-75573-g1d0487f, ffprobe N-75573-g1d0487f, rtmpdump 2.4
|
||||||
[debug] Proxy map: {}
|
[debug] Proxy map: {}
|
||||||
|
@ -19,7 +19,7 @@ labels: 'site-support-request'
|
|||||||
|
|
||||||
<!--
|
<!--
|
||||||
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
||||||
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.12. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.14. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
||||||
- Make sure that all provided video/audio/playlist URLs (if any) are alive and playable in a browser.
|
- Make sure that all provided video/audio/playlist URLs (if any) are alive and playable in a browser.
|
||||||
- Make sure that site you are requesting is not dedicated to copyright infringement, see https://yt-dl.org/copyright-infringement. youtube-dl does not support such sites. In order for site support request to be accepted all provided example URLs should not violate any copyrights.
|
- Make sure that site you are requesting is not dedicated to copyright infringement, see https://yt-dl.org/copyright-infringement. youtube-dl does not support such sites. In order for site support request to be accepted all provided example URLs should not violate any copyrights.
|
||||||
- Search the bugtracker for similar site support requests: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
- Search the bugtracker for similar site support requests: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
||||||
@ -27,7 +27,7 @@ Carefully read and work through this check list in order to prevent the most com
|
|||||||
-->
|
-->
|
||||||
|
|
||||||
- [ ] I'm reporting a new site support request
|
- [ ] I'm reporting a new site support request
|
||||||
- [ ] I've verified that I'm running youtube-dl version **2020.12.12**
|
- [ ] I've verified that I'm running youtube-dl version **2020.12.14**
|
||||||
- [ ] I've checked that all provided URLs are alive and playable in a browser
|
- [ ] I've checked that all provided URLs are alive and playable in a browser
|
||||||
- [ ] I've checked that none of provided URLs violate any copyrights
|
- [ ] I've checked that none of provided URLs violate any copyrights
|
||||||
- [ ] I've searched the bugtracker for similar site support requests including closed ones
|
- [ ] I've searched the bugtracker for similar site support requests including closed ones
|
||||||
|
@ -18,13 +18,13 @@ title: ''
|
|||||||
|
|
||||||
<!--
|
<!--
|
||||||
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
||||||
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.12. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.14. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
||||||
- Search the bugtracker for similar site feature requests: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
- Search the bugtracker for similar site feature requests: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
||||||
- Finally, put x into all relevant boxes (like this [x])
|
- Finally, put x into all relevant boxes (like this [x])
|
||||||
-->
|
-->
|
||||||
|
|
||||||
- [ ] I'm reporting a site feature request
|
- [ ] I'm reporting a site feature request
|
||||||
- [ ] I've verified that I'm running youtube-dl version **2020.12.12**
|
- [ ] I've verified that I'm running youtube-dl version **2020.12.14**
|
||||||
- [ ] I've searched the bugtracker for similar site feature requests including closed ones
|
- [ ] I've searched the bugtracker for similar site feature requests including closed ones
|
||||||
|
|
||||||
|
|
||||||
|
6
.github/ISSUE_TEMPLATE/4_bug_report.md
vendored
6
.github/ISSUE_TEMPLATE/4_bug_report.md
vendored
@ -18,7 +18,7 @@ title: ''
|
|||||||
|
|
||||||
<!--
|
<!--
|
||||||
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
||||||
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.12. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.14. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
||||||
- Make sure that all provided video/audio/playlist URLs (if any) are alive and playable in a browser.
|
- Make sure that all provided video/audio/playlist URLs (if any) are alive and playable in a browser.
|
||||||
- Make sure that all URLs and arguments with special characters are properly quoted or escaped as explained in http://yt-dl.org/escape.
|
- Make sure that all URLs and arguments with special characters are properly quoted or escaped as explained in http://yt-dl.org/escape.
|
||||||
- Search the bugtracker for similar issues: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
- Search the bugtracker for similar issues: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
||||||
@ -27,7 +27,7 @@ Carefully read and work through this check list in order to prevent the most com
|
|||||||
-->
|
-->
|
||||||
|
|
||||||
- [ ] I'm reporting a broken site support issue
|
- [ ] I'm reporting a broken site support issue
|
||||||
- [ ] I've verified that I'm running youtube-dl version **2020.12.12**
|
- [ ] I've verified that I'm running youtube-dl version **2020.12.14**
|
||||||
- [ ] I've checked that all provided URLs are alive and playable in a browser
|
- [ ] I've checked that all provided URLs are alive and playable in a browser
|
||||||
- [ ] I've checked that all URLs and arguments with special characters are properly quoted or escaped
|
- [ ] I've checked that all URLs and arguments with special characters are properly quoted or escaped
|
||||||
- [ ] I've searched the bugtracker for similar bug reports including closed ones
|
- [ ] I've searched the bugtracker for similar bug reports including closed ones
|
||||||
@ -43,7 +43,7 @@ Add the `-v` flag to your command line you run youtube-dl with (`youtube-dl -v <
|
|||||||
[debug] User config: []
|
[debug] User config: []
|
||||||
[debug] Command-line args: [u'-v', u'http://www.youtube.com/watch?v=BaW_jenozKcj']
|
[debug] Command-line args: [u'-v', u'http://www.youtube.com/watch?v=BaW_jenozKcj']
|
||||||
[debug] Encodings: locale cp1251, fs mbcs, out cp866, pref cp1251
|
[debug] Encodings: locale cp1251, fs mbcs, out cp866, pref cp1251
|
||||||
[debug] youtube-dl version 2020.12.12
|
[debug] youtube-dl version 2020.12.14
|
||||||
[debug] Python version 2.7.11 - Windows-2003Server-5.2.3790-SP2
|
[debug] Python version 2.7.11 - Windows-2003Server-5.2.3790-SP2
|
||||||
[debug] exe versions: ffmpeg N-75573-g1d0487f, ffprobe N-75573-g1d0487f, rtmpdump 2.4
|
[debug] exe versions: ffmpeg N-75573-g1d0487f, ffprobe N-75573-g1d0487f, rtmpdump 2.4
|
||||||
[debug] Proxy map: {}
|
[debug] Proxy map: {}
|
||||||
|
4
.github/ISSUE_TEMPLATE/5_feature_request.md
vendored
4
.github/ISSUE_TEMPLATE/5_feature_request.md
vendored
@ -19,13 +19,13 @@ labels: 'request'
|
|||||||
|
|
||||||
<!--
|
<!--
|
||||||
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
Carefully read and work through this check list in order to prevent the most common mistakes and misuse of youtube-dl:
|
||||||
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.12. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
- First of, make sure you are using the latest version of youtube-dl. Run `youtube-dl --version` and ensure your version is 2020.12.14. If it's not, see https://yt-dl.org/update on how to update. Issues with outdated version will be REJECTED.
|
||||||
- Search the bugtracker for similar feature requests: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
- Search the bugtracker for similar feature requests: http://yt-dl.org/search-issues. DO NOT post duplicates.
|
||||||
- Finally, put x into all relevant boxes (like this [x])
|
- Finally, put x into all relevant boxes (like this [x])
|
||||||
-->
|
-->
|
||||||
|
|
||||||
- [ ] I'm reporting a feature request
|
- [ ] I'm reporting a feature request
|
||||||
- [ ] I've verified that I'm running youtube-dl version **2020.12.12**
|
- [ ] I've verified that I'm running youtube-dl version **2020.12.14**
|
||||||
- [ ] I've searched the bugtracker for similar feature requests including closed ones
|
- [ ] I've searched the bugtracker for similar feature requests including closed ones
|
||||||
|
|
||||||
|
|
||||||
|
4
.github/PULL_REQUEST_TEMPLATE.md
vendored
4
.github/PULL_REQUEST_TEMPLATE.md
vendored
@ -7,8 +7,10 @@
|
|||||||
---
|
---
|
||||||
|
|
||||||
### Before submitting a *pull request* make sure you have:
|
### Before submitting a *pull request* make sure you have:
|
||||||
- [ ] At least skimmed through [adding new extractor tutorial](https://github.com/ytdl-org/youtube-dl#adding-support-for-a-new-site) and [youtube-dl coding conventions](https://github.com/ytdl-org/youtube-dl#youtube-dl-coding-conventions) sections
|
|
||||||
- [ ] [Searched](https://github.com/ytdl-org/youtube-dl/search?q=is%3Apr&type=Issues) the bugtracker for similar pull requests
|
- [ ] [Searched](https://github.com/ytdl-org/youtube-dl/search?q=is%3Apr&type=Issues) the bugtracker for similar pull requests
|
||||||
|
- [ ] Read [adding new extractor tutorial](https://github.com/ytdl-org/youtube-dl#adding-support-for-a-new-site)
|
||||||
|
- [ ] Read [youtube-dl coding conventions](https://github.com/ytdl-org/youtube-dl#youtube-dl-coding-conventions) and adjusted the code to meet them
|
||||||
|
- [ ] Covered the code with tests (note that PRs without tests will be REJECTED)
|
||||||
- [ ] Checked the code with [flake8](https://pypi.python.org/pypi/flake8)
|
- [ ] Checked the code with [flake8](https://pypi.python.org/pypi/flake8)
|
||||||
|
|
||||||
### In order to be accepted and merged into youtube-dl each piece of code must be in public domain or released under [Unlicense](http://unlicense.org/). Check one of the following options:
|
### In order to be accepted and merged into youtube-dl each piece of code must be in public domain or released under [Unlicense](http://unlicense.org/). Check one of the following options:
|
||||||
|
29
ChangeLog
29
ChangeLog
@ -1,3 +1,30 @@
|
|||||||
|
version 2020.12.14
|
||||||
|
|
||||||
|
Core
|
||||||
|
* [extractor/common] Improve JSON-LD interaction statistic extraction (#23306)
|
||||||
|
* [downloader/hls] Delegate manifests with media initialization to ffmpeg
|
||||||
|
+ [extractor/common] Document duration meta field for playlists
|
||||||
|
|
||||||
|
Extractors
|
||||||
|
* [mdr] Bypass geo restriction
|
||||||
|
* [mdr] Improve extraction (#24346, #26873)
|
||||||
|
* [yandexmusic:album] Improve album title extraction (#27418)
|
||||||
|
* [eporner] Fix view count extraction and make optional (#23306)
|
||||||
|
+ [eporner] Extend URL regular expression
|
||||||
|
* [eporner] Fix hash extraction and extend _VALID_URL (#27396)
|
||||||
|
* [slideslive] Use m3u8 entry protocol for m3u8 formats (#27400)
|
||||||
|
* [twitcasting] Fix format extraction and improve info extraction (#24868)
|
||||||
|
* [linuxacademy] Fix authentication and extraction (#21129, #26223, #27402)
|
||||||
|
* [itv] Clean description from HTML tags (#27399)
|
||||||
|
* [vlive] Sort live formats (#27404)
|
||||||
|
* [hotstart] Fix and improve extraction
|
||||||
|
* Fix format extraction (#26690)
|
||||||
|
+ Extract thumbnail URL (#16079, #20412)
|
||||||
|
+ Add support for country specific playlist URLs (#23496)
|
||||||
|
* Select the last id in video URL (#26412)
|
||||||
|
+ [youtube] Add some invidious instances (#27373)
|
||||||
|
|
||||||
|
|
||||||
version 2020.12.12
|
version 2020.12.12
|
||||||
|
|
||||||
Core
|
Core
|
||||||
@ -106,7 +133,7 @@ version 2020.12.02
|
|||||||
|
|
||||||
Extractors
|
Extractors
|
||||||
+ [tva] Add support for qub.ca (#27235)
|
+ [tva] Add support for qub.ca (#27235)
|
||||||
+ [toggle] Detect DRM protected videos (closes #16479)(closes #20805)
|
+ [toggle] Detect DRM protected videos (#16479, #20805)
|
||||||
+ [toggle] Add support for new MeWatch URLs (#27256)
|
+ [toggle] Add support for new MeWatch URLs (#27256)
|
||||||
* [youtube:tab] Extract channels only from channels tab (#27266)
|
* [youtube:tab] Extract channels only from channels tab (#27266)
|
||||||
+ [cspan] Extract info from jwplayer data (#3672, #3734, #10638, #13030,
|
+ [cspan] Extract info from jwplayer data (#3672, #3734, #10638, #13030,
|
||||||
|
@ -98,6 +98,55 @@ class TestInfoExtractor(unittest.TestCase):
|
|||||||
self.assertRaises(RegexNotFoundError, ie._html_search_meta, 'z', html, None, fatal=True)
|
self.assertRaises(RegexNotFoundError, ie._html_search_meta, 'z', html, None, fatal=True)
|
||||||
self.assertRaises(RegexNotFoundError, ie._html_search_meta, ('z', 'x'), html, None, fatal=True)
|
self.assertRaises(RegexNotFoundError, ie._html_search_meta, ('z', 'x'), html, None, fatal=True)
|
||||||
|
|
||||||
|
def test_search_json_ld_realworld(self):
|
||||||
|
# https://github.com/ytdl-org/youtube-dl/issues/23306
|
||||||
|
expect_dict(
|
||||||
|
self,
|
||||||
|
self.ie._search_json_ld(r'''<script type="application/ld+json">
|
||||||
|
{
|
||||||
|
"@context": "http://schema.org/",
|
||||||
|
"@type": "VideoObject",
|
||||||
|
"name": "1 On 1 With Kleio",
|
||||||
|
"url": "https://www.eporner.com/hd-porn/xN49A1cT3eB/1-On-1-With-Kleio/",
|
||||||
|
"duration": "PT0H12M23S",
|
||||||
|
"thumbnailUrl": ["https://static-eu-cdn.eporner.com/thumbs/static4/7/78/780/780814/9_360.jpg", "https://imggen.eporner.com/780814/1920/1080/9.jpg"],
|
||||||
|
"contentUrl": "https://gvideo.eporner.com/xN49A1cT3eB/xN49A1cT3eB.mp4",
|
||||||
|
"embedUrl": "https://www.eporner.com/embed/xN49A1cT3eB/1-On-1-With-Kleio/",
|
||||||
|
"image": "https://static-eu-cdn.eporner.com/thumbs/static4/7/78/780/780814/9_360.jpg",
|
||||||
|
"width": "1920",
|
||||||
|
"height": "1080",
|
||||||
|
"encodingFormat": "mp4",
|
||||||
|
"bitrate": "6617kbps",
|
||||||
|
"isFamilyFriendly": "False",
|
||||||
|
"description": "Kleio Valentien",
|
||||||
|
"uploadDate": "2015-12-05T21:24:35+01:00",
|
||||||
|
"interactionStatistic": {
|
||||||
|
"@type": "InteractionCounter",
|
||||||
|
"interactionType": { "@type": "http://schema.org/WatchAction" },
|
||||||
|
"userInteractionCount": 1120958
|
||||||
|
}, "aggregateRating": {
|
||||||
|
"@type": "AggregateRating",
|
||||||
|
"ratingValue": "88",
|
||||||
|
"ratingCount": "630",
|
||||||
|
"bestRating": "100",
|
||||||
|
"worstRating": "0"
|
||||||
|
}, "actor": [{
|
||||||
|
"@type": "Person",
|
||||||
|
"name": "Kleio Valentien",
|
||||||
|
"url": "https://www.eporner.com/pornstar/kleio-valentien/"
|
||||||
|
}]}
|
||||||
|
</script>''', None),
|
||||||
|
{
|
||||||
|
'title': '1 On 1 With Kleio',
|
||||||
|
'description': 'Kleio Valentien',
|
||||||
|
'url': 'https://gvideo.eporner.com/xN49A1cT3eB/xN49A1cT3eB.mp4',
|
||||||
|
'timestamp': 1449347075,
|
||||||
|
'duration': 743.0,
|
||||||
|
'view_count': 1120958,
|
||||||
|
'width': 1920,
|
||||||
|
'height': 1080,
|
||||||
|
})
|
||||||
|
|
||||||
def test_download_json(self):
|
def test_download_json(self):
|
||||||
uri = encode_data_uri(b'{"foo": "blah"}', 'application/json')
|
uri = encode_data_uri(b'{"foo": "blah"}', 'application/json')
|
||||||
self.assertEqual(self.ie._download_json(uri, None), {'foo': 'blah'})
|
self.assertEqual(self.ie._download_json(uri, None), {'foo': 'blah'})
|
||||||
|
@ -42,11 +42,13 @@ class HlsFD(FragmentFD):
|
|||||||
# no segments will definitely be appended to the end of the playlist.
|
# no segments will definitely be appended to the end of the playlist.
|
||||||
# r'#EXT-X-PLAYLIST-TYPE:EVENT', # media segments may be appended to the end of
|
# r'#EXT-X-PLAYLIST-TYPE:EVENT', # media segments may be appended to the end of
|
||||||
# # event media playlists [4]
|
# # event media playlists [4]
|
||||||
|
r'#EXT-X-MAP:', # media initialization [5]
|
||||||
|
|
||||||
# 1. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.2.4
|
# 1. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.2.4
|
||||||
# 2. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.2.2
|
# 2. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.2.2
|
||||||
# 3. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.3.2
|
# 3. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.3.2
|
||||||
# 4. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.3.5
|
# 4. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.3.5
|
||||||
|
# 5. https://tools.ietf.org/html/draft-pantos-http-live-streaming-17#section-4.3.2.5
|
||||||
)
|
)
|
||||||
check_results = [not re.search(feature, manifest) for feature in UNSUPPORTED_FEATURES]
|
check_results = [not re.search(feature, manifest) for feature in UNSUPPORTED_FEATURES]
|
||||||
is_aes128_enc = '#EXT-X-KEY:METHOD=AES-128' in manifest
|
is_aes128_enc = '#EXT-X-KEY:METHOD=AES-128' in manifest
|
||||||
|
@ -1237,8 +1237,16 @@ class InfoExtractor(object):
|
|||||||
'ViewAction': 'view',
|
'ViewAction': 'view',
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def extract_interaction_type(e):
|
||||||
|
interaction_type = e.get('interactionType')
|
||||||
|
if isinstance(interaction_type, dict):
|
||||||
|
interaction_type = interaction_type.get('@type')
|
||||||
|
return str_or_none(interaction_type)
|
||||||
|
|
||||||
def extract_interaction_statistic(e):
|
def extract_interaction_statistic(e):
|
||||||
interaction_statistic = e.get('interactionStatistic')
|
interaction_statistic = e.get('interactionStatistic')
|
||||||
|
if isinstance(interaction_statistic, dict):
|
||||||
|
interaction_statistic = [interaction_statistic]
|
||||||
if not isinstance(interaction_statistic, list):
|
if not isinstance(interaction_statistic, list):
|
||||||
return
|
return
|
||||||
for is_e in interaction_statistic:
|
for is_e in interaction_statistic:
|
||||||
@ -1246,8 +1254,8 @@ class InfoExtractor(object):
|
|||||||
continue
|
continue
|
||||||
if is_e.get('@type') != 'InteractionCounter':
|
if is_e.get('@type') != 'InteractionCounter':
|
||||||
continue
|
continue
|
||||||
interaction_type = is_e.get('interactionType')
|
interaction_type = extract_interaction_type(is_e)
|
||||||
if not isinstance(interaction_type, compat_str):
|
if not interaction_type:
|
||||||
continue
|
continue
|
||||||
# For interaction count some sites provide string instead of
|
# For interaction count some sites provide string instead of
|
||||||
# an integer (as per spec) with non digit characters (e.g. ",")
|
# an integer (as per spec) with non digit characters (e.g. ",")
|
||||||
|
@ -16,7 +16,7 @@ from ..utils import (
|
|||||||
|
|
||||||
|
|
||||||
class EpornerIE(InfoExtractor):
|
class EpornerIE(InfoExtractor):
|
||||||
_VALID_URL = r'https?://(?:www\.)?eporner\.com/(?:hd-porn|embed)/(?P<id>\w+)(?:/(?P<display_id>[\w-]+))?'
|
_VALID_URL = r'https?://(?:www\.)?eporner\.com/(?:(?:hd-porn|embed)/|video-)(?P<id>\w+)(?:/(?P<display_id>[\w-]+))?'
|
||||||
_TESTS = [{
|
_TESTS = [{
|
||||||
'url': 'http://www.eporner.com/hd-porn/95008/Infamous-Tiffany-Teen-Strip-Tease-Video/',
|
'url': 'http://www.eporner.com/hd-porn/95008/Infamous-Tiffany-Teen-Strip-Tease-Video/',
|
||||||
'md5': '39d486f046212d8e1b911c52ab4691f8',
|
'md5': '39d486f046212d8e1b911c52ab4691f8',
|
||||||
@ -43,7 +43,10 @@ class EpornerIE(InfoExtractor):
|
|||||||
'url': 'http://www.eporner.com/hd-porn/3YRUtzMcWn0',
|
'url': 'http://www.eporner.com/hd-porn/3YRUtzMcWn0',
|
||||||
'only_matching': True,
|
'only_matching': True,
|
||||||
}, {
|
}, {
|
||||||
'url': 'http://www.eporner.com/hd-porn/3YRUtzMcWn0',
|
'url': 'http://www.eporner.com/embed/3YRUtzMcWn0',
|
||||||
|
'only_matching': True,
|
||||||
|
}, {
|
||||||
|
'url': 'https://www.eporner.com/video-FJsA19J3Y3H/one-of-the-greats/',
|
||||||
'only_matching': True,
|
'only_matching': True,
|
||||||
}]
|
}]
|
||||||
|
|
||||||
@ -57,7 +60,7 @@ class EpornerIE(InfoExtractor):
|
|||||||
video_id = self._match_id(urlh.geturl())
|
video_id = self._match_id(urlh.geturl())
|
||||||
|
|
||||||
hash = self._search_regex(
|
hash = self._search_regex(
|
||||||
r'hash\s*:\s*["\']([\da-f]{32})', webpage, 'hash')
|
r'hash\s*[:=]\s*["\']([\da-f]{32})', webpage, 'hash')
|
||||||
|
|
||||||
title = self._og_search_title(webpage, default=None) or self._html_search_regex(
|
title = self._og_search_title(webpage, default=None) or self._html_search_regex(
|
||||||
r'<title>(.+?) - EPORNER', webpage, 'title')
|
r'<title>(.+?) - EPORNER', webpage, 'title')
|
||||||
@ -115,8 +118,8 @@ class EpornerIE(InfoExtractor):
|
|||||||
duration = parse_duration(self._html_search_meta(
|
duration = parse_duration(self._html_search_meta(
|
||||||
'duration', webpage, default=None))
|
'duration', webpage, default=None))
|
||||||
view_count = str_to_int(self._search_regex(
|
view_count = str_to_int(self._search_regex(
|
||||||
r'id="cinemaviews">\s*([0-9,]+)\s*<small>views',
|
r'id=["\']cinemaviews1["\'][^>]*>\s*([0-9,]+)',
|
||||||
webpage, 'view count', fatal=False))
|
webpage, 'view count', default=None))
|
||||||
|
|
||||||
return merge_dicts(json_ld, {
|
return merge_dicts(json_ld, {
|
||||||
'id': video_id,
|
'id': video_id,
|
||||||
|
@ -2,12 +2,16 @@
|
|||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
|
|
||||||
from .common import InfoExtractor
|
from .common import InfoExtractor
|
||||||
from ..compat import compat_urlparse
|
from ..compat import (
|
||||||
|
compat_str,
|
||||||
|
compat_urlparse,
|
||||||
|
)
|
||||||
from ..utils import (
|
from ..utils import (
|
||||||
determine_ext,
|
determine_ext,
|
||||||
int_or_none,
|
int_or_none,
|
||||||
parse_duration,
|
parse_duration,
|
||||||
parse_iso8601,
|
parse_iso8601,
|
||||||
|
url_or_none,
|
||||||
xpath_text,
|
xpath_text,
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -16,6 +20,8 @@ class MDRIE(InfoExtractor):
|
|||||||
IE_DESC = 'MDR.DE and KiKA'
|
IE_DESC = 'MDR.DE and KiKA'
|
||||||
_VALID_URL = r'https?://(?:www\.)?(?:mdr|kika)\.de/(?:.*)/[a-z-]+-?(?P<id>\d+)(?:_.+?)?\.html'
|
_VALID_URL = r'https?://(?:www\.)?(?:mdr|kika)\.de/(?:.*)/[a-z-]+-?(?P<id>\d+)(?:_.+?)?\.html'
|
||||||
|
|
||||||
|
_GEO_COUNTRIES = ['DE']
|
||||||
|
|
||||||
_TESTS = [{
|
_TESTS = [{
|
||||||
# MDR regularly deletes its videos
|
# MDR regularly deletes its videos
|
||||||
'url': 'http://www.mdr.de/fakt/video189002.html',
|
'url': 'http://www.mdr.de/fakt/video189002.html',
|
||||||
@ -66,6 +72,22 @@ class MDRIE(InfoExtractor):
|
|||||||
'duration': 3239,
|
'duration': 3239,
|
||||||
'uploader': 'MITTELDEUTSCHER RUNDFUNK',
|
'uploader': 'MITTELDEUTSCHER RUNDFUNK',
|
||||||
},
|
},
|
||||||
|
}, {
|
||||||
|
# empty bitrateVideo and bitrateAudio
|
||||||
|
'url': 'https://www.kika.de/filme/sendung128372_zc-572e3f45_zs-1d9fb70e.html',
|
||||||
|
'info_dict': {
|
||||||
|
'id': '128372',
|
||||||
|
'ext': 'mp4',
|
||||||
|
'title': 'Der kleine Wichtel kehrt zurück',
|
||||||
|
'description': 'md5:f77fafdff90f7aa1e9dca14f662c052a',
|
||||||
|
'duration': 4876,
|
||||||
|
'timestamp': 1607823300,
|
||||||
|
'upload_date': '20201213',
|
||||||
|
'uploader': 'ZDF',
|
||||||
|
},
|
||||||
|
'params': {
|
||||||
|
'skip_download': True,
|
||||||
|
},
|
||||||
}, {
|
}, {
|
||||||
'url': 'http://www.kika.de/baumhaus/sendungen/video19636_zc-fea7f8a0_zs-4bf89c60.html',
|
'url': 'http://www.kika.de/baumhaus/sendungen/video19636_zc-fea7f8a0_zs-4bf89c60.html',
|
||||||
'only_matching': True,
|
'only_matching': True,
|
||||||
@ -91,10 +113,13 @@ class MDRIE(InfoExtractor):
|
|||||||
|
|
||||||
title = xpath_text(doc, ['./title', './broadcast/broadcastName'], 'title', fatal=True)
|
title = xpath_text(doc, ['./title', './broadcast/broadcastName'], 'title', fatal=True)
|
||||||
|
|
||||||
|
type_ = xpath_text(doc, './type', default=None)
|
||||||
|
|
||||||
formats = []
|
formats = []
|
||||||
processed_urls = []
|
processed_urls = []
|
||||||
for asset in doc.findall('./assets/asset'):
|
for asset in doc.findall('./assets/asset'):
|
||||||
for source in (
|
for source in (
|
||||||
|
'download',
|
||||||
'progressiveDownload',
|
'progressiveDownload',
|
||||||
'dynamicHttpStreamingRedirector',
|
'dynamicHttpStreamingRedirector',
|
||||||
'adaptiveHttpStreamingRedirector'):
|
'adaptiveHttpStreamingRedirector'):
|
||||||
@ -102,63 +127,49 @@ class MDRIE(InfoExtractor):
|
|||||||
if url_el is None:
|
if url_el is None:
|
||||||
continue
|
continue
|
||||||
|
|
||||||
video_url = url_el.text
|
video_url = url_or_none(url_el.text)
|
||||||
if video_url in processed_urls:
|
if not video_url or video_url in processed_urls:
|
||||||
continue
|
continue
|
||||||
|
|
||||||
processed_urls.append(video_url)
|
processed_urls.append(video_url)
|
||||||
|
|
||||||
vbr = int_or_none(xpath_text(asset, './bitrateVideo', 'vbr'), 1000)
|
ext = determine_ext(video_url)
|
||||||
abr = int_or_none(xpath_text(asset, './bitrateAudio', 'abr'), 1000)
|
|
||||||
|
|
||||||
ext = determine_ext(url_el.text)
|
|
||||||
if ext == 'm3u8':
|
if ext == 'm3u8':
|
||||||
url_formats = self._extract_m3u8_formats(
|
formats.extend(self._extract_m3u8_formats(
|
||||||
video_url, video_id, 'mp4', entry_protocol='m3u8_native',
|
video_url, video_id, 'mp4', entry_protocol='m3u8_native',
|
||||||
preference=0, m3u8_id='HLS', fatal=False)
|
preference=0, m3u8_id='HLS', fatal=False))
|
||||||
elif ext == 'f4m':
|
elif ext == 'f4m':
|
||||||
url_formats = self._extract_f4m_formats(
|
formats.extend(self._extract_f4m_formats(
|
||||||
video_url + '?hdcore=3.7.0&plugin=aasp-3.7.0.39.44', video_id,
|
video_url + '?hdcore=3.7.0&plugin=aasp-3.7.0.39.44', video_id,
|
||||||
preference=0, f4m_id='HDS', fatal=False)
|
preference=0, f4m_id='HDS', fatal=False))
|
||||||
else:
|
else:
|
||||||
media_type = xpath_text(asset, './mediaType', 'media type', default='MP4')
|
media_type = xpath_text(asset, './mediaType', 'media type', default='MP4')
|
||||||
vbr = int_or_none(xpath_text(asset, './bitrateVideo', 'vbr'), 1000)
|
vbr = int_or_none(xpath_text(asset, './bitrateVideo', 'vbr'), 1000)
|
||||||
abr = int_or_none(xpath_text(asset, './bitrateAudio', 'abr'), 1000)
|
abr = int_or_none(xpath_text(asset, './bitrateAudio', 'abr'), 1000)
|
||||||
filesize = int_or_none(xpath_text(asset, './fileSize', 'file size'))
|
filesize = int_or_none(xpath_text(asset, './fileSize', 'file size'))
|
||||||
|
|
||||||
|
format_id = [media_type]
|
||||||
|
if vbr or abr:
|
||||||
|
format_id.append(compat_str(vbr or abr))
|
||||||
|
|
||||||
f = {
|
f = {
|
||||||
'url': video_url,
|
'url': video_url,
|
||||||
'format_id': '%s-%d' % (media_type, vbr or abr),
|
'format_id': '-'.join(format_id),
|
||||||
'filesize': filesize,
|
'filesize': filesize,
|
||||||
'abr': abr,
|
'abr': abr,
|
||||||
'preference': 1,
|
'vbr': vbr,
|
||||||
}
|
}
|
||||||
|
|
||||||
if vbr:
|
if vbr:
|
||||||
width = int_or_none(xpath_text(asset, './frameWidth', 'width'))
|
|
||||||
height = int_or_none(xpath_text(asset, './frameHeight', 'height'))
|
|
||||||
f.update({
|
f.update({
|
||||||
'vbr': vbr,
|
'width': int_or_none(xpath_text(asset, './frameWidth', 'width')),
|
||||||
'width': width,
|
'height': int_or_none(xpath_text(asset, './frameHeight', 'height')),
|
||||||
'height': height,
|
|
||||||
})
|
})
|
||||||
|
|
||||||
url_formats = [f]
|
if type_ == 'audio':
|
||||||
|
f['vcodec'] = 'none'
|
||||||
|
|
||||||
if not url_formats:
|
formats.append(f)
|
||||||
continue
|
|
||||||
|
|
||||||
if not vbr:
|
|
||||||
for f in url_formats:
|
|
||||||
abr = f.get('tbr') or abr
|
|
||||||
if 'tbr' in f:
|
|
||||||
del f['tbr']
|
|
||||||
f.update({
|
|
||||||
'abr': abr,
|
|
||||||
'vcodec': 'none',
|
|
||||||
})
|
|
||||||
|
|
||||||
formats.extend(url_formats)
|
|
||||||
|
|
||||||
self._sort_formats(formats)
|
self._sort_formats(formats)
|
||||||
|
|
||||||
|
@ -83,9 +83,10 @@ class SlidesLiveIE(InfoExtractor):
|
|||||||
else:
|
else:
|
||||||
formats = []
|
formats = []
|
||||||
_MANIFEST_PATTERN = 'https://01.cdn.yoda.slideslive.com/%s/master.%s'
|
_MANIFEST_PATTERN = 'https://01.cdn.yoda.slideslive.com/%s/master.%s'
|
||||||
|
# use `m3u8` entry_protocol until EXT-X-MAP is properly supported by `m3u8_native` entry_protocol
|
||||||
formats.extend(self._extract_m3u8_formats(
|
formats.extend(self._extract_m3u8_formats(
|
||||||
_MANIFEST_PATTERN % (service_id, 'm3u8'), service_id, 'mp4',
|
_MANIFEST_PATTERN % (service_id, 'm3u8'),
|
||||||
entry_protocol='m3u8_native', m3u8_id='hls', fatal=False))
|
service_id, 'mp4', m3u8_id='hls', fatal=False))
|
||||||
formats.extend(self._extract_mpd_formats(
|
formats.extend(self._extract_mpd_formats(
|
||||||
_MANIFEST_PATTERN % (service_id, 'mpd'), service_id,
|
_MANIFEST_PATTERN % (service_id, 'mpd'), service_id,
|
||||||
mpd_id='dash', fatal=False))
|
mpd_id='dash', fatal=False))
|
||||||
|
@ -1,11 +1,20 @@
|
|||||||
# coding: utf-8
|
# coding: utf-8
|
||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
|
|
||||||
from .common import InfoExtractor
|
|
||||||
from ..utils import urlencode_postdata
|
|
||||||
|
|
||||||
import re
|
import re
|
||||||
|
|
||||||
|
from .common import InfoExtractor
|
||||||
|
from ..utils import (
|
||||||
|
clean_html,
|
||||||
|
float_or_none,
|
||||||
|
get_element_by_class,
|
||||||
|
get_element_by_id,
|
||||||
|
parse_duration,
|
||||||
|
str_to_int,
|
||||||
|
unified_timestamp,
|
||||||
|
urlencode_postdata,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class TwitCastingIE(InfoExtractor):
|
class TwitCastingIE(InfoExtractor):
|
||||||
_VALID_URL = r'https?://(?:[^/]+\.)?twitcasting\.tv/(?P<uploader_id>[^/]+)/movie/(?P<id>\d+)'
|
_VALID_URL = r'https?://(?:[^/]+\.)?twitcasting\.tv/(?P<uploader_id>[^/]+)/movie/(?P<id>\d+)'
|
||||||
@ -17,8 +26,12 @@ class TwitCastingIE(InfoExtractor):
|
|||||||
'ext': 'mp4',
|
'ext': 'mp4',
|
||||||
'title': 'Live #2357609',
|
'title': 'Live #2357609',
|
||||||
'uploader_id': 'ivetesangalo',
|
'uploader_id': 'ivetesangalo',
|
||||||
'description': "Moi! I'm live on TwitCasting from my iPhone.",
|
'description': 'Twitter Oficial da cantora brasileira Ivete Sangalo.',
|
||||||
'thumbnail': r're:^https?://.*\.jpg$',
|
'thumbnail': r're:^https?://.*\.jpg$',
|
||||||
|
'upload_date': '20110822',
|
||||||
|
'timestamp': 1314010824,
|
||||||
|
'duration': 32,
|
||||||
|
'view_count': int,
|
||||||
},
|
},
|
||||||
'params': {
|
'params': {
|
||||||
'skip_download': True,
|
'skip_download': True,
|
||||||
@ -30,8 +43,12 @@ class TwitCastingIE(InfoExtractor):
|
|||||||
'ext': 'mp4',
|
'ext': 'mp4',
|
||||||
'title': 'Live playing something #3689740',
|
'title': 'Live playing something #3689740',
|
||||||
'uploader_id': 'mttbernardini',
|
'uploader_id': 'mttbernardini',
|
||||||
'description': "I'm live on TwitCasting from my iPad. password: abc (Santa Marinella/Lazio, Italia)",
|
'description': 'Salve, io sono Matto (ma con la e). Questa è la mia presentazione, in quanto sono letteralmente matto (nel senso di strano), con qualcosa in più.',
|
||||||
'thumbnail': r're:^https?://.*\.jpg$',
|
'thumbnail': r're:^https?://.*\.jpg$',
|
||||||
|
'upload_date': '20120212',
|
||||||
|
'timestamp': 1329028024,
|
||||||
|
'duration': 681,
|
||||||
|
'view_count': int,
|
||||||
},
|
},
|
||||||
'params': {
|
'params': {
|
||||||
'skip_download': True,
|
'skip_download': True,
|
||||||
@ -40,9 +57,7 @@ class TwitCastingIE(InfoExtractor):
|
|||||||
}]
|
}]
|
||||||
|
|
||||||
def _real_extract(self, url):
|
def _real_extract(self, url):
|
||||||
mobj = re.match(self._VALID_URL, url)
|
uploader_id, video_id = re.match(self._VALID_URL, url).groups()
|
||||||
video_id = mobj.group('id')
|
|
||||||
uploader_id = mobj.group('uploader_id')
|
|
||||||
|
|
||||||
video_password = self._downloader.params.get('videopassword')
|
video_password = self._downloader.params.get('videopassword')
|
||||||
request_data = None
|
request_data = None
|
||||||
@ -52,30 +67,45 @@ class TwitCastingIE(InfoExtractor):
|
|||||||
})
|
})
|
||||||
webpage = self._download_webpage(url, video_id, data=request_data)
|
webpage = self._download_webpage(url, video_id, data=request_data)
|
||||||
|
|
||||||
title = self._html_search_regex(
|
title = clean_html(get_element_by_id(
|
||||||
r'(?s)<[^>]+id=["\']movietitle[^>]+>(.+?)</',
|
'movietitle', webpage)) or self._html_search_meta(
|
||||||
webpage, 'title', default=None) or self._html_search_meta(
|
['og:title', 'twitter:title'], webpage, fatal=True)
|
||||||
'twitter:title', webpage, fatal=True)
|
|
||||||
|
|
||||||
|
video_js_data = {}
|
||||||
m3u8_url = self._search_regex(
|
m3u8_url = self._search_regex(
|
||||||
(r'data-movie-url=(["\'])(?P<url>(?:(?!\1).)+)\1',
|
r'data-movie-url=(["\'])(?P<url>(?:(?!\1).)+)\1',
|
||||||
r'(["\'])(?P<url>http.+?\.m3u8.*?)\1'),
|
webpage, 'm3u8 url', group='url', default=None)
|
||||||
webpage, 'm3u8 url', group='url')
|
if not m3u8_url:
|
||||||
|
video_js_data = self._parse_json(self._search_regex(
|
||||||
|
r"data-movie-playlist='(\[[^']+\])'",
|
||||||
|
webpage, 'movie playlist'), video_id)[0]
|
||||||
|
m3u8_url = video_js_data['source']['url']
|
||||||
|
|
||||||
|
# use `m3u8` entry_protocol until EXT-X-MAP is properly supported by `m3u8_native` entry_protocol
|
||||||
formats = self._extract_m3u8_formats(
|
formats = self._extract_m3u8_formats(
|
||||||
m3u8_url, video_id, ext='mp4', entry_protocol='m3u8_native',
|
m3u8_url, video_id, 'mp4', m3u8_id='hls')
|
||||||
m3u8_id='hls')
|
|
||||||
|
|
||||||
thumbnail = self._og_search_thumbnail(webpage)
|
thumbnail = video_js_data.get('thumbnailUrl') or self._og_search_thumbnail(webpage)
|
||||||
description = self._og_search_description(
|
description = clean_html(get_element_by_id(
|
||||||
webpage, default=None) or self._html_search_meta(
|
'authorcomment', webpage)) or self._html_search_meta(
|
||||||
'twitter:description', webpage)
|
['description', 'og:description', 'twitter:description'], webpage)
|
||||||
|
duration = float_or_none(video_js_data.get(
|
||||||
|
'duration'), 1000) or parse_duration(clean_html(
|
||||||
|
get_element_by_class('tw-player-duration-time', webpage)))
|
||||||
|
view_count = str_to_int(self._search_regex(
|
||||||
|
r'Total\s*:\s*([\d,]+)\s*Views', webpage, 'views', None))
|
||||||
|
timestamp = unified_timestamp(self._search_regex(
|
||||||
|
r'data-toggle="true"[^>]+datetime="([^"]+)"',
|
||||||
|
webpage, 'datetime', None))
|
||||||
|
|
||||||
return {
|
return {
|
||||||
'id': video_id,
|
'id': video_id,
|
||||||
'title': title,
|
'title': title,
|
||||||
'description': description,
|
'description': description,
|
||||||
'thumbnail': thumbnail,
|
'thumbnail': thumbnail,
|
||||||
|
'timestamp': timestamp,
|
||||||
'uploader_id': uploader_id,
|
'uploader_id': uploader_id,
|
||||||
|
'duration': duration,
|
||||||
|
'view_count': view_count,
|
||||||
'formats': formats,
|
'formats': formats,
|
||||||
}
|
}
|
||||||
|
@ -260,6 +260,14 @@ class YandexMusicAlbumIE(YandexMusicPlaylistBaseIE):
|
|||||||
},
|
},
|
||||||
'playlist_count': 33,
|
'playlist_count': 33,
|
||||||
# 'skip': 'Travis CI servers blocked by YandexMusic',
|
# 'skip': 'Travis CI servers blocked by YandexMusic',
|
||||||
|
}, {
|
||||||
|
# empty artists
|
||||||
|
'url': 'https://music.yandex.ru/album/9091882',
|
||||||
|
'info_dict': {
|
||||||
|
'id': '9091882',
|
||||||
|
'title': 'ТЕД на русском',
|
||||||
|
},
|
||||||
|
'playlist_count': 187,
|
||||||
}]
|
}]
|
||||||
|
|
||||||
def _real_extract(self, url):
|
def _real_extract(self, url):
|
||||||
@ -273,7 +281,10 @@ class YandexMusicAlbumIE(YandexMusicPlaylistBaseIE):
|
|||||||
|
|
||||||
entries = self._build_playlist([track for volume in album['volumes'] for track in volume])
|
entries = self._build_playlist([track for volume in album['volumes'] for track in volume])
|
||||||
|
|
||||||
title = '%s - %s' % (album['artists'][0]['name'], album['title'])
|
title = album['title']
|
||||||
|
artist = try_get(album, lambda x: x['artists'][0]['name'], compat_str)
|
||||||
|
if artist:
|
||||||
|
title = '%s - %s' % (artist, title)
|
||||||
year = album.get('year')
|
year = album.get('year')
|
||||||
if year:
|
if year:
|
||||||
title += ' (%s)' % year
|
title += ' (%s)' % year
|
||||||
|
@ -1,3 +1,3 @@
|
|||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
|
|
||||||
__version__ = '2020.12.12'
|
__version__ = '2020.12.14'
|
||||||
|
Loading…
Reference in New Issue
Block a user