def api_vod_download(type, start=0): if not api_get_session(): return None if type == "movies": url = '{base_url}/v6/tabs/GenreFilms?count=52&expand=true&expandlist=true&maxResults=52&offset={start}'.format(base_url=CONST_API_URL, start=start) elif type == "watchahead": url = '{base_url}/v6/tabs/VooruitKijken2?count=52&expand=true&expandlist=true&maxResults=52&offset={start}'.format(base_url=CONST_API_URL, start=start) elif type == "seriesbinge": url = '{base_url}/v6/tabs/SeriesBingewatch?count=52&expand=true&expandlist=true&maxResults=52&offset={start}'.format(base_url=CONST_API_URL, start=start) elif type == "mostviewed": url = '{base_url}/v6/tabs/MostViewed?count=52&expand=true&expandlist=true&maxResults=52&offset={start}'.format(base_url=CONST_API_URL, start=start) elif type == "tipfeed": url = '{base_url}/v6/tabs/Tipfeed?count=52&expand=true&expandlist=true&maxResults=52&offset={start}'.format(base_url=CONST_API_URL, start=start) else: return None file = "cache" + os.sep + "vod_" + type + "_" + unicode(start) + ".json" if settings.getBool(key='enable_cache') and not is_file_older_than_x_minutes(file=ADDON_PROFILE + file, minutes=10): data = load_file(file=file, isJSON=True) else: download = api_download(url=url, type='get', headers=None, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and settings.getBool(key='enable_cache'): write_file(file=file, data=data, isJSON=True) if not data or not check_key(data, 'Items'): return None return api_process_vod(data=data)
def api_vod_seasons(id): if not api_get_session(): return None profile_settings = load_profile(profile_id=1) seasons = [] program_url = '{api_url}/CONTENT/DETAIL/GROUP_OF_BUNDLES/{id}'.format( api_url=profile_settings['api_url'], id=id) file = "cache" + os.sep + "vod_seasons_" + unicode(id) + ".json" if settings.getBool( key='enable_cache') and not is_file_older_than_x_minutes( file=ADDON_PROFILE + file, minutes=10): data = load_file(file=file, isJSON=True) else: download = api_download(url=program_url, type='get', headers=None, data=None, json_data=True, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and check_key( data, 'resultCode') and data['resultCode'] == 'OK' and check_key( data, 'resultObj') and check_key( data['resultObj'], 'containers') and settings.getBool(key='enable_cache'): write_file(file=file, data=data, isJSON=True) if not data or not check_key(data['resultObj'], 'containers'): return None for row in data['resultObj']['containers']: for currow in row['containers']: if check_key(currow, 'metadata') and check_key( currow['metadata'], 'season' ) and currow['metadata']['contentSubtype'] == 'SEASON': seasons.append({ 'id': currow['metadata']['contentId'], 'seriesNumber': currow['metadata']['season'], 'description': currow['metadata']['shortDescription'], 'image': "{image_url}/vod/{image}/1920x1080.jpg?blurred=false". format(image_url=CONST_IMAGE_URL, image=currow['metadata']['pictureUrl']) }) return {'type': 'seasons', 'seasons': seasons}
def update_prefs(profile_id=1, channels=None): prefs = load_prefs(profile_id=1) if prefs: for pref in prefs: if not pref in channels: prefs.pop(pref) if channels: for currow in channels: row = channels[currow] if not prefs or not check_key(prefs, unicode(currow)): if (settings.getBool(key='minimalChannels') == True and int(row['minimal']) == 0) or (settings.getBool(key='disableErotica') == True and int(row['erotica']) == 1) or (settings.getBool(key='disableRegionalChannels') == True and int(row['regional']) == 1) or (PROVIDER_NAME == 'kpn' and settings.getBool(key='homeConnection') == False and int(row['home_only']) == 1): mod_pref = { 'live': 0, 'replay': 0, } else: if int(row['replay']) == 0: mod_pref = { 'live': 1, 'replay': 0, } else: mod_pref = { 'live': 1, 'replay': 1, } prefs[unicode(currow)] = mod_pref save_prefs(profile_id=1, prefs=prefs)
def plugin_process_vod_seasons(id, data): seasons = [] ref = id id = id[1:] if not data or not check_key(data, 'details'): return None for currow in data['details']: row = data['details'][currow] if check_key(row, 'type') and row['type'] == 'season': if settings.getBool('use_small_images', default=False) == True: image = data['poster'].replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['small']) else: image = data['poster'].replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['large']) seasons.append({ 'id': str(id) + '###' + str(row['id']), 'seriesNumber': row['title'], 'description': data['description'], 'image': image, 'watchlist': ref }) return {'type': 'seasons', 'seasons': seasons}
def plugin_login_error(login_result): email_or_pin = settings.getBool(key='email_instead_of_customer') if email_or_pin: gui.ok(message=_.LOGIN_ERROR2, heading=_.LOGIN_ERROR_TITLE) else: gui.ok(message=_.LOGIN_ERROR, heading=_.LOGIN_ERROR_TITLE)
def home(**kwargs): clear_old() check_first() profile_settings = load_profile(profile_id=1) folder = plugin.Folder() if profile_settings and check_key(profile_settings, 'pswd') and len(profile_settings['pswd']) > 0: folder.add_item(label=_(_.LIVE_TV, _bold=True), path=plugin.url_for(func_or_url=live_tv)) folder.add_item(label=_(_.CHANNELS, _bold=True), path=plugin.url_for(func_or_url=replaytv)) if settings.getBool('showMoviesSeries'): for vod_entry in CONST_VOD_CAPABILITY: folder.add_item(label=_(vod_entry['label'], _bold=True), path=plugin.url_for(func_or_url=vod, file=vod_entry['file'], label=vod_entry['label'], start=vod_entry['start'], online=vod_entry['online'], split=vod_entry['split'])) if CONST_WATCHLIST: folder.add_item(label=_(_.WATCHLIST, _bold=True), path=plugin.url_for(func_or_url=watchlist)) folder.add_item(label=_(_.SEARCH, _bold=True), path=plugin.url_for(func_or_url=search_menu)) folder.add_item(label=_(_.LOGIN, _bold=True), path=plugin.url_for(func_or_url=login)) folder.add_item(label=_.SETTINGS, path=plugin.url_for(func_or_url=settings_menu)) return folder
def api_get_channels(): channels_url = '{dut_epg_url}/channels.json'.format( dut_epg_url=CONST_DUT_EPG) file = "cache" + os.sep + "channels.json" if not is_file_older_than_x_days(file=ADDON_PROFILE + file, days=1): data = load_file(file=file, isJSON=True) else: download = api_download(url=channels_url, type='get', headers=None, data=None, json_data=True, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data: write_file(file=file, data=data, isJSON=True) update_prefs(profile_id=1, channels=data) else: return None change_icon() data2 = OrderedDict() for currow in data: row = data[currow] if settings.getBool('minimalChannels') and int(row['minimal']) == 0: continue if settings.getBool('disableErotica') and int(row['erotica']) == 1: continue data2[currow] = row return data2
def api_vod_season(series, id): if not api_get_session(): return None season = [] file = "cache" + os.sep + "vod_season_" + unicode(id) + ".json" if settings.getBool(key='enable_cache') and not is_file_older_than_x_minutes(file=ADDON_PROFILE + file, minutes=10): data = load_file(file=file, isJSON=True) else: profile_settings = load_profile(profile_id=1) headers = {'Content-Type': 'application/json', 'X_CSRFToken': profile_settings['csrf_token']} session_post_data = { 'VODID': unicode(id), 'offset': '0', 'count': '35', } seasons_url = '{base_url}/VSP/V3/QueryEpisodeList?from=throughMSAAccess'.format(base_url=CONST_BASE_URL) download = api_download(url=seasons_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and check_key(data, 'result') and check_key(data['result'], 'retCode') and data['result']['retCode'] == '000000000' and check_key(data, 'episodes') and settings.getBool(key='enable_cache'): write_file(file=file, data=data, isJSON=True) if not data or not check_key(data, 'episodes'): return None for row in data['episodes']: if check_key(row, 'VOD') and check_key(row['VOD'], 'ID') and check_key(row['VOD'], 'name') and check_key(row, 'sitcomNO'): image = '' duration = 0 if not check_key(row['VOD'], 'mediaFiles') or not check_key(row['VOD']['mediaFiles'][0], 'ID'): continue if check_key(row['VOD']['mediaFiles'][0], 'elapseTime'): duration = row['VOD']['mediaFiles'][0]['elapseTime'] if check_key(row['VOD'], 'picture') and check_key(row['VOD']['picture'], 'posters'): image = row['VOD']['picture']['posters'][0] label = '{episode} - {title}'.format(episode=row['sitcomNO'], title=row['VOD']['name']) season.append({'label': label, 'id': row['VOD']['ID'], 'media_id': row['VOD']['mediaFiles'][0]['ID'], 'duration': duration, 'title': row['VOD']['name'], 'episodeNumber': row['sitcomNO'], 'description': '', 'image': image}) return season
def change_channel(type, id, change, **kwargs): change = int(change) if not id or len(unicode(id)) == 0 or not type or len(unicode(type)) == 0: return False prefs = load_prefs(profile_id=1) id = unicode(id) type = unicode(type) data = api_get_channels() if data and check_key(data, id) and prefs and check_key(prefs, id) and int(prefs[id][type]) == 0: if type == 'replay' and int(data[id]['replay']) == 0: gui.ok(message=_.EXPLAIN_NO_REPLAY) return False elif settings.getBool(key='homeConnection') == False and int(data[id]['home_only']) == 1: gui.ok(message=_.EXPLAIN_HOME_CONNECTION) return False keys = ['live', 'replay'] mod_pref = { 'live': 1, 'replay': 1, } if prefs and check_key(prefs, id): for key in keys: if key == type: continue mod_pref[key] = prefs[id][key] if change == 0: if not check_key(prefs, id): mod_pref[type] = 0 else: if prefs[id][type] == 1: mod_pref[type] = 0 else: mod_pref[type] = 1 else: mod_pref[type] = 1 prefs[id] = mod_pref save_prefs(profile_id=1, prefs=prefs) xbmc.executeJSONRPC('{{"jsonrpc":"2.0","id":1,"method":"GUI.ActivateWindow","params":{{"window":"videos","parameters":["plugin://' + unicode(ADDON_ID) + '/?_=channel_picker&type=' + type + '"]}}}}')
def combine_playlist(): tv = load_file(file='tv.m3u8', isJSON=False) if not tv: tv = u'#EXTM3U\n' radio = None if settings.getBool(key='enable_radio'): radio = load_file(file='radio.m3u8', isJSON=False) if not radio: radio = '' write_file(file='playlist.m3u8', data=tv + radio, isJSON=False)
def search(query=None, **kwargs): items = [] if not query: query = gui.input(message=_.SEARCH, default='').strip() if not query: return profile_settings = load_profile(profile_id=1) for x in reversed(range(2, 10)): if check_key(profile_settings, 'search' + unicode(x - 1)): profile_settings['search' + unicode(x)] = profile_settings['search' + unicode(x - 1)] else: profile_settings['search' + unicode(x)] = '' profile_settings['search1'] = query if CONST_ONLINE_SEARCH: for x in reversed(range(2, 10)): if check_key(profile_settings, 'search_type' + unicode(x - 1)): profile_settings['search_type' + unicode(x)] = profile_settings['search_type' + unicode(x - 1)] else: profile_settings['search_type' + unicode(x)] = 0 profile_settings['search_type1'] = 0 save_profile(profile_id=1, profile=profile_settings) else: query = unicode(query) folder = plugin.Folder(title=_(_.SEARCH_FOR, query=query)) processed = process_replaytv_search(search=query) items += processed['items'] if settings.getBool('showMoviesSeries'): for vod_entry in CONST_VOD_CAPABILITY: processed = process_vod_content(data=vod_entry['file'], start=vod_entry['start'], search=query, type=vod_entry['label'], online=vod_entry['online']) items += processed['items'] items[:] = sorted(items, key=_sort_replay_items, reverse=True) items = items[:25] folder.add_items(items) return folder
def download_files(): resp = requests.get(url=CONST_MD5) write_file(file='md5.json', data=resp.text, isJSON=False) profile_settings = load_profile(profile_id=1) if is_file_older_than_x_days(file=ADDON_PROFILE + "settings.json", days=1): download_settings() md5JSON = load_file(file='md5.json', isJSON=True) if int(profile_settings['epgrun']) == 0 or int( profile_settings['epgruntime']) < (int(time.time()) - 300): try: if settings.getBool(key="minimalChannels"): try: if profile_settings['base_v3'] == 1: key = 'epg.db.v3.minimal.zip' else: key = 'epg.db.minimal.zip' except: key = 'epg.db.minimal.zip' else: try: if profile_settings['base_v3'] == 1: key = 'epg.db.v3.zip' else: key = 'epg.db.zip' except: key = 'epg.db.zip' if is_file_older_than_x_days( file=ADDON_PROFILE + "epg_all.xml", days=1) or len( profile_settings['epg_md5'] ) == 0 or profile_settings['epg_md5'] != md5JSON[key]: download_epg() except: download_epg() try: if len( profile_settings['images_md5'] ) == 0 or profile_settings['images_md5'] != md5JSON['images.zip']: download_images() except: download_images()
def download_epg(): query = "UPDATE `vars` SET `epgrun`='{epgrun}', `epgruntime`='{epgruntime}' WHERE profile_id={profile_id}".format( epgrun=1, epgruntime=int(time.time()), profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) if settings.getBool(key="minimalChannels"): url = CONST_MINIMALEPG else: url = CONST_EPG try: profile_settings = load_profile(profile_id=1) if profile_settings['base_v3'] == 1: url = url.replace('epg.db.', 'epg.db.v3.') except: pass resp = requests.get(url=url) zipfile = ZipFile(BytesIO(resp.content)) zipfile.extractall(ADDON_PROFILE) zipfile.close() for file in glob.glob(ADDON_PROFILE + "*_replay.xml"): if is_file_older_than_x_days(file=file, days=7): os.remove(file) for file in glob.glob(ADDON_PROFILE + "*_replay.json"): if is_file_older_than_x_days(file=file, days=7): os.remove(file) query = "UPDATE `vars` SET `epgrun`='{epgrun}', `epg_md5`='{epg_md5}' WHERE profile_id={profile_id}".format( epgrun=0, epg_md5=hashlib.md5(resp.content).hexdigest(), profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) clear_prefs_tests() create_playlist() mod_epg()
def check_iptv_link(): if settings.getBool(key='enable_simple_iptv'): try: IPTV_SIMPLE = xbmcaddon.Addon(id="pvr.iptvsimple") if not IPTV_SIMPLE.getSetting("epgPath") == ( ADDON_PROFILE + "epg.xml") or not IPTV_SIMPLE.getSetting( "m3uPath") == (ADDON_PROFILE + "playlist.m3u8"): settings.setBool(key='enable_simple_iptv', value=False) else: profile_settings = load_profile(profile_id=1) if IPTV_SIMPLE.getSetting( "userAgent") != profile_settings['user_agent']: IPTV_SIMPLE.setSetting("userAgent", profile_settings['user_agent']) except: pass
def plugin_ask_for_creds(creds): email_or_pin = settings.getBool(key='email_instead_of_customer') if email_or_pin: if unicode(creds['username']).isnumeric(): creds['username'] = '' username = unicode( gui.input(message=_.ASK_USERNAME2, default=creds['username'])).strip() else: if not unicode(creds['username']).isnumeric(): creds['username'] = '' username = unicode( gui.input(message=_.ASK_USERNAME, default=creds['username'])).strip() if not len(unicode(username)) > 0: if email_or_pin: gui.ok(message=_.EMPTY_USER2, heading=_.LOGIN_ERROR_TITLE) else: gui.ok(message=_.EMPTY_USER, heading=_.LOGIN_ERROR_TITLE) return {'result': False, 'username': '', 'password': ''} if email_or_pin: password = unicode(gui.input(message=_.ASK_PASSWORD2, hide_input=True)).strip() else: password = unicode(gui.input(message=_.ASK_PASSWORD, hide_input=True)).strip() if not len(unicode(password)) > 0: if email_or_pin: gui.ok(message=_.EMPTY_PASS2, heading=_.LOGIN_ERROR_TITLE) else: gui.ok(message=_.EMPTY_PASS, heading=_.LOGIN_ERROR_TITLE) return {'result': False, 'username': '', 'password': ''} return {'result': True, 'username': username, 'password': password}
def download_settings(): resp = requests.get(url=CONST_SETTINGS) write_file(file='settings.json', data=resp.text, isJSON=False) if settings.getBool(key='enable_radio'): resp = requests.get(url=CONST_RADIO) write_file(file='radio.m3u8', data=resp.text, isJSON=False) combine_playlist() settingsJSON = load_file(file='settings.json', isJSON=True) try: user_agent = settingsJSON['user_agent'] except: user_agent = DEFAULT_USER_AGENT query = "UPDATE `vars` SET `user_agent`='{user_agent}' WHERE profile_id={profile_id}".format( user_agent=user_agent, profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True)
def api_play_url(type, channel=None, id=None, video_data=None, from_beginning=0, pvr=0): playdata = {'path': '', 'license': '', 'info': '', 'properties': {}} if not api_get_session(): return playdata from_beginning = int(from_beginning) pvr = int(pvr) profile_settings = load_profile(profile_id=1) found_alt = False info = {} properties = {} headers = {'Authorization': 'Bearer ' + profile_settings['session_token']} if type == 'channel': info_url = '{api_url}/assets/{channel}'.format(api_url=CONST_DEFAULT_API, channel=channel) else: info_url = '{api_url}/assets/{id}'.format(api_url=CONST_DEFAULT_API, id=id) play_url = info_url + '/play' session_post_data = { "player": { "name":"Bitmovin", "version":"8.22.0", "capabilities": { "mediaTypes": ["DASH","HLS","MSSS","Unspecified"], "drmSystems": ["Widevine"], }, "drmSystems": ["Widevine"], }, } if not pvr == 1 or settings.getBool(key='ask_start_from_beginning') or from_beginning == 1: download = api_download(url=info_url, type='get', headers=headers, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key(data, 'id'): return playdata info = data if type == 'channel' and check_key(data, 'params') and check_key(data['params'], 'now') and check_key(data['params']['now'], 'id'): play_url2 = '{api_url}/assets/{id}/play'.format(api_url=CONST_DEFAULT_API, id=data['params']['now']['id']) info = data['params']['now'] if from_beginning == 1: download = api_download(url=play_url2, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and check_key(data, 'url'): if check_key(data, 'drm') and check_key(data['drm'], 'licenseUrl'): license = data['drm']['licenseUrl'] path = data['url'] found_alt = True if not from_beginning == 1 or not found_alt: download = api_download(url=play_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key(data, 'url'): return playdata if check_key(data, 'drm') and check_key(data['drm'], 'licenseUrl'): license = data['drm']['licenseUrl'] path = data['url'] playdata = {'path': path, 'license': license, 'info': info, 'properties': properties} return playdata
def plugin_process_watchlist(data): items = [] if check_key(data, 'entries'): for row in data['entries']: context = [] if check_key(row, 'mediaGroup') and check_key(row['mediaGroup'], 'medium') and check_key(row['mediaGroup'], 'id'): currow = row['mediaGroup'] id = currow['id'] elif check_key(row, 'mediaItem') and check_key(row['mediaItem'], 'medium') and check_key(row['mediaItem'], 'mediaGroupId'): currow = row['mediaItem'] id = currow['mediaGroupId'] else: continue if not check_key(currow, 'title'): continue context.append((_.REMOVE_FROM_WATCHLIST, 'RunPlugin({context_url})'.format(context_url=plugin.url_for(func_or_url=remove_from_watchlist, id=id)), )) if check_key(currow, 'isReplayTv') and currow['isReplayTv'] == "false": if not settings.getBool('showMoviesSeries'): continue type = 'vod' else: type = 'program' channel = '' mediatype = '' duration = '' description = '' program_image = '' program_image_large = '' playable = False path = '' if check_key(currow, 'description'): description = currow['description'] if check_key(currow, 'images'): program_image = get_image("boxart", currow['images']) program_image_large = get_image("HighResLandscape", currow['images']) if program_image_large == '': program_image_large = program_image else: program_image_large += '?w=1920&mode=box' if currow['medium'] == 'TV': if not check_key(currow, 'seriesLinks'): path = plugin.url_for(func_or_url=watchlist_listing, label=currow['title'], id=id, search=0) else: path = plugin.url_for(func_or_url=vod_series, type='series', label=currow['title'], id=id) elif currow['medium'] == 'Movie': if check_key(currow, 'duration'): duration = int(currow['duration']) elif check_key(currow, 'startTime') and check_key(currow, 'endTime'): duration = int(int(currow['endTime']) - int(currow['startTime'])) // 1000 else: duration = 0 path = plugin.url_for(func_or_url=play_video, type=type, channel=channel, id=currow['id'], title=None) playable = True mediatype = 'video' items.append(plugin.Item( label = currow['title'], info = { 'plot': description, 'duration': duration, 'mediatype': mediatype, 'sorttitle': currow['title'].upper(), }, art = { 'thumb': program_image, 'fanart': program_image_large }, path = path, playable = playable, context = context )) return items
def api_login(): creds = get_credentials() username = creds['username'] password = creds['password'] try: os.remove(ADDON_PROFILE + 'stream_cookies') except: pass profile_settings = load_profile(profile_id=1) if not profile_settings or not check_key( profile_settings, 'devicekey') or len( profile_settings['devicekey']) == 0: devicekey = ''.join( random.choice(string.ascii_uppercase + string.ascii_lowercase + string.digits) for _ in range(64)) profile_settings['devicekey'] = devicekey save_profile(profile_id=1, profile=profile_settings) session_url = '{api_url}/USER/SESSIONS/'.format(api_url=CONST_DEFAULT_API) email_or_pin = settings.getBool(key='email_instead_of_customer') if email_or_pin: session_post_data = { "credentialsExtAuth": { 'credentials': { 'loginType': 'UsernamePassword', 'username': username, 'password': password, 'appId': 'KPN', }, 'remember': 'Y', 'deviceInfo': { 'deviceId': profile_settings['devicekey'], 'deviceIdType': 'DEVICEID', 'deviceType': 'PCTV', 'deviceVendor': DEFAULT_BROWSER_NAME, 'deviceModel': DEFAULT_BROWSER_VERSION, 'deviceFirmVersion': DEFAULT_OS_NAME, 'appVersion': DEFAULT_OS_VERSION } }, } else: session_post_data = { "credentialsStdAuth": { 'username': username, 'password': password, 'remember': 'Y', 'deviceRegistrationData': { 'deviceId': profile_settings['devicekey'], 'accountDeviceIdType': 'DEVICEID', 'deviceType': 'PCTV', 'vendor': DEFAULT_BROWSER_NAME, 'model': DEFAULT_BROWSER_VERSION, 'deviceFirmVersion': DEFAULT_OS_NAME, 'appVersion': DEFAULT_OS_VERSION } }, } download = api_download(url=session_url, type='post', headers=None, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'resultCode') or not data['resultCode'] == 'OK': return {'code': code, 'data': data, 'result': False} return {'code': code, 'data': data, 'result': True}
def update_library(): #if check_loggedin(ADDON_ID): librarysettings = {} librarysettings['library_movies'] = settings.getInt(key='library_movies') librarysettings['library_shows'] = settings.getInt(key='library_shows') movies_added = False shows_added = False movies_removed = False shows_removed = False if librarysettings['library_movies'] == 0: for file in glob.glob(os.path.join(ADDON_PROFILE, "movies", "*.*")): movies_removed = True os.remove(file) if librarysettings['library_shows'] == 0: for file in glob.glob(os.path.join(ADDON_PROFILE, "shows", "*.*")): shows_removed = True os.remove(file) if librarysettings['library_movies'] > 0 or librarysettings[ 'library_shows'] > 0: log('Update Dut-IPTV Library for {}'.format(PROVIDER_NAME)) skiplist = [] skiplist2 = [] if librarysettings['library_movies'] == 1 or librarysettings[ 'library_shows'] == 1: data = api_list_watchlist(type='watchlist') if data: processed = plugin_process_watchlist(data=data, type='watchlist') if processed: for ref in processed: currow = processed[ref] if currow['type'] == 'movie': skiplist.append(ref) elif currow['type'] == 'series': skiplist2.append(ref) movie_list = [] if librarysettings['library_movies'] > 0: for type in CONST_LIBRARY['movies']: if settings.getBool(key='library_movies_' + str(type), default=False): result = create_stream(type, 'movies', librarysettings['library_movies'], skiplist) movie_list.extend(result['list']) if result['add'] == True: movies_added = True for file in glob.glob(os.path.join(ADDON_PROFILE, "movies", "*.*")): filename = os.path.basename(file) if not filename in movie_list: movies_removed = True try: os.remove(file) except: pass shows_list = [] remove_shows = [] remove_shows2 = [] if librarysettings['library_shows'] > 0: if librarysettings['library_shows'] == 2: api_get_series_nfo() for type in CONST_LIBRARY['shows']: if settings.getBool(key='library_shows_' + str(type), default=False): result = create_stream(type, 'shows', librarysettings['library_shows'], skiplist2) shows_list.extend(result['list']) if result['add'] == True: shows_added = True for file in glob.glob(os.path.join(ADDON_PROFILE, "shows", "*"), recursive=False): filename = os.path.basename(os.path.normpath(file)) if not filename in shows_list: shows_removed = True try: os.remove( os.path.join(ADDON_PROFILE, "shows", filename, 'tvshow.nfo')) remove_shows.append( os.path.join(ADDON_PROFILE, "shows", filename, "")) except: pass for file in glob.glob(os.path.join(ADDON_PROFILE, "shows", "*", "*", "*.*"), recursive=False): filename = os.path.basename(file) if not filename in shows_list: shows_removed = True try: os.remove(file) except: pass index = 0 for root, dirs, files in os.walk(os.path.join(ADDON_PROFILE, "shows")): for dir in dirs: newDir = os.path.join(root, dir) index += 1 try: os.removedirs(newDir) remove_shows2.append(os.path.join(newDir, "")) shows_removed = True except: pass for removal in remove_shows: clean_library(show_dialog=False, path=removal) #Manual DB removal? for removal2 in remove_shows2: clean_library(show_dialog=False, path=removal2) #Manual DB removal? if movies_added == True or shows_added == True: if movies_added == True: scan_library(show_dialog=False, path=os.path.join(ADDON_PROFILE, "movies", "")) if shows_added == True: scan_library(show_dialog=False, path=os.path.join(ADDON_PROFILE, "shows", "")) if movies_removed == True or shows_removed == True: clean_library(show_dialog=False)
def create_nfo_file(filename, data, type): doc = Document() if type == 'movie': root = doc.createElement("movie") elif type == 'show': root = doc.createElement("tvshow") else: root = doc.createElement("episodedetails") if len(str(data['title'])) == 0: data['title'] = 'Aflevering {episode}'.format( episode=data['position']) doc.appendChild(root) XMLvalues = {} XMLvalues['title'] = str(data['title']) if len(str(data['description'])) > 0: XMLvalues['plot'] = str(data['description']) if not type == 'show' and len(str(data['duration'])) > 0 and int( data['duration']) > 0: XMLvalues['runtime'] = str(int(int(data['duration']) / 60)) if len(str(data['datum'])) > 3: XMLvalues['year'] = str(data['datum'])[:4] for value in XMLvalues: tempChild = doc.createElement(value) root.appendChild(tempChild) nodeText = doc.createTextNode(XMLvalues[value].strip()) tempChild.appendChild(nodeText) tempChild = doc.createElement('uniqueid') tempChild.setAttribute("type", str(PROVIDER_NAME)) tempChild.setAttribute("default", 'true') root.appendChild(tempChild) nodeText = doc.createTextNode(str(data['id']).strip()) tempChild.appendChild(nodeText) if not type == 'episode': if type == 'show': genres = data['category'] else: genres = data['category'].split(', ') if len(genres) > 0: for genre in genres: tempChild = doc.createElement('genre') root.appendChild(tempChild) nodeText = doc.createTextNode(str(genre).strip()) tempChild.appendChild(nodeText) if check_key(data, 'seasons'): for season in data['seasons']: origtitle = data['seasons'][season] tempChild = doc.createElement('namedseason') if str(origtitle).strip().isnumeric(): nodeText = doc.createTextNode('Seizoen ' + str(origtitle).strip()) else: nodeText = doc.createTextNode(str(origtitle).strip()) tempChild.appendChild(nodeText) tempChild.setAttribute("number", season) root.appendChild(tempChild) tempChild = doc.createElement('thumb') if type == 'movie' or type == 'show': tempChild.setAttribute("aspect", 'poster') else: tempChild.setAttribute("aspect", 'thumb') root.appendChild(tempChild) if len(str(data['icon_poster'])) > 0: if settings.getBool('use_small_images', default=False) == True: nodeText = doc.createTextNode( str(data['icon_poster'].replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['small'])).strip()) else: nodeText = doc.createTextNode( str(data['icon_poster'].replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['large'])).strip()) elif len(str(data['icon_still'])) > 0: if settings.getBool('use_small_images', default=False) == True: nodeText = doc.createTextNode( str(data['icon_still'].replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['small'])).strip()) else: nodeText = doc.createTextNode( str(data['icon_still'].replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['large'])).strip()) tempChild.appendChild(nodeText) if not os.path.isfile(filename + '.nfo'): write_file(file=filename + '.nfo', data=doc.toprettyxml(), ext=True, isJSON=False) return True else: if not load_file(filename + '.nfo', ext=True, isJSON=False) == doc.toprettyxml(): write_file(file=filename + '.nfo', data=doc.toprettyxml(), ext=True, isJSON=False) if type == 'movie': method = 'VideoLibrary.GetMovies' basefilename = os.path.basename(os.path.normpath(filename)) path = os.path.dirname(filename) params = { "filter": { "and": [{ "operator": "contains", "field": "path", "value": path }, { "operator": "is", "field": "filename", "value": str(basefilename) + '.strm' }] } } result = json_rpc(method, params) if result and check_key( result, 'movies') and len(result['movies']) > 0: libraryid = result['movies'][0]['movieid'] method = 'VideoLibrary.RefreshMovie' params = {"movieid": libraryid} result = json_rpc(method, params) elif type == 'show': method = 'VideoLibrary.GetTVShows' path = os.path.dirname(filename) params = { "filter": { "operator": "contains", "field": "path", "value": path } } result = json_rpc(method, params) if result and check_key( result, 'tvshows') and len(result['tvshows']) > 0: libraryid = result['tvshows'][0]['tvshowid'] method = 'VideoLibrary.RefreshTVShow' params = {"tvshowid": libraryid} result = json_rpc(method, params) else: method = 'VideoLibrary.GetEpisodes' params = { "filter": { "operator": "contains", "field": "filename", "value": filename } } result = json_rpc(method, params) if result and check_key( result, 'episodes') and len(result['episodes']) > 0: libraryid = result['episodes'][0]['episodeid'] method = 'VideoLibrary.RefreshEpisode' params = {"episodeid": libraryid} result = json_rpc(method, params) return True else: return False
def play(self): try: if 'seekTime' in self.properties or sys.argv[3] == 'resume:true': self.properties.pop('ResumeTime', None) self.properties.pop('TotalTime', None) except: pass device_id = plugin_get_device_id if not device_id: method = 'settings.GetSettingValue' cursetting = {} cursetting['debug.extralogging'] = json_rpc( method, {"setting": "debug.extralogging"})['value'] cursetting['debug.showloginfo'] = json_rpc( method, {"setting": "debug.showloginfo"})['value'] cursetting['debug.setextraloglevel'] = json_rpc( method, {"setting": "debug.setextraloglevel"})['value'] method = 'settings.SetSettingValue' json_rpc(method, { "setting": "debug.extralogging", "value": "true" }) json_rpc(method, {"setting": "debug.showloginfo", "value": "true"}) json_rpc(method, { "setting": "debug.setextraloglevel", "value": [64] }) if settings.getBool(key='disable_subtitle'): self.properties['disable_subtitle'] = 1 li = self.get_li() handle = _handle() #if 'seekTime' in self.properties: #li.setProperty('ResumeTime', str(self.properties['seekTime'])) #if 'totalTime' in self.properties: # li.setProperty('TotalTime', str(self.properties['totalTime'])) #else: # li.setProperty('TotalTime', '999999') player = MyPlayer() playbackStarted = False seekTime = False replay_pvr = False if handle > 0: if 'Replay' in self.properties or 'PVR' in self.properties: replay_pvr = True self.properties.pop('Replay', None) self.properties.pop('PVR', None) xbmcplugin.setResolvedUrl(handle, True, li) else: xbmcplugin.setResolvedUrl(handle, False, li) player.play(self.path, li) else: player.play(self.path, li) currentTime = 0 upnext = settings.getBool('upnext_enabled') while player.is_active: if xbmc.getCondVisibility("Player.HasMedia") and player.is_started: if playbackStarted == False: playbackStarted = True if upnext: upnext = False result = json_rpc("XBMC.GetInfoLabels", { "labels": ["VideoPlayer.DBID", "VideoPlayer.TvShowDBID"] }) if result and len(str( result['VideoPlayer.DBID'])) > 0 and len( str(result['VideoPlayer.TvShowDBID'])) > 0: result2 = json_rpc( "VideoLibrary.GetEpisodes", { "tvshowid": int(result['VideoPlayer.TvShowDBID']), "properties": [ "title", "plot", "rating", "firstaired", "playcount", "runtime", "season", "episode", "showtitle", "fanart", "thumbnail", "art" ] }) nextep = 0 current_episode = dict() next_episode = dict() if result2: for result3 in result2['episodes']: if nextep == 0 and int( result3['episodeid']) == int( result['VideoPlayer.DBID']): current_episode = dict( episodeid=result3['episodeid'], tvshowid=int( result['VideoPlayer.TvShowDBID']), title=result3["title"], art=result3["art"], season=result3["season"], episode=result3["episode"], showtitle=result3["showtitle"], plot=result3["plot"], playcount=result3["playcount"], rating=result3["rating"], firstaired=result3["firstaired"], runtime=result3["runtime"]) nextep = 1 elif nextep == 1: params = [] params.append(('_', 'play_dbitem')) params.append(('id', result3['episodeid'])) path = 'plugin://{0}/?{1}'.format( ADDON_ID, urlencode(encode_obj(params))) next_info = dict( current_episode=current_episode, next_episode=dict( episodeid=result3['episodeid'], tvshowid=int(result[ 'VideoPlayer.TvShowDBID']), title=result3["title"], art=result3["art"], season=result3["season"], episode=result3["episode"], showtitle=result3["showtitle"], plot=result3["plot"], playcount=result3["playcount"], rating=result3["rating"], firstaired=result3["firstaired"], runtime=result3["runtime"]), play_url=path, #notification_time=60, #notification_offset=notification_offset, ) upnext_signal(sender=ADDON_ID, next_info=next_info) #upnext_signal(sender=ADDON_ID) break if not device_id: player.stop() if 'disable_subtitle' in self.properties: player.showSubtitles(False) self.properties.pop('disable_subtitle', None) if 'seekTime' in self.properties: seekTime = True xbmc.Monitor().waitForAbort(1) player.seekTime(int(self.properties['seekTime'])) self.properties.pop('seekTime', None) if not replay_pvr and not seekTime and 'Live' in self.properties and 'Live_ID' in self.properties and 'Live_Channel' in self.properties: id = self.properties['Live_ID'] channel = self.properties['Live_Channel'] self.properties.pop('Live', None) self.properties.pop('Live_ID', None) self.properties.pop('Live_Channel', None) wait = 60 end = load_file(file='stream_end', isJSON=False) if end: calc_wait = int(end) - int(time.time()) + 30 if calc_wait > 60: wait = calc_wait while not xbmc.Monitor().waitForAbort( wait) and xbmc.getCondVisibility( "Player.HasMedia") and player.is_started: info = None try: info = api_get_info(id=id, channel=channel) except: pass if info: info2 = { 'plot': str(info['description']), 'title': str(info['label1']), 'tagline': str(info['label2']), 'duration': info['duration'], 'credits': info['credits'], 'cast': info['cast'], 'director': info['director'], 'writer': info['writer'], 'genre': info['genres'], 'year': info['year'], } li.setInfo('video', info2) li.setArt({ 'thumb': info['image'], 'icon': info['image'], 'fanart': info['image_large'] }) try: player.updateInfoTag(li) except: pass wait = 60 end = load_file(file='stream_end', isJSON=False) if end: calc_wait = int(end) - int(time.time()) + 30 if calc_wait > 60: wait = calc_wait xbmc.Monitor().waitForAbort(1) try: currentTime = player.getTime() except: pass if playbackStarted == True: api_clean_after_playback(int(currentTime)) try: if settings.getInt(key='max_bandwidth') > 0: _restore_network_bandwidth() except: pass if not device_id: json_rpc( method, { "setting": "debug.showloginfo", "value": cursetting['debug.showloginfo'] }) json_rpc( method, { "setting": "debug.setextraloglevel", "value": str(', '.join([ str(elem) for elem in cursetting['debug.setextraloglevel'] ])) }) json_rpc( method, { "setting": "debug.extralogging", "value": cursetting['debug.setextraloglevel'] })
def api_test_channels(tested=False, channel=None): profile_settings = load_profile(profile_id=1) if channel: channel = unicode(channel) try: if not profile_settings['last_login_success'] == 1 or not settings.getBool(key='run_tests') or not api_get_session(): return 5 query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=1,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) query = "SELECT * FROM `channels`" channels = query_epg(query=query, return_result=True, return_insert=False, commit=False) results = load_tests(profile_id=1) count = 0 first = True last_tested_found = False test_run = False user_agent = profile_settings['user_agent'] if not results: results = {} for row in channels: if count == 5 or (count == 1 and tested): if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return count id = unicode(row['id']) if len(id) > 0: if channel: if not id == channel: continue elif tested: if unicode(profile_settings['last_tested']) == id: last_tested_found = True continue elif last_tested_found: pass else: continue if check_key(results, id) and not tested and not first: continue livebandwidth = 0 replaybandwidth = 0 live = 0 replay = 0 epg = 0 guide = 0 profile_settings = load_profile(profile_id=1) if profile_settings['last_playing'] > int(time.time() - 300): if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return 5 playdata = api_play_url(type='channel', channel=id, id=None, test=True) if first and not profile_settings['last_login_success']: if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return 5 if len(playdata['path']) > 0: CDMHEADERS = { 'User-Agent': user_agent, 'X_CSRFToken': profile_settings['csrf_token'], 'Cookie': playdata['license']['cookie'], } if check_key(playdata, 'license') and check_key(playdata['license'], 'triggers') and check_key(playdata['license']['triggers'][0], 'licenseURL'): if check_key(playdata['license']['triggers'][0], 'customData'): CDMHEADERS['AcquireLicense.CustomData'] = playdata['license']['triggers'][0]['customData'] CDMHEADERS['CADeviceType'] = 'Widevine OTT client' session = Session(headers=CDMHEADERS) resp = session.get(playdata['path']) if resp.status_code == 200: livebandwidth = find_highest_bandwidth(xml=resp.text) live = 1 if check_key(results, id) and first and not tested: first = False if live == 1: continue else: if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return 5 first = False counter = 0 while not xbmc.Monitor().abortRequested() and counter < 5: if xbmc.Monitor().waitForAbort(1): break counter += 1 profile_settings = load_profile(profile_id=1) if profile_settings['last_playing'] > int(time.time() - 300): if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return 5 if xbmc.Monitor().abortRequested(): return 5 militime = int(int(time.time() - 86400) * 1000) session_post_data = { 'needChannel': '0', 'queryChannel': { 'channelIDs': [ id, ], 'isReturnAllMedia': '1', }, 'queryPlaybill': { 'count': '1', 'endTime': militime, 'isFillProgram': '1', 'offset': '0', 'startTime': militime, 'type': '0', } } headers = {'Content-Type': 'application/json', 'X_CSRFToken': profile_settings['csrf_token']} channel_url = '{base_url}/VSP/V3/QueryPlaybillListStcProps?SID=queryPlaybillListStcProps3&DEVICE=PC&DID={deviceID}&from=throughMSAAccess'.format(base_url=CONST_BASE_URL, deviceID=profile_settings['devicekey']) download = api_download(url=channel_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and check_key(data, 'channelPlaybills') and check_key(data['channelPlaybills'][0], 'playbillLites') and check_key(data['channelPlaybills'][0]['playbillLites'][0], 'ID'): profile_settings = load_profile(profile_id=1) if profile_settings['last_playing'] > int(time.time() - 300): if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return 5 playdata = api_play_url(type='program', channel=id, id=data['channelPlaybills'][0]['playbillLites'][0]['ID'], test=True) if len(playdata['path']) > 0: CDMHEADERS = { 'User-Agent': user_agent, 'X_CSRFToken': profile_settings['csrf_token'], 'Cookie': playdata['license']['cookie'], } if check_key(playdata, 'license') and check_key(playdata['license'], 'triggers') and check_key(playdata['license']['triggers'][0], 'licenseURL'): if check_key(playdata['license']['triggers'][0], 'customData'): CDMHEADERS['AcquireLicense.CustomData'] = playdata['license']['triggers'][0]['customData'] CDMHEADERS['CADeviceType'] = 'Widevine OTT client' session = Session(headers=CDMHEADERS) resp = session.get(playdata['path']) if resp.status_code == 200: replaybandwidth = find_highest_bandwidth(xml=resp.text) replay = 1 query = "SELECT id FROM `epg` WHERE channel='{channel}' LIMIT 1".format(channel=id) data = query_epg(query=query, return_result=True, return_insert=False, commit=False) if len(data) > 0: guide = 1 if live == 1: epg = 1 if not xbmc.Monitor().abortRequested(): query = "UPDATE `vars` SET `last_tested`='{last_tested}' WHERE profile_id={profile_id}".format(last_tested=id,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) query = "REPLACE INTO `tests_{profile_id}` VALUES ('{id}', '{live}', '{livebandwidth}', '{replay}', '{replaybandwidth}', '{epg}', '{guide}')".format(profile_id=1, id=id, live=live, livebandwidth=livebandwidth, replay=replay, replaybandwidth=replaybandwidth, epg=epg, guide=guide) query_settings(query=query, return_result=False, return_insert=False, commit=True) test_run = True counter = 0 while not xbmc.Monitor().abortRequested() and counter < 15: if xbmc.Monitor().waitForAbort(1): break counter += 1 profile_settings = load_profile(profile_id=1) if profile_settings['last_playing'] > int(time.time() - 300): if test_run: update_prefs() query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return 5 if xbmc.Monitor().abortRequested(): return 5 count += 1 except: if test_run: update_prefs() count = 5 query = "UPDATE `vars` SET `test_running`={test_running} WHERE profile_id={profile_id}".format(test_running=0,profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) return count
def api_play_url(type, channel=None, id=None, video_data=None, test=False, from_beginning=0, pvr=0): playdata = { 'path': '', 'license': '', 'info': '', 'alt_path': '', 'alt_license': '' } if not api_get_session(): return playdata alt_path = '' alt_license = '' from_beginning = int(from_beginning) pvr = int(pvr) profile_settings = load_profile(profile_id=1) headers = { 'Content-Type': 'application/json', 'X_CSRFToken': profile_settings['csrf_token'] } mediaID = None info = {} if not type or not len(unicode(type)) > 0: return playdata militime = int(time.time() * 1000) if not type == 'vod': if video_data: try: video_data = json.loads(video_data) mediaID = int(video_data['media_id']) + 1 except: pass data = api_get_channels() try: mediaID = data[unicode(channel)]['assetid'] except: pass if type == 'channel' and channel: if not pvr == 1 or settings.getBool( key='ask_start_from_beginning') or from_beginning == 1: session_post_data = { 'needChannel': '0', 'queryChannel': { 'channelIDs': [ channel, ], 'isReturnAllMedia': '1', }, 'queryPlaybill': { 'count': '1', 'endTime': militime, 'isFillProgram': '1', 'offset': '0', 'startTime': militime, 'type': '0', } } channel_url = '{base_url}/VSP/V3/QueryPlaybillListStcProps?SID=queryPlaybillListStcProps3&DEVICE=PC&DID={deviceID}&from=throughMSAAccess'.format( base_url=CONST_BASE_URL, deviceID=profile_settings['devicekey']) download = api_download(url=channel_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'result') or not check_key( data['result'], 'retCode') or not data['result'][ 'retCode'] == '000000000' or not check_key( data, 'channelPlaybills') or not check_key( data['channelPlaybills'][0], 'playbillLites') or not check_key( data['channelPlaybills'][0] ['playbillLites'][0], 'ID'): return playdata id = data['channelPlaybills'][0]['playbillLites'][0]['ID'] session_post_data = { 'playbillID': id, 'channelNamespace': '310303', 'isReturnAllMedia': '1', } program_url = '{base_url}/VSP/V3/QueryPlaybill?from=throughMSAAccess'.format( base_url=CONST_BASE_URL) download = api_download(url=program_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'result') or not check_key( data['result'], 'retCode') or not data['result'][ 'retCode'] == '000000000' or not check_key( data, 'playbillDetail'): info = {} else: info = data['playbillDetail'] if settings.getBool( key='ask_start_from_beginning') or from_beginning == 1: session_post_data = { "businessType": "PLTV", "channelID": channel, "checkLock": { "checkType": "0", }, "isHTTPS": "1", "isReturnProduct": "1", "mediaID": mediaID, 'playbillID': id, } play_url_path = '{base_url}/VSP/V3/PlayChannel?from=throughMSAAccess'.format( base_url=CONST_BASE_URL) download = api_download(url=play_url_path, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'result') or not check_key( data['result'], 'retCode') or not data['result'][ 'retCode'] == '000000000' or not check_key( data, 'playURL'): pass else: alt_path = data['playURL'] if check_key(data, 'authorizeResult'): profile_settings = load_profile(profile_id=1) data['authorizeResult']['cookie'] = api_getCookies( load_file('stream_cookies'), '') alt_license = data['authorizeResult'] session_post_data = { "businessType": "BTV", "channelID": channel, "checkLock": { "checkType": "0", }, "isHTTPS": "1", "isReturnProduct": "1", "mediaID": mediaID, } elif type == 'program' and id: if not test and not pvr == 1: session_post_data = { 'playbillID': id, 'channelNamespace': '310303', 'isReturnAllMedia': '1', } program_url = '{base_url}/VSP/V3/QueryPlaybill?from=throughMSAAccess'.format( base_url=CONST_BASE_URL) download = api_download(url=program_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'result') or not check_key( data['result'], 'retCode') or not data['result'][ 'retCode'] == '000000000' or not check_key( data, 'playbillDetail'): info = {} else: info = data['playbillDetail'] session_post_data = { "businessType": "CUTV", "channelID": channel, "checkLock": { "checkType": "0", }, "isHTTPS": "1", "isReturnProduct": "1", "mediaID": mediaID, "playbillID": id, } elif type == 'vod' and id: session_post_data = {'VODID': id} program_url = '{base_url}/VSP/V3/QueryVOD?from=throughMSAAccess'.format( base_url=CONST_BASE_URL) download = api_download(url=program_url, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'result') or not check_key( data['result'], 'retCode') or not data['result'][ 'retCode'] == '000000000' or not check_key( data, 'VODDetail') or not check_key( data['VODDetail'], 'VODType'): return playdata info = data['VODDetail'] session_post_data = { "VODID": id, "checkLock": { "checkType": "0", }, "isHTTPS": "1", "isReturnProduct": "1", "mediaID": '', } if not check_key(info, 'mediaFiles') or not check_key( info['mediaFiles'][0], 'ID'): return playdata if check_key(info, 'series') and check_key(info['series'][0], 'VODID'): session_post_data["seriesID"] = info['series'][0]['VODID'] session_post_data["mediaID"] = info['mediaFiles'][0]['ID'] if not len(unicode(session_post_data["mediaID"])) > 0: return playdata if type == 'vod': play_url_path = '{base_url}/VSP/V3/PlayVOD?from=throughMSAAccess'.format( base_url=CONST_BASE_URL) else: play_url_path = '{base_url}/VSP/V3/PlayChannel?from=throughMSAAccess'.format( base_url=CONST_BASE_URL) download = api_download(url=play_url_path, type='post', headers=headers, data=session_post_data, json_data=True, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'result') or not check_key( data['result'], 'retCode' ) or not data['result']['retCode'] == '000000000' or not check_key( data, 'playURL'): return playdata path = data['playURL'] if check_key(data, 'authorizeResult'): profile_settings = load_profile(profile_id=1) data['authorizeResult']['cookie'] = api_getCookies( load_file('stream_cookies'), '') license = data['authorizeResult'] playdata = { 'path': path, 'license': license, 'info': info, 'alt_path': alt_path, 'alt_license': alt_license } return playdata
def plugin_process_vod_season(series, id, data): if not data or not check_key(data, 'details'): return None id_ar = id.split('###') series = id_ar[0] seasonstr = id_ar[1] season = [] seasonno = '' if check_key(data['details'], 'SN' + str(seasonstr)): seasonno = re.sub("[^0-9]", "", data['details']['SN' + str(seasonstr)]['title']) for currow in data['details']: row = data['details'][currow] if check_key(row, 'type') and row['type'] == 'episode': image = '' duration = 0 if check_key(row, 'runtime'): duration = row['runtime'] if check_key(row, 'still'): if settings.getBool('use_small_images', default=False) == True: image = row['still'].replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['small']) else: image = row['still'].replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['large']) if check_key(row, 'title') and len(str(row['title'])) > 0: name = row['title'] else: name = 'Aflevering {position}'.format(position=row['position']) label = '{seasonno}.{episode} - {title}'.format( seasonno=seasonno, episode=row['position'], title=name) season.append({ 'label': label, 'id': 'E' + str(series) + '###' + str(seasonstr) + '###' + str(row['id']), 'media_id': '', 'duration': duration, 'title': name, 'episodeNumber': row['position'], 'description': row['description'], 'image': image }) return season
def do_GET(self): try: self._stream_url except: profile_settings = load_profile(profile_id=1) self._stream_url = profile_settings['stream_hostname'] try: self._last_playing except: self._last_playing = 0 if "status" in self.path: self.send_response(200) self.send_header('X-TEST', 'OK') self.end_headers() elif proxy_get_match(self.path): profile_settings = load_profile(profile_id=1) self._stream_url = profile_settings['stream_hostname'] URL = proxy_get_url(self) session = proxy_get_session(self) r = session.get(URL) xml = r.text xml = set_duration(xml=xml) if settings.getBool(key='disable_subtitle'): xml = remove_subs(xml=xml) if settings.getBool(key='force_highest_bandwidth'): xml = force_highest_bandwidth(xml=xml) xml = proxy_xml_mod(xml) self.send_response(r.status_code) r.headers['Content-Length'] = len(xml) for header in r.headers: if not 'Content-Encoding' in header and not 'Transfer-Encoding' in header: self.send_header(header, r.headers[header]) self.end_headers() try: xml = xml.encode('utf-8') except: pass try: self.wfile.write(xml) except: pass else: URL = proxy_get_url(self) self._now_playing = int(time.time()) if self._last_playing + 60 < self._now_playing: self._last_playing = int(time.time()) query = "UPDATE `vars` SET `last_playing`='{last_playing}' WHERE profile_id={profile_id}".format(last_playing=self._last_playing, profile_id=1) query_settings(query=query, return_result=False, return_insert=False, commit=True) self.send_response(302) self.send_header('Location', URL) self.end_headers()
def plugin_process_info(playdata): info = { 'label1': '', 'label2': '', 'description': '', 'image': '', 'image_large': '', 'duration': 0, 'credits': [], 'cast': [], 'director': [], 'writer': [], 'genres': [], 'year': '', } if check_key(playdata['info'], 'title'): info['label1'] += playdata['info']['title'] info['label2'] = playdata['info']['title'] if check_key(playdata['info'], 'runtime'): info['duration'] = int(playdata['info']['runtime']) if check_key(playdata['info'], 'description'): info['description'] = playdata['info']['description'] if check_key(playdata['info'], 'still'): if settings.getBool('use_small_images', default=False) == True: info['image'] = str(playdata['info']['still']).replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['small']) info['image_large'] = str(playdata['info']['still']).replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['small']) else: info['image'] = str(playdata['info']['still']).replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['large']) info['image_large'] = str(playdata['info']['still']).replace( CONST_IMAGES['still']['replace'], CONST_IMAGES['still']['large']) elif check_key(playdata['info'], 'poster'): if settings.getBool('use_small_images', default=False) == True: info['image'] = str(playdata['info']['poster']).replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['small']) info['image_large'] = str(playdata['info']['poster']).replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['small']) else: info['image'] = str(playdata['info']['poster']).replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['large']) info['image_large'] = str(playdata['info']['poster']).replace( CONST_IMAGES['poster']['replace'], CONST_IMAGES['poster']['large']) if check_key(playdata['info'], 'year'): info['year'] = playdata['info']['year'] if check_key(playdata['info'], 'cast') and check_key( playdata['info']['cast'], 'actors'): info['cast'] = playdata['info']['cast']['actors'] if check_key(playdata['info'], 'genres'): info['genres'] = playdata['info']['genres'] if check_key(playdata['info'], 'directors'): info['director'] = playdata['info']['directors'] return info
def api_search(query): if not api_get_session(): return None profile_settings = load_profile(profile_id=1) encodedBytes = base64.b32encode(query.encode("utf-8")) queryb32 = str(encodedBytes, "utf-8") file = "cache" + os.sep + "{query}.json".format(query=queryb32) headers = {'Authorization': 'Bearer ' + profile_settings['session_token']} search_url = '{api_url}/search?query={query}'.format(api_url=CONST_DEFAULT_API, query=quote_plus(query)) if not is_file_older_than_x_days(file=ADDON_PROFILE + file, days=0.5): data = load_file(file=file, isJSON=True) else: download = api_download(url=search_url, type='get', headers=headers, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and check_key(data, 'collection'): write_file(file=file, data=data, isJSON=True) if not data or not check_key(data, 'collection'): return None items = [] items_vod = [] items_program = [] for currow in data['collection']: if not settings.getBool('showMoviesSeries') and currow['label'] == 'sg.ui.search.vod': continue elif currow['label'] == 'sg.ui.search.epg': continue if currow['label'] == 'sg.ui.search.vod': type = 'vod' else: type = 'program' for row in currow['assets']: if not check_key(row, 'id') or not check_key(row, 'title'): continue item = {} id = row['id'] label = row['title'] description = '' duration = 0 program_image = '' program_image_large = '' start = '' if check_key(row, 'images'): program_image = row['images'][0]['url'] program_image_large = row['images'][0]['url'] if type == 'vod': item_type = 'Vod' label += " (VOD)" else: item_type = 'Epg' label += " (ReplayTV)" if check_key(row, 'params'): if check_key(row['params'], 'duration'): duration = int(row['params']['duration']) elif check_key(row['params'], 'start') and check_key(row['params'], 'end'): duration = int(re.sub('[^0-9]','', row['params']['end'])) - int(re.sub('[^0-9]','', row['params']['end'])) item['id'] = id item['title'] = label item['description'] = description item['duration'] = duration item['type'] = item_type item['icon'] = program_image_large item['start'] = start if type == "vod": items_vod.append(item) else: items_program.append(item) #num = min(len(items_program), len(items_vod)) #items = [None]*(num*2) #items[::2] = items_program[:num] #items[1::2] = items_vod[:num] #items.extend(items_program[num:]) #items.extend(items_vod[num:]) items = items_program return items
def api_search(query): if not api_get_session(): return None profile_settings = load_profile(profile_id=1) if int(profile_settings['v3']) == 1: return False end = int(time.time() * 1000) start = end - (7 * 24 * 60 * 60 * 1000) vodstr = '' encodedBytes = base64.b32encode(query.encode("utf-8")) queryb32 = unicode(encodedBytes, "utf-8") file = "cache" + os.sep + "{query}.json".format(query=queryb32) try: profile_settings = load_profile(profile_id=1) if int(profile_settings['v3']) == 1: file = "cache" + os.sep + "{query}.v3.json".format(query=queryb32) except: pass search_url = '{search_url}?byBroadcastStartTimeRange={start}~{end}&numItems=25&byEntitled=true&personalised=true&q={query}'.format( search_url=CONST_API_URLS[int(profile_settings['v3'])]['search_url'], start=start, end=end, query=quote(query)) if not is_file_older_than_x_days(file=ADDON_PROFILE + file, days=0.5): data = load_file(file=file, isJSON=True) else: download = api_download(url=search_url, type='get', headers=api_get_headers(), data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if code and code == 200 and data and (check_key( data, 'tvPrograms') or check_key(data, 'moviesAndSeries')): write_file(file=file, data=data, isJSON=True) if not data or (not check_key(data, 'tvPrograms') and not check_key(data, 'moviesAndSeries')): return False items = [] items_vod = [] items_program = [] vod_links = {} if not settings.getBool('showMoviesSeries'): try: data.pop('moviesAndSeries', None) except: pass else: for entry in CONST_VOD_CAPABILITY: data2 = api_get_vod_by_type(type=entry['file'], character=None, subscription_filter=None) for currow in data2: row = data2[currow] vod_links[row['id']] = {} vod_links[row['id']]['seasons'] = row['seasons'] vod_links[row['id']]['duration'] = row['duration'] vod_links[row['id']]['desc'] = row['description'] vod_links[row['id']]['type'] = row['type'] for currow in list(data): if currow == "moviesAndSeries": type = 'vod' else: type = 'program' for row in data[currow]['entries']: if not check_key(row, 'id') or not check_key(row, 'title'): continue item = {} id = row['id'] label = row['title'] description = '' duration = 0 program_image = '' program_image_large = '' start = '' if check_key(row, 'images'): program_image = get_image("boxart", row['images']) program_image_large = get_image("HighResLandscape", row['images']) if program_image_large == '': program_image_large = program_image else: program_image_large += '?w=1920&mode=box' if type == 'vod': if check_key(vod_links, row['id']): description = vod_links[row['id']]['desc'] item_type = vod_links[row['id']]['type'] else: item_type = 'Vod' label += " (Movies and Series)" else: item_type = 'Epg' label += " (ReplayTV)" if check_key(row, 'groupType') and row['groupType'] == 'show': if check_key(row, 'episodeMatch') and check_key( row['episodeMatch'], 'seriesEpisodeNumber') and check_key( row['episodeMatch'], 'secondaryTitle'): if len(description) == 0: description += label season = '' if check_key(row, 'seriesNumber'): season = "S" + row['seriesNumber'] description += " Episode Match: {season}E{episode} - {secondary}".format( season=season, episode=row['episodeMatch']['seriesEpisodeNumber'], secondary=row['episodeMatch']['secondaryTitle']) else: if check_key(row, 'duration'): duration = int(row['duration']) elif check_key(row, 'episodeMatch') and check_key( row['episodeMatch'], 'startTime') and check_key( row['episodeMatch'], 'endTime'): duration = int( int(row['episodeMatch']['endTime']) - int(row['episodeMatch']['startTime'])) // 1000 id = row['episodeMatch']['id'] elif check_key(vod_links, row['id']) and check_key( vod_links[row['id']], 'duration'): duration = vod_links[row['id']]['duration'] item['id'] = id item['title'] = label item['description'] = description item['duration'] = duration item['type'] = item_type item['icon'] = program_image_large item['start'] = start if type == "vod": items_vod.append(item) else: items_program.append(item) num = min(len(items_program), len(items_vod)) items = [None] * (num * 2) items[::2] = items_program[:num] items[1::2] = items_vod[:num] items.extend(items_program[num:]) items.extend(items_vod[num:]) return items
def api_play_url(type, channel=None, id=None, video_data=None, from_beginning=0, pvr=0): playdata = { 'path': '', 'license': '', 'info': '', 'alt_path': '', 'alt_license': '' } if not api_get_session(): return playdata from_beginning = int(from_beginning) pvr = int(pvr) profile_settings = load_profile(profile_id=1) headers = { 'authorization': 'Bearer {id_token}'.format(id_token=profile_settings['access_token']) } alt_path = '' alt_license = '' found_alt = False friendly = '' info = {} data = api_get_channels() try: friendly = data[unicode(channel)]['assetid'] except: pass if not type == 'vod' and (pvr == 0 or settings.getBool( key='ask_start_from_beginning') or from_beginning == 1): if type == 'channel' and friendly: channel_url = '{base_url}/v6/epg/locations/{friendly}/live/1?fromDate={date}'.format( base_url=CONST_API_URL, friendly=friendly, date=datetime.datetime.now().strftime("%Y-%m-%dT%H%M%S")) download = api_download(url=channel_url, type='get', headers=None, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data: return playdata for row in data: if not check_key(row, 'Channel') or not check_key( row, 'Locations'): return playdata for row2 in row['Locations']: id = row2['LocationId'] if not id: return playdata location_url = '{base_url}/v6/epg/location/{location}'.format( base_url=CONST_API_URL, location=id) download = api_download(url=location_url, type='get', headers=None, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data: return playdata info = data timeshift = '' if check_key( info, 'VodContentId') and len(unicode(info['VodContentId'])) > 0: timeshift = info['VodContentId'] play_url = '{base_url}/v6/stream/handshake/Widevine/dash/VOD/{id}?playerName=NLZIET%20Meister%20Player%20Web&profile=default&maxResolution=×hift={timeshift}'.format( base_url=CONST_API_URL, id=info['VodContentId'], timeshift=timeshift) download = api_download(url=play_url, type='get', headers=headers, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'uri'): pass else: alt_license = data alt_path = data['uri'] found_alt = True elif type == 'channel' and channel and friendly: timeshift = 'false' play_url = '{base_url}/v6/stream/handshake/Widevine/dash/Restart/{id}?playerName=NLZIET%20Meister%20Player%20Web&profile=default&maxResolution=×hift={timeshift}'.format( base_url=CONST_API_URL, id=id, timeshift=timeshift) download = api_download(url=play_url, type='get', headers=headers, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'uri'): pass else: alt_license = data alt_path = data['uri'] found_alt = True if type == 'vod': play_url = '{base_url}/v6/playnow/ondemand/0/{location}'.format( base_url=CONST_API_URL, location=id) download = api_download(url=play_url, type='get', headers=headers, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'VideoInformation'): return playdata info = data['VideoInformation'] url_base = '{base_url}/v6/stream/handshake/Widevine/dash/VOD/{id}'.format( base_url=CONST_API_URL, id=info['Id']) timeshift = info['Id'] elif type == 'channel' and channel and friendly: url_base = '{base_url}/v6/stream/handshake/Widevine/dash/Live/{friendly}'.format( base_url=CONST_API_URL, friendly=friendly) timeshift = 'false' else: if len(unicode(alt_path)) == 0: url_base = '{base_url}/v6/stream/handshake/Widevine/dash/Replay/{id}'.format( base_url=CONST_API_URL, id=id) timeshift = id else: license = alt_license = data path = alt_path alt_license = '' alt_path = '' if not type == 'program' or found_alt == False: play_url = '{url_base}?playerName=NLZIET%20Meister%20Player%20Web&profile=default&maxResolution=×hift={timeshift}'.format( url_base=url_base, timeshift=timeshift) download = api_download(url=play_url, type='get', headers=headers, data=None, json_data=False, return_json=True) data = download['data'] code = download['code'] if not code or not code == 200 or not data or not check_key( data, 'uri'): return playdata license = data path = data['uri'] if not len(unicode(license)) > 0: return playdata playdata = { 'path': path, 'license': license, 'info': info, 'alt_path': alt_path, 'alt_license': alt_license } return playdata