pladform.py 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137
  1. from .common import InfoExtractor
  2. from ..utils import (
  3. determine_ext,
  4. ExtractorError,
  5. int_or_none,
  6. parse_qs,
  7. xpath_text,
  8. qualities,
  9. )
  10. class PladformIE(InfoExtractor):
  11. _VALID_URL = r'''(?x)
  12. https?://
  13. (?:
  14. (?:
  15. out\.pladform\.ru/player|
  16. static\.pladform\.ru/player\.swf
  17. )
  18. \?.*\bvideoid=|
  19. video\.pladform\.ru/catalog/video/videoid/
  20. )
  21. (?P<id>\d+)
  22. '''
  23. _EMBED_REGEX = [r'<iframe[^>]+src=(["\'])(?P<url>(?:https?:)?//out\.pladform\.ru/player\?.+?)\1']
  24. _TESTS = [{
  25. 'url': 'http://out.pladform.ru/player?pl=18079&type=html5&videoid=100231282',
  26. 'info_dict': {
  27. 'id': '6216d548e755edae6e8280667d774791',
  28. 'ext': 'mp4',
  29. 'timestamp': 1406117012,
  30. 'title': 'Гарик Мартиросян и Гарик Харламов - Кастинг на концерт ко Дню милиции',
  31. 'age_limit': 0,
  32. 'upload_date': '20140723',
  33. 'thumbnail': str,
  34. 'view_count': int,
  35. 'description': str,
  36. 'category': list,
  37. 'uploader_id': '12082',
  38. 'uploader': 'Comedy Club',
  39. 'duration': 367,
  40. },
  41. 'expected_warnings': ['HTTP Error 404: Not Found']
  42. }, {
  43. 'url': 'https://out.pladform.ru/player?pl=64471&videoid=3777899&vk_puid15=0&vk_puid34=0',
  44. 'md5': '53362fac3a27352da20fa2803cc5cd6f',
  45. 'info_dict': {
  46. 'id': '3777899',
  47. 'ext': 'mp4',
  48. 'title': 'СТУДИЯ СОЮЗ • Шоу Студия Союз, 24 выпуск (01.02.2018) Нурлан Сабуров и Слава Комиссаренко',
  49. 'description': 'md5:05140e8bf1b7e2d46e7ba140be57fd95',
  50. 'thumbnail': r're:^https?://.*\.jpg$',
  51. 'duration': 3190,
  52. },
  53. }, {
  54. 'url': 'http://static.pladform.ru/player.swf?pl=21469&videoid=100183293&vkcid=0',
  55. 'only_matching': True,
  56. }, {
  57. 'url': 'http://video.pladform.ru/catalog/video/videoid/100183293/vkcid/0',
  58. 'only_matching': True,
  59. }]
  60. def _real_extract(self, url):
  61. video_id = self._match_id(url)
  62. qs = parse_qs(url)
  63. pl = qs.get('pl', ['1'])[0]
  64. video = self._download_xml(
  65. 'http://out.pladform.ru/getVideo', video_id, query={
  66. 'pl': pl,
  67. 'videoid': video_id,
  68. }, fatal=False)
  69. def fail(text):
  70. raise ExtractorError(
  71. '%s returned error: %s' % (self.IE_NAME, text),
  72. expected=True)
  73. if not video:
  74. targetUrl = self._request_webpage(url, video_id, note='Resolving final URL').geturl()
  75. if targetUrl == url:
  76. raise ExtractorError('Can\'t parse page')
  77. return self.url_result(targetUrl)
  78. if video.tag == 'error':
  79. fail(video.text)
  80. quality = qualities(('ld', 'sd', 'hd'))
  81. formats = []
  82. for src in video.findall('./src'):
  83. if src is None:
  84. continue
  85. format_url = src.text
  86. if not format_url:
  87. continue
  88. if src.get('type') == 'hls' or determine_ext(format_url) == 'm3u8':
  89. formats.extend(self._extract_m3u8_formats(
  90. format_url, video_id, 'mp4', entry_protocol='m3u8_native',
  91. m3u8_id='hls', fatal=False))
  92. else:
  93. formats.append({
  94. 'url': src.text,
  95. 'format_id': src.get('quality'),
  96. 'quality': quality(src.get('quality')),
  97. })
  98. if not formats:
  99. error = xpath_text(video, './cap', 'error', default=None)
  100. if error:
  101. fail(error)
  102. webpage = self._download_webpage(
  103. 'http://video.pladform.ru/catalog/video/videoid/%s' % video_id,
  104. video_id)
  105. title = self._og_search_title(webpage, fatal=False) or xpath_text(
  106. video, './/title', 'title', fatal=True)
  107. description = self._search_regex(
  108. r'</h3>\s*<p>([^<]+)</p>', webpage, 'description', fatal=False)
  109. thumbnail = self._og_search_thumbnail(webpage) or xpath_text(
  110. video, './/cover', 'cover')
  111. duration = int_or_none(xpath_text(video, './/time', 'duration'))
  112. age_limit = int_or_none(xpath_text(video, './/age18', 'age limit'))
  113. return {
  114. 'id': video_id,
  115. 'title': title,
  116. 'description': description,
  117. 'thumbnail': thumbnail,
  118. 'duration': duration,
  119. 'age_limit': age_limit,
  120. 'formats': formats,
  121. }