def do_languages(self, arg): if arg: try: if int(arg) == 0: self.state.set_download_languages([]) self.echo(_('Filter languages cleared')) return except ValueError: pass try: langs = [Language.from_unknown(l_str, xx=True, xxx=True, name=True, locale=True) for l_str in self.shlex_parse_argstr(arg)] except NotALanguageException as e: self.echo(_('"{}" is not a valid language').format(e.value)) return self.state.set_download_languages(langs) self.echo(ngettext('New filter language:', 'New filter languages:', len(self.state.get_download_languages()))) for language in self.state.get_download_languages(): self.echo('- {}'.format(language.name())) return else: self.echo(ngettext('Current filter language:', 'Current filter languages:', len(self.state.get_download_languages()))) if self.state.get_download_languages(): for language in self.state.get_download_languages(): self.echo('- {}'.format(language.name())) else: self.echo(_('(None)'))
def get_system_language(): locale = i18n_system_locale() for lc_fallback in i18n_locale_fallbacks_calculate(locale): try: language = Language.from_unknown(lc_fallback, locale=True) return language except NotALanguageException: continue return UnknownLanguage.create_generic()
def __call__(self, parser, namespace, values, option_string=None): try: languages = [ Language.from_unknown(value, xx=True, xxx=True, locale=True, name=True) for value in values ] setattr(namespace, self.dest, languages) except NotALanguageException as e: parser.error( _('{lang_str} is an unknown language.').format( lang_str=e.value))
def matches_video_filename(self, video): """ Detect whether the filename of videofile matches with this SubtitleFile. :param video: VideoFile instance :return: True if match """ vid_fn = video.get_filename() vid_stem, _ = os.path.splitext(vid_fn) vid_stem = vid_stem.lower() sub_fn = self.get_filename() sub_stem, _ = os.path.splitext(sub_fn) sub_stem = sub_stem.lower() log.debug( 'matches_filename(subtitle="{sub_filename}", video="{vid_filename}") ...' .format(sub_filename=sub_fn, vid_filename=vid_fn)) matches = sub_stem == vid_stem lang = None if not matches: if sub_stem.startswith(vid_stem): sub_rest = sub_stem[len(vid_stem):] rests = sub_rest.split('.') rest_matches = True for rest in rests: if not rest: continue try: int(rest) continue except ValueError: pass try: lang = Language.from_unknown(rest, xx=True, xxx=True) continue except NotALanguageException: pass rest_matches = False break matches = rest_matches if matches: log.debug( '... matches (language={language})'.format(language=lang)) else: log.debug('... does not match') return matches
def do_upload_set_language(self, arg): args = self.shlex_parse_argstr(arg) if len(args) == 0: self._upload_movie.set_language(UnknownLanguage.create_generic()) return if len(args) != 1: self.echo('Need 1 argument') return try: lang = Language.from_unknown(args[0], xx=True, xxx=True, name=True, locale=True) self.echo(_('Upload language set to {}.').format(lang.name())) self._upload_movie.set_language(lang) except NotALanguageException: self.echo(_('Unknown language')) return
def matches_videofile_filename(self, videofile): """ Detect whether the filename of videofile matches with this SubtitleFile. :param videofile: VideoFile instance :return: True if match """ vid_fn = videofile.get_filename() vid_base, _ = os.path.splitext(vid_fn) vid_base = vid_base.lower() sub_fn = self.get_filename() sub_base, _ = os.path.splitext(sub_fn) sub_base = sub_base.lower() log.debug( 'matches_filename(subtitle="{sub_filename}", video="{vid_filename}") ...' .format(sub_filename=sub_fn, vid_filename=vid_fn)) matches = sub_base == vid_base lang = None if not matches: if sub_base.startswith(vid_base): sub_rest = sub_base[len(vid_base):] while len(sub_rest) > 0: if sub_rest[0].isalnum(): break sub_rest = sub_rest[1:] try: lang = Language.from_unknown(sub_rest, locale=False, name=False) matches = True except NotALanguageException: matches = False if matches: log.debug( '... matches (language={language})'.format(language=lang)) else: log.debug('... does not match') return matches
def detect_language_filename(cls, filename): """ Detect the language of a subtitle filename :param filename: filename of a subtitle :return: Language object, None if language could not be detected. """ log.debug('detect_language(filename="{}") ...'.format(filename)) root, _ = os.path.splitext(filename) fn_lang = cls.DETECT_LANGUAGE_REGEX.findall(root) if fn_lang: language_part = fn_lang[0] try: lang = Language.from_unknown(language_part, xx=True, xxx=True) log.debug('... SUCCESS: detected from filename: {lang}'.format( lang=lang)) return lang except NotALanguageException: pass else: log.debug('... FAIL: could not detect from filename') return UnknownLanguage.create_generic()
def do_languages(self, arg): if arg: langs = None if langs is None: try: if int(arg) == 0: langs = [] except ValueError: pass if langs is None: try: langs = [ Language.from_unknown(l_str, xx=True, xxx=True, name=True, locale=True) for l_str in shlex.split(arg) ] except NotALanguageException as e: self.print( _('"{}" is not a valid language').format(e.value)) return self.state.set_download_languages(langs) if arg: self.print( ngettext('New filter language:', 'New filter languages:', len(self.state.get_download_languages()))) else: self.print( ngettext('Current filter language:', 'Current filter languages:', len(self.state.get_download_languages()))) if self.state.get_download_languages(): for language in self.state.get_download_languages(): self.print('- {}'.format(language.name())) else: self.print(_('(None)'))
def search_videos(self, videos, callback, languages=None): log.debug('search_videos(#videos={})'.format(len(videos))) if not self.logged_in(): raise ProviderNotConnectedError() lang_str = self._languages_to_str(languages) window_size = 5 callback.set_range(0, (len(videos) + (window_size - 1)) // window_size) remote_subtitles = [] for window_i, video_window in enumerate( window_iterator(videos, window_size)): callback.update(window_i) if callback.canceled(): break queries = [] hash_video = {} for video in video_window: query = { 'sublanguageid': lang_str, 'moviehash': video.get_osdb_hash(), 'moviebytesize': str(video.get_size()), } queries.append(query) hash_video[video.get_osdb_hash()] = video def run_query(): return self._xmlrpc.SearchSubtitles( self._token, queries, {'limit': self.SEARCH_LIMIT}) result = self._safe_exec(run_query, None) self.check_result(result) if result is None: continue for rsub_raw in result['data']: try: remote_filename = rsub_raw['SubFileName'] remote_file_size = int(rsub_raw['SubSize']) remote_id = rsub_raw['IDSubtitleFile'] remote_md5_hash = rsub_raw['SubHash'] remote_download_link = rsub_raw['SubDownloadLink'] remote_link = rsub_raw['SubtitlesLink'] remote_uploader = rsub_raw['UserNickName'].strip() remote_language_raw = rsub_raw['SubLanguageID'] try: remote_language = Language.from_unknown( remote_language_raw, xx=True, xxx=True) except NotALanguageException: remote_language = UnknownLanguage(remote_language_raw) remote_rating = float(rsub_raw['SubRating']) remote_date = datetime.datetime.strptime( rsub_raw['SubAddDate'], '%Y-%m-%d %H:%M:%S') remote_subtitle = OpenSubtitlesSubtitleFile( filename=remote_filename, file_size=remote_file_size, md5_hash=remote_md5_hash, id_online=remote_id, download_link=remote_download_link, link=remote_link, uploader=remote_uploader, language=remote_language, rating=remote_rating, age=remote_date, ) movie_hash = '{:>016}'.format(rsub_raw['MovieHash']) video = hash_video[movie_hash] imdb_id = rsub_raw['IDMovieImdb'] imdb_identity = ImdbIdentity(imdb_id=imdb_id, imdb_rating=None) identity = ProviderIdentities(imdb_identity=imdb_identity, provider=self) video.add_subtitle(remote_subtitle) video.add_identity(identity) remote_subtitles.append(remote_subtitle) except (KeyError, ValueError): log.exception( 'Error parsing result of SearchSubtitles(...)') log.error('Offending query is: {queries}'.format( queries=queries)) log.error('Offending result is: {remote_sub}'.format( remote_sub=rsub_raw)) callback.finish() return remote_subtitles
def search_videos(self, videos, callback, languages=None): limit = 500 if languages: lang_str = ','.join([language.xxx() for language in languages]) else: lang_str = 'all' window_size = 5 callback.set_range(0, (len(videos) + (window_size - 1)) // window_size) remote_subtitles = [] for window_i, video_window in enumerate(window_iterator(videos, window_size)): callback.update(window_i) if callback.canceled(): break queries = [] hash_video = {} for video in video_window: query = { 'sublanguageid': lang_str, 'moviehash': video.get_osdb_hash(), 'moviebytesize': str(video.get_size()), } queries.append(query) hash_video[video.get_osdb_hash()] = video def run_query(): return self._xmlrpc_server.SearchSubtitles(self._token, queries, {'limit': limit}) result = self._safe_exec(run_query, None) if result is None: return remote_subtitles self.check_result(result) for rsub_raw in result['data']: try: remote_filename = rsub_raw['SubFileName'] remote_file_size = int(rsub_raw['SubSize']) remote_id = rsub_raw['IDSubtitleFile'] remote_md5_hash = rsub_raw['SubHash'] remote_download_link = rsub_raw['SubDownloadLink'] remote_link = rsub_raw['SubtitlesLink'] remote_uploader = rsub_raw['UserNickName'] remote_language_raw = rsub_raw['SubLanguageID'] try: remote_language = Language.from_unknown(remote_language_raw, locale=False, name=False) except NotALanguageException: remote_language = UnknownLanguage(remote_language_raw) remote_rating = float(rsub_raw['SubRating']) remote_subtitle = OpenSubtitles_SubtitleFile( filename=remote_filename, file_size=remote_file_size , md5_hash=remote_md5_hash, id_online=remote_id, download_link=remote_download_link, link=remote_link, uploader=remote_uploader, language=remote_language, rating=remote_rating, ) movie_hash = '{:>016}'.format(rsub_raw['MovieHash']) hash_video[movie_hash].add_subtitle(remote_subtitle) remote_subtitles.append(remote_subtitle) except (KeyError, ValueError): log.exception('Error parsing result of SearchSubtitles(...)') log.error('Offending query is: {queries}'.format(queries=queries)) log.error('Offending result is: {remote_sub}'.format(remote_sub=rsub_raw)) callback.finish() return remote_subtitles