]>
Raphaƫl G. Git Repositories - youtubedl/blob - youtube_dl/extractor/adultswim.py
2 from __future__
import unicode_literals
7 from . turner
import TurnerBaseIE
20 class AdultSwimIE ( TurnerBaseIE
):
21 _VALID_URL
= r
'https?://(?:www\.)?adultswim\.com/videos/(?P<show_path>[^/?#]+)(?:/(?P<episode_path>[^/?#]+))?'
24 'url' : 'http://adultswim.com/videos/rick-and-morty/pilot' ,
26 'id' : 'rQxZvXQ4ROaSOqq-or2Mow' ,
28 'title' : 'Rick and Morty - Pilot' ,
29 'description' : 'Rick moves in with his daughter \' s family and establishes himself as a bad influence on his grandson, Morty.' ,
30 'timestamp' : 1543294800 ,
31 'upload_date' : '20181127' ,
35 'skip_download' : True ,
37 'expected_warnings' : [ 'Unable to download f4m manifest' ],
39 'url' : 'http://www.adultswim.com/videos/tim-and-eric-awesome-show-great-job/dr-steve-brule-for-your-wine/' ,
41 'id' : 'sY3cMUR_TbuE4YmdjzbIcQ' ,
43 'title' : 'Tim and Eric Awesome Show Great Job! - Dr. Steve Brule, For Your Wine' ,
44 'description' : 'Dr. Brule reports live from Wine Country with a special report on wines. \n Watch Tim and Eric Awesome Show Great Job! episode #20, "Embarrassed" on Adult Swim.' ,
45 'upload_date' : '20080124' ,
46 'timestamp' : 1201150800 ,
50 'skip_download' : True ,
52 'skip' : '404 Not Found' ,
54 'url' : 'http://www.adultswim.com/videos/decker/inside-decker-a-new-hero/' ,
56 'id' : 'I0LQFQkaSUaFp8PnAWHhoQ' ,
58 'title' : 'Decker - Inside Decker: A New Hero' ,
59 'description' : 'The guys recap the conclusion of the season. They announce a new hero, take a peek into the Victorville Film Archive and welcome back the talented James Dean.' ,
60 'timestamp' : 1469480460 ,
61 'upload_date' : '20160725' ,
65 'skip_download' : True ,
67 'expected_warnings' : [ 'Unable to download f4m manifest' ],
69 'url' : 'http://www.adultswim.com/videos/attack-on-titan' ,
71 'id' : 'attack-on-titan' ,
72 'title' : 'Attack on Titan' ,
73 'description' : 'md5:41caa9416906d90711e31dc00cb7db7e' ,
75 'playlist_mincount' : 12 ,
77 'url' : 'http://www.adultswim.com/videos/streams/williams-stream' ,
79 'id' : 'd8DEBj7QRfetLsRgFnGEyg' ,
81 'title' : r
're:^Williams Stream \d {4} -\d {2} -\d {2} \d {2} :\d {2} $' ,
82 'description' : 'original programming' ,
86 'skip_download' : True ,
88 'skip' : '404 Not Found' ,
91 def _real_extract ( self
, url
):
92 show_path
, episode_path
= re
. match ( self
._ VALID
_U RL
, url
). groups ()
93 display_id
= episode_path
or show_path
95 getShowBySlug(slug:" %s ") {
100 query
= query
% '''title
101 getVideoBySlug(slug:" %s ") {
116 query
= query
% '''metaDescription
118 videos(first:1000,sort:["episode_number"]) {
126 show_data
= self
._ download
_ json
(
127 'https://www.adultswim.com/api/search' , display_id
,
128 data
= json
. dumps ({ 'query' : query
}). encode (),
129 headers
={ 'Content-Type' : 'application/json' })[ 'data' ][ 'getShowBySlug' ]
131 video_data
= show_data
[ 'getVideoBySlug' ]
132 video_id
= video_data
[ '_id' ]
133 episode_title
= title
= video_data
[ 'title' ]
134 series
= show_data
. get ( 'title' )
136 title
= ' %s - %s ' % ( series
, title
)
140 'description' : strip_or_none ( video_data
. get ( 'description' )),
141 'duration' : float_or_none ( video_data
. get ( 'duration' )),
144 'age_limit' : parse_age_limit ( video_data
. get ( 'tvRating' )),
145 'thumbnail' : video_data
. get ( 'poster' ),
146 'timestamp' : parse_iso8601 ( video_data
. get ( 'launchDate' )),
148 'season_number' : int_or_none ( video_data
. get ( 'seasonNumber' )),
149 'episode' : episode_title
,
150 'episode_number' : int_or_none ( video_data
. get ( 'episodeNumber' )),
153 auth
= video_data
. get ( 'auth' )
154 media_id
= video_data
. get ( 'mediaID' )
156 info
. update ( self
._ extract
_ ngtv
_ info
( media_id
, {
157 # CDN_TOKEN_APP_ID from:
158 # https://d2gg02c3xr550i.cloudfront.net/assets/asvp.e9c8bef24322d060ef87.bundle.js
159 'appId' : 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhcHBJZCI6ImFzLXR2ZS1kZXNrdG9wLXB0enQ2bSIsInByb2R1Y3QiOiJ0dmUiLCJuZXR3b3JrIjoiYXMiLCJwbGF0Zm9ybSI6ImRlc2t0b3AiLCJpYXQiOjE1MzI3MDIyNzl9.BzSCk-WYOZ2GMCIaeVb8zWnzhlgnXuJTCu0jGp_VaZE' ,
162 'site_name' : 'AdultSwim' ,
163 'auth_required' : auth
,
167 extract_data
= self
._ download
_ json
(
168 'https://www.adultswim.com/api/shows/v1/videos/' + video_id
,
169 video_id
, query
={ 'fields' : 'stream' }, fatal
= False ) or {}
170 assets
= try_get ( extract_data
, lambda x
: x
[ 'data' ][ 'video' ][ 'stream' ][ 'assets' ], list ) or []
172 asset_url
= asset
. get ( 'url' )
175 ext
= determine_ext ( asset_url
, mimetype2ext ( asset
. get ( 'mime_type' )))
177 info
[ 'formats' ]. extend ( self
._ extract
_ m
3u8_ formats
(
178 asset_url
, video_id
, 'mp4' , m3u8_id
= 'hls' , fatal
= False ))
181 # info['formats'].extend(self._extract_f4m_formats(
182 # asset_url, video_id, f4m_id='hds', fatal=False))
183 elif ext
in ( 'scc' , 'ttml' , 'vtt' ):
184 info
[ 'subtitles' ]. setdefault ( 'en' , []). append ({
187 self
._ sort
_ formats
( info
[ 'formats' ])
192 for edge
in show_data
. get ( 'videos' , {}). get ( 'edges' , []):
193 video
= edge
. get ( 'node' ) or {}
194 slug
= video
. get ( 'slug' )
197 entries
. append ( self
. url_result (
198 'http://adultswim.com/videos/ %s / %s ' % ( show_path
, slug
),
199 'AdultSwim' , video
. get ( '_id' )))
200 return self
. playlist_result (
201 entries
, show_path
, show_data
. get ( 'title' ),
202 strip_or_none ( show_data
. get ( 'metaDescription' )))