def get_media_info(video_node): progress = 0 if None is not video_node.get('viewOffset') and None is not video_node.get('duration'): progress = try_int(video_node.get('viewOffset')) * 100 / try_int(video_node.get('duration')) for media in video_node.findall('Media'): for part in media.findall('Part'): file_name = part.get('file') # if '3' > sys.version: # remove HTML quoted characters, only works in python < 3 # file_name = urllib2.unquote(file_name.encode('utf-8', errors='replace')) # else: file_name = unquote(file_name) return {'path_file': file_name, 'media_id': video_node.get('ratingKey'), 'played': int(video_node.get('viewCount') or 0), 'progress': progress}
def prepare_failed_name(release): """Standardizes release name for failed DB :param release: release name :type release: AnyStr :return: standardized release name :rtype: AnyStr """ fixed = unquote(release) if fixed.endswith('.nzb'): fixed = fixed.rpartition('.')[0] fixed = re.sub(r'[.\-+ ]', '_', fixed) # noinspection PyUnresolvedReferences if PY2 and not isinstance(fixed, unicode): fixed = text_type(fixed, 'utf-8', 'replace') return fixed
def _authorised(self, **kwargs): result = False if self.digest: digest = [x[::-1] for x in self.digest[::-1].rpartition('=')] self.digest = digest[2] + digest[1] + quote(unquote(digest[0])) params = dict(logged_in=(lambda y='': all([ self.url and self.session.cookies.get_dict( domain='.' + urlparse(self.url).netloc) and self.session. cookies.clear('.' + urlparse(self.url).netloc) is None or True ] + [ 'RSS' in y, 'type="password"' not in y, self.has_all_cookies(['speedian'], 'inSpeed_') ] + [(self.session.cookies.get('inSpeed_' + c) or 'sg!no!pw') in self.digest for c in ['speedian']])), failed_msg=(lambda y=None: None), post_params={'login': False}) result = super(SpeedCDProvider, self)._authorised(**params) if not result and not self.failure_count: if self.url and self.digest: self.get_url('%slogout.php' % self.url, skip_auth=True, post_data={ 'submit.x': 24, 'submit.y': 11 }) self.digest = '' params = dict( logged_in=(lambda y='': all([ self.session.cookies.get_dict(domain='.speed.cd') and self. session.cookies.clear('.speed.cd') is None or True ] + [bool(y), not re.search('(?i)type="password"', y)] + [ re.search('(?i)Logout', y) or not self.digest or (self.session.cookies.get('inSpeed_speedian') or 'sg!no!pw' ) in self.digest ])), failed_msg= (lambda y='': (re.search( r'(?i)(username|password)((<[^>]+>)|\W)*' + r'(or|and|/|\s)((<[^>]+>)|\W)*(password|incorrect)', y ) and u'Invalid username or password for %s. Check settings' or u'Failed to authenticate or parse a response from %s, abort provider' )), post_params={'form_tmpl': True}) self.urls['login_action'] = self.urls.get('do_login') session = super(SpeedCDProvider, self)._authorised(session=None, resp_sess=True, **params) self.urls['login_action'] = '' if session: self.digest = 'inSpeed_speedian=%s' % session.cookies.get( 'inSpeed_speedian') sickbeard.save_config() result = True logger.log('Cookie details for %s updated.' % self.name, logger.DEBUG) elif not self.failure_count: logger.log( 'Invalid cookie details for %s and login failed. Check settings' % self.name, logger.ERROR) return result
def _update(self, host=None, show_name=None): """ Handle updating Kodi host via HTTP API Update the video library for a specific tv show if passed, otherwise update the whole library if option enabled. Args: show_name: Name of a TV show to target for a library update Return: True or False """ if not host: self._log_warning(u'No host specified, aborting update') return False self._log_debug(u'Updating library via HTTP method for host: %s' % host) # if we're doing per-show if show_name: self._log_debug(u'Updating library via HTTP method for show %s' % show_name) # noinspection SqlResolve path_sql = 'SELECT path.strPath' \ ' FROM path, tvshow, tvshowlinkpath' \ ' WHERE tvshow.c00 = "%s"' % show_name \ + ' AND tvshowlinkpath.idShow = tvshow.idShow' \ ' AND tvshowlinkpath.idPath = path.idPath' # set xml response format, if this fails then don't bother with the rest if not self._send( host, { 'command': 'SetResponseFormat(webheader;false;webfooter;false;header;<xml>;footer;</xml>;' 'opentag;<tag>;closetag;</tag>;closefinaltag;false)' }): return False # sql used to grab path(s) response = self._send( host, {'command': 'QueryVideoDatabase(%s)' % path_sql}) if not response: self._log_debug(u'Invalid response for %s on %s' % (show_name, host)) return False try: et = XmlEtree.fromstring(quote(response, ':\\/<>')) except SyntaxError as e: self._log_error(u'Unable to parse XML in response: %s' % ex(e)) return False paths = et.findall('.//field') if not paths: self._log_debug(u'No valid path found for %s on %s' % (show_name, host)) return False for path in paths: # we do not need it double-encoded, gawd this is dumb un_enc_path = decode_str(unquote(path.text), sickbeard.SYS_ENCODING) self._log_debug(u'Updating %s on %s at %s' % (show_name, host, un_enc_path)) if not self._send( host, dict(command='ExecBuiltIn', parameter='Kodi.updatelibrary(video, %s)' % un_enc_path)): self._log_error( u'Update of show directory failed for %s on %s at %s' % (show_name, host, un_enc_path)) return False # sleep for a few seconds just to be sure kodi has a chance to finish each directory if 1 < len(paths): time.sleep(5) # do a full update if requested else: self._log_debug(u'Full library update on host: %s' % host) if not self._send( host, dict(command='ExecBuiltIn', parameter='Kodi.updatelibrary(video)')): self._log_error(u'Failed full library update on: %s' % host) return False return True
def _authorised(self, **kwargs): result = False if self.digest and 'None' not in self.digest and 'login_chk' in self.urls: digest = [x[::-1] for x in self.digest[::-1].rpartition('=')] self.digest = digest[2] + digest[1] + quote(unquote(digest[0])) self.session.cookies = cookiejar_from_dict( dict({digest[2]: quote(unquote(digest[0]))})) html = self.get_url(self.urls['login_chk'], skip_auth=True) result = html and 'RSS' in html and 'type="password"' not in html if not result and not self.failure_count: if self.url and self.digest: self.get_url(self.urls['logout'], skip_auth=True, post_data={ 'submit.x': 24, 'submit.y': 11 }) self.digest = '' self.session.cookies.clear() json = self.get_url(self.urls['login_1'], skip_auth=True, post_data={'username': self.username}, parse_json=True) resp = filter_list(lambda l: isinstance(l, list), json.get('Fs', [])) def get_html(_resp): for cur_item in _resp: if isinstance(cur_item, list): _html = filter_list( lambda s: isinstance(s, string_types) and 'password' in s, cur_item) if not _html: _html = get_html(cur_item) if _html: return _html params = {} html = get_html(resp) if html: tags = re.findall(r'(?is)(<input[^>]*?name=[\'"][^\'"]+[^>]*)', html[0]) attrs = [[(re.findall(r'(?is)%s=[\'"]([^\'"]+)' % attr, x) or [''])[0] for attr in ['type', 'name', 'value']] for x in tags] for itype, name, value in attrs: if 'password' in [itype, name]: params[name] = self.password if name not in ('username', 'password') and 'password' != itype: params.setdefault(name, value) if params: html = self.get_url(self.urls['login_2'], skip_auth=True, post_data=params) if html and 'RSS' in html: self.digest = None if self.session.cookies.get('inSpeed_speedian'): self.digest = 'inSpeed_speedian=%s' % self.session.cookies.get( 'inSpeed_speedian') sickbeard.save_config() result = True logger.log('Cookie details for %s updated.' % self.name, logger.DEBUG) elif not self.failure_count: logger.log( 'Invalid cookie details for %s and login failed. Check settings' % self.name, logger.ERROR) return result
def _update_library_http(self, host=None, show_name=None): """Handles updating XBMC host via HTTP API Attempts to update the XBMC video library for a specific tv show if passed, otherwise update the whole library if enabled. Args: host: XBMC webserver host:port show_name: Name of a TV show to specifically target the library update for Returns: Returns True or False """ if not host: self._log_debug(u'No host passed, aborting update') return False self._log_debug(u'Updating XMBC library via HTTP method for host: ' + host) # if we're doing per-show if show_name: self._log_debug(u'Updating library via HTTP method for show ' + show_name) # noinspection SqlResolve path_sql = 'select path.strPath' \ ' from path, tvshow, tvshowlinkpath' \ ' where tvshow.c00 = "%s"' \ ' and tvshowlinkpath.idShow = tvshow.idShow' \ ' and tvshowlinkpath.idPath = path.idPath' % show_name # use this to get xml back for the path lookups xml_command = dict( command= 'SetResponseFormat(webheader;false;webfooter;false;header;<xml>;footer;</xml>;' 'opentag;<tag>;closetag;</tag>;closefinaltag;false)') # sql used to grab path(s) sql_command = dict(command='QueryVideoDatabase(%s)' % path_sql) # set output back to default reset_command = dict(command='SetResponseFormat()') # set xml response format, if this fails then don't bother with the rest request = self._send_to_xbmc(xml_command, host) if not request: return False sql_xml = self._send_to_xbmc(sql_command, host) self._send_to_xbmc(reset_command, host) if not sql_xml: self._log_debug(u'Invalid response for ' + show_name + ' on ' + host) return False enc_sql_xml = quote(sql_xml, ':\\/<>') try: et = XmlEtree.fromstring(enc_sql_xml) except SyntaxError as e: self._log_error(u'Unable to parse XML response: ' + ex(e)) return False paths = et.findall('.//field') if not paths: self._log_debug(u'No valid paths found for ' + show_name + ' on ' + host) return False for path in paths: # we do not need it double-encoded, gawd this is dumb un_enc_path = decode_str(unquote(path.text), sickbeard.SYS_ENCODING) self._log_debug(u'Updating ' + show_name + ' on ' + host + ' at ' + un_enc_path) update_command = dict( command='ExecBuiltIn', parameter='XBMC.updatelibrary(video, %s)' % un_enc_path) request = self._send_to_xbmc(update_command, host) if not request: self._log_error(u'Update of show directory failed on ' + show_name + ' on ' + host + ' at ' + un_enc_path) return False # sleep for a few seconds just to be sure xbmc has a chance to finish each directory if 1 < len(paths): time.sleep(5) # do a full update if requested else: self._log(u'Doing full library update on host: ' + host) update_command = { 'command': 'ExecBuiltIn', 'parameter': 'XBMC.updatelibrary(video)' } request = self._send_to_xbmc(update_command, host) if not request: self._log_error(u'Full Library update failed on: ' + host) return False return True