Ejemplo n.º 1
0
def clean_database(device):
    def _exists(item_path):
        return os.path.exists(os.path.join(device.mount,
                                           item_path))
    known_files = set()
    to_remove = []
    for item_type in (u'video', u'audio', u'other'):
        device.database.setdefault(item_type, {})
        if isinstance(device.database[item_type], list):
            # 17554: we could accidentally set this to a list
            device.database[item_type] = {}
        for item_path_unicode in device.database[item_type]:
            item_path = utf8_to_filename(item_path_unicode.encode('utf8'))
            if _exists(item_path):
                known_files.add(os.path.normcase(item_path))
            else:
                to_remove.append((item_type, item_path_unicode))

    if to_remove:
        device.database.set_bulk_mode(True)
        for item_type, item_path in to_remove:
            del device.database[item_type][item_path]
        device.database.set_bulk_mode(False)

    return known_files
Ejemplo n.º 2
0
 def got_metainfo(self):
     # FIXME: If the client is stopped before a BT download gets
     #        its metadata, we never run this. It's not a huge deal
     #        because it only affects the incomplete filename
     if not self.restarting:
         try:
             metainfo = lt.bdecode(self.metainfo)
             # if we don't get valid torrent metadata back, then the
             # metainfo is None.  treat that like a runtime error.
             if not metainfo:
                 raise RuntimeError()
             name = metainfo['info']['name']
         # Note: handle KeyError as well because bdecode() may return
         # an object with no 'info' key, or with 'info' key but no 'name'
         # key.  This allows us to catch lousily made torrent files.
         except (KeyError, RuntimeError):
             self.handle_corrupt_torrent()
             return
         self.shortFilename = utf8_to_filename(name)
         try:
             self.pick_initial_filename(suffix="", torrent=True)
         # Somewhere deep it calls makedirs() which can throw exceptions.
         #
         # Not sure if this is correct but if we throw a runtime error
         # like above it can't hurt anyone.
         except (OSError, IOError):
             raise RuntimeError
     self.update_client()
     self._resume_torrent()
Ejemplo n.º 3
0
def unicode_to_path(path):
    """
    Convert a Unicode string into a file path.  We don't do any of the string
    replace nonsense that unicode_to_filename does.  We also convert separators
    into the appropriate type for the platform.
    """
    return utf8_to_filename(path.encode('utf8')).replace('/', os.path.sep)
Ejemplo n.º 4
0
def unicode_to_path(path):
    """
    Convert a Unicode string into a file path.  We don't do any of the string
    replace nonsense that unicode_to_filename does.  We also convert separators
    into the appropriate type for the platform.
    """
    return utf8_to_filename(path.encode('utf8')).replace('/', os.path.sep)
Ejemplo n.º 5
0
def clean_database(device):
    def _exists(item_path):
        return os.path.exists(os.path.join(device.mount, item_path))

    known_files = set()
    to_remove = []
    for item_type in (u'video', u'audio', u'other'):
        device.database.setdefault(item_type, {})
        if isinstance(device.database[item_type], list):
            # 17554: we could accidentally set this to a list
            device.database[item_type] = {}
        for item_path_unicode in device.database[item_type]:
            item_path = utf8_to_filename(item_path_unicode.encode('utf8'))
            if _exists(item_path):
                known_files.add(os.path.normcase(item_path))
            else:
                to_remove.append((item_type, item_path_unicode))

    if to_remove:
        device.database.set_bulk_mode(True)
        for item_type, item_path in to_remove:
            del device.database[item_type][item_path]
        device.database.set_bulk_mode(False)

    return known_files
Ejemplo n.º 6
0
 def remove_(index):
     size, file_type, id_ = sizes.pop(index)
     del self.device.database[file_type][id_]
     fileutil.delete(os.path.join(self.device.mount,
                                  utf8_to_filename(
                 id_.encode('utf8'))))
     self.device.remaining += size
     return keys.pop(index)
