2016-08-16 05:43:33 -07:00
# coding: utf-8
from __future__ import unicode_literals
from . theplatform import ThePlatformIE
from . . utils import (
2016-08-16 06:49:32 -07:00
int_or_none ,
2017-07-26 12:04:51 -07:00
parse_age_limit ,
try_get ,
update_url_query ,
2016-08-16 05:43:33 -07:00
)
class AMCNetworksIE ( ThePlatformIE ) :
2018-01-28 02:30:20 -08:00
_VALID_URL = r ' https?://(?:www \ .)?(?:amc|bbcamerica|ifc|(?:we|sundance)tv) \ .com/(?:movies|shows(?:/[^/]+)+)/(?P<id>[^/?#]+) '
2016-08-16 05:43:33 -07:00
_TESTS = [ {
' url ' : ' http://www.ifc.com/shows/maron/season-04/episode-01/step-1 ' ,
' md5 ' : ' ' ,
' info_dict ' : {
' id ' : ' s3MX01Nl4vPH ' ,
' ext ' : ' mp4 ' ,
2016-08-16 06:49:32 -07:00
' title ' : ' Maron - Season 4 - Step 1 ' ,
2016-08-16 05:43:33 -07:00
' description ' : ' In denial about his current situation, Marc is reluctantly convinced by his friends to enter rehab. Starring Marc Maron and Constance Zimmer. ' ,
' age_limit ' : 17 ,
' upload_date ' : ' 20160505 ' ,
' timestamp ' : 1462468831 ,
' uploader ' : ' AMCN ' ,
} ,
' params ' : {
# m3u8 download
' skip_download ' : True ,
} ,
2016-10-01 23:25:06 -07:00
' skip ' : ' Requires TV provider accounts ' ,
2016-08-16 05:43:33 -07:00
} , {
' url ' : ' http://www.bbcamerica.com/shows/the-hunt/full-episodes/season-1/episode-01-the-hardest-challenge ' ,
' only_matching ' : True ,
} , {
' url ' : ' http://www.amc.com/shows/preacher/full-episodes/season-01/episode-00/pilot ' ,
' only_matching ' : True ,
} , {
' url ' : ' http://www.wetv.com/shows/million-dollar-matchmaker/season-01/episode-06-the-dumped-dj-and-shallow-hal ' ,
' only_matching ' : True ,
} , {
' url ' : ' http://www.ifc.com/movies/chaos ' ,
' only_matching ' : True ,
2016-11-22 04:40:57 -08:00
} , {
' url ' : ' http://www.bbcamerica.com/shows/doctor-who/full-episodes/the-power-of-the-daleks/episode-01-episode-1-color-version ' ,
' only_matching ' : True ,
2017-02-24 11:51:53 -08:00
} , {
' url ' : ' http://www.wetv.com/shows/mama-june-from-not-to-hot/full-episode/season-01/thin-tervention ' ,
' only_matching ' : True ,
} , {
' url ' : ' http://www.wetv.com/shows/la-hair/videos/season-05/episode-09-episode-9-2/episode-9-sneak-peek-3 ' ,
' only_matching ' : True ,
2018-01-28 02:30:20 -08:00
} , {
' url ' : ' https://www.sundancetv.com/shows/riviera/full-episodes/season-1/episode-01-episode-1 ' ,
' only_matching ' : True ,
2016-08-16 05:43:33 -07:00
} ]
def _real_extract ( self , url ) :
display_id = self . _match_id ( url )
webpage = self . _download_webpage ( url , display_id )
query = {
' mbr ' : ' true ' ,
' manifest ' : ' m3u ' ,
}
2017-02-15 05:18:50 -08:00
media_url = self . _search_regex (
r ' window \ .platformLinkURL \ s*= \ s*[ \' " ]([^ \' " ]+) ' ,
webpage , ' media url ' )
2016-08-16 05:43:33 -07:00
theplatform_metadata = self . _download_theplatform_metadata ( self . _search_regex (
2017-02-15 05:18:50 -08:00
r ' link \ .theplatform \ .com/s/([^?]+) ' ,
media_url , ' theplatform_path ' ) , display_id )
2016-08-16 05:43:33 -07:00
info = self . _parse_theplatform_metadata ( theplatform_metadata )
video_id = theplatform_metadata [ ' pid ' ]
title = theplatform_metadata [ ' title ' ]
2017-07-26 12:04:51 -07:00
rating = try_get (
theplatform_metadata , lambda x : x [ ' ratings ' ] [ 0 ] [ ' rating ' ] )
2017-02-15 05:18:50 -08:00
auth_required = self . _search_regex (
r ' window \ .authRequired \ s*= \ s*(true|false); ' ,
webpage , ' auth required ' )
2016-08-16 05:43:33 -07:00
if auth_required == ' true ' :
2017-02-15 05:18:50 -08:00
requestor_id = self . _search_regex (
r ' window \ .requestor_id \ s*= \ s*[ \' " ]([^ \' " ]+) ' ,
webpage , ' requestor id ' )
resource = self . _get_mvpd_resource (
requestor_id , title , video_id , rating )
query [ ' auth ' ] = self . _extract_mvpd_auth (
url , video_id , requestor_id , resource )
2016-08-16 05:43:33 -07:00
media_url = update_url_query ( media_url , query )
2017-02-15 05:18:50 -08:00
formats , subtitles = self . _extract_theplatform_smil (
media_url , video_id )
2016-08-16 05:43:33 -07:00
self . _sort_formats ( formats )
info . update ( {
' id ' : video_id ,
2016-08-16 08:20:07 -07:00
' subtitles ' : subtitles ,
2016-08-16 05:43:33 -07:00
' formats ' : formats ,
' age_limit ' : parse_age_limit ( parse_age_limit ( rating ) ) ,
} )
2016-08-16 06:49:32 -07:00
ns_keys = theplatform_metadata . get ( ' $xmlns ' , { } ) . keys ( )
if ns_keys :
ns = list ( ns_keys ) [ 0 ]
series = theplatform_metadata . get ( ns + ' $show ' )
2017-02-15 05:18:50 -08:00
season_number = int_or_none (
theplatform_metadata . get ( ns + ' $season ' ) )
2016-08-16 06:49:32 -07:00
episode = theplatform_metadata . get ( ns + ' $episodeTitle ' )
2017-02-15 05:18:50 -08:00
episode_number = int_or_none (
theplatform_metadata . get ( ns + ' $episode ' ) )
2016-08-16 06:49:32 -07:00
if season_number :
title = ' Season %d - %s ' % ( season_number , title )
if series :
title = ' %s - %s ' % ( series , title )
info . update ( {
' title ' : title ,
' series ' : series ,
' season_number ' : season_number ,
' episode ' : episode ,
' episode_number ' : episode_number ,
} )
2016-08-16 05:43:33 -07:00
return info