Ejemplo n.º 7
0
    def check_json_import(self, device_data):
        """Check that we successfully imported the sqlite data."""
        sqlite_db = devices.load_sqlite_database(self.device.mount, 1024)
        sqlite_db.cursor.execute("SELECT album from metadata")
        db_info = database.DeviceDBInfo(sqlite_db, self.device.id)
        importer = devicedatabaseupgrade.OldItemImporter(
            sqlite_db, self.device.mount, self.device.db)
        importer.import_metadata()
        metadata_manager = devices.make_metadata_manager(
            self.device.mount, db_info, self.device.id)
        importer.import_device_items(metadata_manager)

        for path, item_data in device_data.items():
            # fill in data that's implicit with the dict
            item_data['file_type'] = u'audio'
            item_data['video_path'] = path
            filename = utf8_to_filename(path.encode('utf-8'))
            self.check_migrated_status(filename, db_info)
            self.check_migrated_entries(filename, item_data, db_info)
            self.check_migrated_device_item(filename, item_data, db_info)
            # check that the title tag was deleted
            self.assert_(not hasattr(item, 'title_tag'))
Ejemplo n.º 8
0
    def check_json_import(self, device_data):
        """Check that we successfully imported the sqlite data."""
        sqlite_db = devices.load_sqlite_database(self.device.mount, 1024)
        sqlite_db.cursor.execute("SELECT album from metadata")
        db_info = database.DeviceDBInfo(sqlite_db, self.device.id)
        importer = devicedatabaseupgrade.OldItemImporter(sqlite_db,
                                                         self.device.mount,
                                                         self.device.db)
        importer.import_metadata()
        metadata_manager = devices.make_metadata_manager(self.device.mount,
                                                         db_info,
                                                         self.device.id)
        importer.import_device_items(metadata_manager)

        for path, item_data in device_data.items():
            # fill in data that's implicit with the dict
            item_data['file_type'] = u'audio'
            item_data['video_path'] = path
            filename = utf8_to_filename(path.encode('utf-8'))
            self.check_migrated_status(filename, db_info)
            self.check_migrated_entries(filename, item_data, db_info)
            self.check_migrated_device_item(filename, item_data, db_info)
            # check that the title tag was deleted
            self.assert_(not hasattr(item, 'title_tag'))
Ejemplo n.º 9
0
    def __init__(self, **kwargs):
        self.__initialized = False
        for required in ('video_path', 'file_type', 'device'):
            if required not in kwargs:
                raise TypeError('DeviceItem must be given a "%s" argument' %
                                required)
        self.file_format = self.size = None
        self.release_date = self.feed_name = self.feed_id = None
        self.keep = True
        self.isContainerItem = False
        self.url = self.payment_link = None
        self.comments_link = self.permalink = self.file_url = None
        self.license = self.downloader = None
        self.duration = self.screenshot = self.thumbnail_url = None
        self.resumeTime = 0
        self.subtitle_encoding = self.enclosure_type = None
        self.file_type = None
        self.creation_time = None
        self.is_playing = False
        metadata.Store.setup_new(self)
        self.__dict__.update(kwargs)

        if isinstance(self.video_path, unicode):
            # make sure video path is a filename and ID is Unicode
            self.id = self.video_path
            self.video_path = utf8_to_filename(self.video_path.encode('utf8'))
        else:
            self.id = filename_to_unicode(self.video_path)
        if isinstance(self.screenshot, unicode):
            self.screenshot = utf8_to_filename(self.screenshot.encode('utf8'))
        if isinstance(self.cover_art, unicode):
            self.cover_art = utf8_to_filename(self.cover_art.encode('utf8'))
        if self.file_format is None:
            self.file_format = filename_to_unicode(
                os.path.splitext(self.video_path)[1])
            if self.file_type == 'audio':
                self.file_format = self.file_format + ' audio'

        try:  # filesystem operations
            if self.size is None:
                self.size = os.path.getsize(self.get_filename())
            if self.release_date is None or self.creation_time is None:
                ctime = fileutil.getctime(self.get_filename())
                if self.release_date is None:
                    self.release_date = ctime
                if self.creation_time is None:
                    self.creation_time = ctime
            if not self.metadata_version:
                # haven't run read_metadata yet.  We don't check the actual
                # version because upgrading metadata isn't supported.
                self.read_metadata()
                if not self.get_title():
                    self.title = filename_to_unicode(
                        os.path.basename(self.video_path))

        except (OSError, IOError):
            # if there was an error reading the data from the filesystem, don't
            # bother continuing with other FS operations or starting moviedata
            logging.debug('error reading %s', self.id, exc_info=True)
        else:
            if self.mdp_state is None:  # haven't run MDP yet
                moviedata.movie_data_updater.request_update(self)
        self.__initialized = True
Ejemplo n.º 10
0
 def _send_deleted(self, path):
     eventloop.add_idle(self.emit,
                        "emit deleted signal",
                        args=("deleted", utf8_to_filename(path)))
Ejemplo n.º 11
0
 def _send_added(self, path):
     # use add_idle() to pass things over to the backend thread
     # FIXME: there should be a cleaner way to do this
     eventloop.add_idle(self.emit,
                        "emit added signal",
                        args=("added", utf8_to_filename(path)))
Ejemplo n.º 12
0
 def _send_deleted(self, path):
     eventloop.add_idle(self.emit, "emit deleted signal",
             args=("deleted", utf8_to_filename(path)))
Ejemplo n.º 13
0
 def _send_added(self, path):
     # use add_idle() to pass things over to the backend thread
     # FIXME: there should be a cleaner way to do this
     eventloop.add_idle(self.emit, "emit added signal",
             args=("added", utf8_to_filename(path)))
Ejemplo n.º 14
0
    def __init__(self, **kwargs):
        self.__initialized = False
        for required in ('video_path', 'file_type', 'device'):
            if required not in kwargs:
                raise TypeError('DeviceItem must be given a "%s" argument'
                                % required)
        self.file_format = self.size = None
        self.release_date = self.feed_name = self.feed_id = None
        self.keep = True
        self.isContainerItem = False
        self.url = self.payment_link = None
        self.comments_link = self.permalink = self.file_url = None
        self.license = self.downloader = None
        self.duration = self.screenshot = self.thumbnail_url = None
        self.resumeTime = 0
        self.subtitle_encoding = self.enclosure_type = None
        self.file_type = None
        self.creation_time = None
        self.is_playing = False
        metadata.Store.setup_new(self)
        self.__dict__.update(kwargs)

        if isinstance(self.video_path, unicode):
            # make sure video path is a filename and ID is Unicode
            self.id = self.video_path
            self.video_path = utf8_to_filename(self.video_path.encode('utf8'))
        else:
            self.id = filename_to_unicode(self.video_path)
        if isinstance(self.screenshot, unicode):
            self.screenshot = utf8_to_filename(self.screenshot.encode('utf8'))
        if isinstance(self.cover_art, unicode):
            self.cover_art = utf8_to_filename(self.cover_art.encode('utf8'))
        if self.file_format is None:
            self.file_format = filename_to_unicode(
                os.path.splitext(self.video_path)[1])
            if self.file_type == 'audio':
                self.file_format = self.file_format + ' audio'

        try: # filesystem operations
            if self.size is None:
                self.size = os.path.getsize(self.get_filename())
            if self.release_date is None or self.creation_time is None:
                ctime = fileutil.getctime(self.get_filename())
                if self.release_date is None:
                    self.release_date = ctime
                if self.creation_time is None:
                    self.creation_time = ctime
            if not self.metadata_version:
                # haven't run read_metadata yet.  We don't check the actual
                # version because upgrading metadata isn't supported.
                self.read_metadata()
                if not self.get_title():
                    self.title = filename_to_unicode(
                        os.path.basename(self.video_path))

        except (OSError, IOError):
            # if there was an error reading the data from the filesystem, don't
            # bother continuing with other FS operations or starting moviedata
            logging.debug('error reading %s', self.id, exc_info=True)
        else:
            if self.mdp_state is None: # haven't run MDP yet
                moviedata.movie_data_updater.request_update(self)
        self.__initialized = True