def create_thumbnails(self): """ Create thumbnail images for presentation. """ log.debug('create thumbnails OpenOffice') if self.check_thumbnails(): return temp_folder_path = self.get_temp_folder() thumb_dir_url = temp_folder_path.as_uri() properties = [] properties.append(self.create_property('FilterName', 'impress_png_Export')) properties = tuple(properties) doc = self.document pages = doc.getDrawPages() if not pages: return if not temp_folder_path.is_dir(): temp_folder_path.mkdir(parents=True) for index in range(pages.getCount()): page = pages.getByIndex(index) doc.getCurrentController().setCurrentPage(page) url_path = '{path}/{name:d}.png'.format(path=thumb_dir_url, name=index + 1) path = temp_folder_path / '{number:d}.png'.format(number=index + 1) try: doc.storeToURL(url_path, properties) self.convert_thumbnail(path, index + 1) delete_file(path) except ErrorCodeIOException as exception: log.exception('ERROR! ErrorCodeIOException {error:d}'.format(error=exception.ErrCode)) except: log.exception('{path} - Unable to store openoffice preview'.format(path=path))
def _write_theme(self, theme, image_source_path=None, image_destination_path=None): """ Writes the theme to the disk and handles the background image if necessary :param Theme theme: The theme data object. :param openlp.core.common.path.Path image_source_path: Where the theme image is currently located. :param openlp.core.common.path.Path image_destination_path: Where the Theme Image is to be saved to :rtype: None """ name = theme.theme_name theme_pretty = theme.export_theme(self.theme_path) theme_dir = self.theme_path / name create_paths(theme_dir) theme_path = theme_dir / '{file_name}.json'.format(file_name=name) try: theme_path.write_text(theme_pretty) except OSError: self.log_exception('Saving theme to file failed') if image_source_path and image_destination_path: if self.old_background_image_path and image_destination_path != self.old_background_image_path: delete_file(self.old_background_image_path) if image_source_path != image_destination_path: try: copyfile(image_source_path, image_destination_path) except OSError: self.log_exception('Failed to save theme image') self.generate_and_save_image(name, theme)
def create_thumbnails(self): """ Create thumbnail images for presentation. """ log.debug('create thumbnails OpenOffice') if self.check_thumbnails(): return if is_win(): thumb_dir_url = 'file:///' + self.get_temp_folder().replace('\\', '/') \ .replace(':', '|').replace(' ', '%20') else: thumb_dir_url = uno.systemPathToFileUrl(self.get_temp_folder()) properties = [] properties.append(self.create_property('FilterName', 'impress_png_Export')) properties = tuple(properties) doc = self.document pages = doc.getDrawPages() if not pages: return if not os.path.isdir(self.get_temp_folder()): os.makedirs(self.get_temp_folder()) for index in range(pages.getCount()): page = pages.getByIndex(index) doc.getCurrentController().setCurrentPage(page) url_path = '{path}/{name}.png'.format(path=thumb_dir_url, name=str(index + 1)) path = os.path.join(self.get_temp_folder(), str(index + 1) + '.png') try: doc.storeToURL(url_path, properties) self.convert_thumbnail(path, index + 1) delete_file(path) except ErrorCodeIOException as exception: log.exception('ERROR! ErrorCodeIOException {error:d}'.format(error=exception.ErrCode)) except: log.exception('{path} - Unable to store openoffice preview'.format(path=path))
def on_delete_click(self): """ Remove an image item from the list. """ # Turn off auto preview triggers. self.list_view.blockSignals(True) if check_item_selected( self.list_view, translate('ImagePlugin.MediaItem', 'You must select an image or group to delete.')): item_list = self.list_view.selectedItems() self.application.set_busy_cursor() self.main_window.display_progress_bar(len(item_list)) for row_item in item_list: if row_item: item_data = row_item.data(0, QtCore.Qt.UserRole) if isinstance(item_data, ImageFilenames): delete_file( os.path.join(self.service_path, row_item.text(0))) delete_file(self.generate_thumbnail_path(item_data)) if item_data.group_id == 0: self.list_view.takeTopLevelItem( self.list_view.indexOfTopLevelItem(row_item)) else: row_item.parent().removeChild(row_item) self.manager.delete_object( ImageFilenames, row_item.data(0, QtCore.Qt.UserRole).id) elif isinstance(item_data, ImageGroups): if QtWidgets.QMessageBox.question( self.list_view.parent(), translate('ImagePlugin.MediaItem', 'Remove group'), translate( 'ImagePlugin.MediaItem', 'Are you sure you want to remove "{name}" and everything in it?' ).format(name=item_data.group_name), QtWidgets.QMessageBox.StandardButtons( QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No) ) == QtWidgets.QMessageBox.Yes: self.recursively_delete_group(item_data) self.manager.delete_object( ImageGroups, row_item.data(0, QtCore.Qt.UserRole).id) if item_data.parent_id == 0: self.list_view.takeTopLevelItem( self.list_view.indexOfTopLevelItem( row_item)) else: row_item.parent().removeChild(row_item) self.fill_groups_combobox( self.choose_group_form.group_combobox) self.fill_groups_combobox( self.add_group_form.parent_group_combobox) self.main_window.increment_progress_bar() self.main_window.finished_progress_bar() self.application.set_normal_cursor() self.list_view.blockSignals(False)
def do_import(self): """ Receive a path to a LiveWorship (valentina) DB. """ self.dump_file = Path(gettempdir()) / 'openlp-liveworship-dump.xml' if not self.dump_valentina_to_xml(): return self.load_xml_dump() if self.root is None: return self.extract_songs() delete_file(self.dump_file)
def create_thumbnails(self): """ Create thumbnail images for presentation. """ log.debug('create thumbnails LibreOffice') if self.check_thumbnails(): return temp_thumbnails = self.client.extract_thumbnails( str(self.get_temp_folder())) for index, temp_thumb in enumerate(temp_thumbnails): temp_thumb = Path(temp_thumb) self.convert_thumbnail(temp_thumb, index + 1) delete_file(temp_thumb)
def delete_theme(self, theme): """ Delete a theme. :param theme: The theme to delete. """ self.theme_list.remove(theme) thumb = '{name}.png'.format(name=theme) delete_file(self.theme_path / thumb) delete_file(self.thumb_path / thumb) try: (self.theme_path / theme).rmtree() except OSError: self.log_exception('Error deleting theme {name}'.format(name=theme))
def recursively_delete_group(self, image_group): """ Recursively deletes a group and all groups and images in it. :param image_group: The ImageGroups instance of the group that will be deleted. """ images = self.manager.get_all_objects( ImageFilenames, ImageFilenames.group_id == image_group.id) for image in images: delete_file(self.service_path / image.file_path.name) delete_file(self.generate_thumbnail_path(image)) self.manager.delete_object(ImageFilenames, image.id) image_groups = self.manager.get_all_objects( ImageGroups, ImageGroups.parent_id == image_group.id) for group in image_groups: self.recursively_delete_group(group) self.manager.delete_object(ImageGroups, group.id)
def load_first_time_themes(self): """ Imports any themes on start up and makes sure there is at least one theme """ self.application.set_busy_cursor() files = AppLocation.get_files(self.settings_section, '.otz') for theme_file in files: theme_file = os.path.join(self.path, theme_file) self.unzip_theme(theme_file, self.path) delete_file(theme_file) files = AppLocation.get_files(self.settings_section, '.png') # No themes have been found so create one if not files: theme = ThemeXML() theme.theme_name = UiStrings().Default self._write_theme(theme, None, None) Settings().setValue(self.settings_section + '/global theme', theme.theme_name) self.application.set_normal_cursor()
def load_first_time_themes(self): """ Imports any themes on start up and makes sure there is at least one theme """ self.application.set_busy_cursor() theme_paths = AppLocation.get_files(self.settings_section, '.otz') for theme_path in theme_paths: theme_path = self.theme_path / theme_path self.unzip_theme(theme_path, self.theme_path) delete_file(theme_path) theme_paths = AppLocation.get_files(self.settings_section, '.png') # No themes have been found so create one if not theme_paths: theme = Theme() theme.theme_name = UiStrings().Default self._write_theme(theme) Settings().setValue(self.settings_section + '/global theme', theme.theme_name) self.application.set_normal_cursor()
def test_delete_file_no_path(self): """ Test the delete_file function when called with out a valid path """ # GIVEN: A blank path # WEHN: Calling delete_file result = delete_file('') # THEN: delete_file should return False self.assertFalse(result, "delete_file should return False when called with ''")
def test_delete_file_no_path(self): """ Test the delete_file function when called with out a valid path """ # GIVEN: A blank path # WEHN: Calling delete_file result = delete_file('') # THEN: delete_file should return False self.assertFalse(result, "delete_file should return False when called with ''")
def save_theme(self, theme, image=None, background_override=None): """ Writes the theme to the disk and including the background image and thumbnail if necessary :param Theme theme: The theme data object. :param image: The theme thumbnail. Optionally. :param background_override: Background to use rather than background_source. Optionally. :rtype: None """ name = theme.theme_name theme_pretty = theme.export_theme(self.theme_path) theme_dir = self.theme_path / name create_paths(theme_dir) theme_path = theme_dir / '{file_name}.json'.format(file_name=name) try: theme_path.write_text(theme_pretty) except OSError: self.log_exception('Saving theme to file failed') if theme.background_source and theme.background_filename: background_file = background_override # Use theme source image if override doesn't exist if not background_file or not background_file.exists(): background_file = theme.background_source if self.old_background_image_path and theme.background_filename != self.old_background_image_path: delete_file(self.old_background_image_path) if not background_file.exists(): self.log_warning( 'Background does not exist, retaining cached background') elif background_file != theme.background_filename: try: shutil.copyfile(background_file, theme.background_filename) except OSError: self.log_exception('Failed to save theme image') if image: sample_path_name = self.theme_path / '{file_name}.png'.format( file_name=name) if sample_path_name.exists(): sample_path_name.unlink() image.save(str(sample_path_name), 'png') thumb_path = self.thumb_path / '{name}.png'.format(name=name) create_thumb(sample_path_name, thumb_path, False) else: self.update_preview_images([name])
def test_delete_file_no_path(self): """ Test the delete_file function when called with out a valid path """ # GIVEN: A blank path # WEHN: Calling delete_file result = delete_file(None) # THEN: delete_file should return False assert result is False, "delete_file should return False when called with None"
def delete_bible(self, name): """ Delete a bible completely. :param name: The name of the bible. """ log.debug('BibleManager.delete_bible("{name}")'.format(name=name)) bible = self.db_cache[name] bible.session.close_all() bible.session = None return delete_file(Path(bible.path, bible.file))
def delete_theme(self, theme): """ Delete a theme. :param theme: The theme to delete. """ self.theme_list.remove(theme) thumb = '{name}.png'.format(name=theme) delete_file(os.path.join(self.path, thumb)) delete_file(os.path.join(self.thumb_path, thumb)) try: # Windows is always unicode, so no need to encode filenames if is_win(): shutil.rmtree(os.path.join(self.path, theme)) else: encoding = get_filesystem_encoding() shutil.rmtree(os.path.join(self.path, theme).encode(encoding)) except OSError as os_error: shutil.Error = os_error self.log_exception('Error deleting theme {name}'.format(name=theme))
def test_delete_file_path_no_file_exists(self): """ Test the delete_file function when the file to remove does not exist """ # GIVEN: A mocked os which returns False when os.path.exists is called with patch('openlp.core.common.os', **{'path.exists.return_value': False}): # WHEN: Calling delete_file with a file path result = delete_file('path/file.ext') # THEN: delete_file should return True self.assertTrue(result, 'delete_file should return True when the file doesnt exist')
def test_delete_file_path_success(self): """ Test the delete_file function when it successfully deletes a file """ # GIVEN: A mocked os which returns True when os.path.exists is called with patch('openlp.core.common.os', **{'path.exists.return_value': False}): # WHEN: Calling delete_file with a file path result = delete_file(Path('path', 'file.ext')) # THEN: delete_file should return True assert result is True, 'delete_file should return True when it successfully deletes a file'
def test_delete_file_path_no_file_exists(self): """ Test the delete_file function when the file to remove does not exist """ # GIVEN: A mocked os which returns False when os.path.exists is called with patch('openlp.core.common.os', **{'path.exists.return_value': False}): # WHEN: Calling delete_file with a file path result = delete_file('path/file.ext') # THEN: delete_file should return True self.assertTrue(result, 'delete_file should return True when the file doesnt exist')
def test_delete_file_path_success(self): """ Test the delete_file function when it successfully deletes a file """ # GIVEN: A mocked os which returns True when os.path.exists is called with patch('openlp.core.common.os', **{'path.exists.return_value': False}): # WHEN: Calling delete_file with a file path result = delete_file('path/file.ext') # THEN: delete_file should return True self.assertTrue(result, 'delete_file should return True when it successfully deletes a file')
def delete_database(plugin_name, db_file_name=None): """ Remove a database file from the system. :param plugin_name: The name of the plugin to remove the database for :param db_file_name: The database file name. Defaults to None resulting in the plugin_name being used. """ if db_file_name: db_file_path = os.path.join(AppLocation.get_section_data_path(plugin_name), db_file_name) else: db_file_path = os.path.join(AppLocation.get_section_data_path(plugin_name), plugin_name) return delete_file(db_file_path)
def reload_bibles(self): """ Reloads the Bibles from the available Bible databases on disk. If a web Bible is encountered, an instance of HTTPBible is loaded instead of the BibleDB class. """ log.debug('Reload bibles') file_paths = AppLocation.get_files(self.settings_section, self.suffix) if Path('alternative_book_names.sqlite') in file_paths: file_paths.remove(Path('alternative_book_names.sqlite')) log.debug('Bible Files {text}'.format(text=file_paths)) self.db_cache = {} for file_path in file_paths: bible = BibleDB(self.parent, path=self.path, file=file_path) if not bible.session: continue name = bible.get_name() # Remove corrupted files. if name is None: bible.session.close_all() delete_file(self.path / file_path) continue log.debug('Bible Name: "{name}"'.format(name=name)) self.db_cache[name] = bible # Look to see if lazy load bible exists and get create getter. if self.db_cache[name].is_web_bible: source = self.db_cache[name].get_object( BibleMeta, 'download_source') download_name = self.db_cache[name].get_object( BibleMeta, 'download_name').value meta_proxy = self.db_cache[name].get_object( BibleMeta, 'proxy_server') web_bible = HTTPBible(self.parent, path=self.path, file=file_path, download_source=source.value, download_name=download_name) if meta_proxy: web_bible.proxy_server = meta_proxy.value self.db_cache[name] = web_bible log.debug('Bibles reloaded')
def create_thumbnails(self): """ Create thumbnail images for presentation. """ log.debug('create thumbnails OpenOffice') if self.check_thumbnails(): return if is_win(): thumb_dir_url = 'file:///' + self.get_temp_folder().replace('\\', '/') \ .replace(':', '|').replace(' ', '%20') else: thumb_dir_url = uno.systemPathToFileUrl(self.get_temp_folder()) properties = [] properties.append( self.create_property('FilterName', 'impress_png_Export')) properties = tuple(properties) doc = self.document pages = doc.getDrawPages() if not pages: return if not os.path.isdir(self.get_temp_folder()): os.makedirs(self.get_temp_folder()) for index in range(pages.getCount()): page = pages.getByIndex(index) doc.getCurrentController().setCurrentPage(page) url_path = '{path}/{name}.png'.format(path=thumb_dir_url, name=str(index + 1)) path = os.path.join(self.get_temp_folder(), str(index + 1) + '.png') try: doc.storeToURL(url_path, properties) self.convert_thumbnail(path, index + 1) delete_file(path) except ErrorCodeIOException as exception: log.exception('ERROR! ErrorCodeIOException {error:d}'.format( error=exception.ErrCode)) except: log.exception( '{path} - Unable to store openoffice preview'.format( path=path))
def delete_database(plugin_name, db_file_name=None): """ Remove a database file from the system. :param plugin_name: The name of the plugin to remove the database for :param db_file_name: The database file name. Defaults to None resulting in the plugin_name being used. """ db_file_path = AppLocation.get_section_data_path(plugin_name) if db_file_name: db_file_path = db_file_path / db_file_name else: db_file_path = db_file_path / plugin_name return delete_file(db_file_path)
def test_delete_file_path_no_file_exists(self): """ Test the `delete_file` function when the file to remove does not exist """ # GIVEN: A patched `exists` methods on the Path object, which returns False with patch.object(Path, 'exists', return_value=False), \ patch.object(Path, 'unlink') as mocked_unlink: # WHEN: Calling `delete_file with` a file path result = delete_file(Path('path', 'file.ext')) # THEN: The function should not attempt to delete the file and it should return True assert mocked_unlink.called is False assert result is True, 'delete_file should return True when the file doesnt exist'
def test_delete_file_path_exception(self): """ Test the delete_file function when os.remove raises an exception """ # GIVEN: A mocked os which returns True when os.path.exists is called and raises an OSError when os.remove is # called. with patch('openlp.core.common.os', **{'path.exists.return_value': True, 'path.exists.side_effect': OSError}), \ patch('openlp.core.common.log') as mocked_log: # WHEN: Calling delete_file with a file path result = delete_file('path/file.ext') # THEN: delete_file should log and exception and return False self.assertEqual(mocked_log.exception.call_count, 1) self.assertFalse(result, 'delete_file should return False when os.remove raises an OSError')
def test_delete_file_path_exception(self): """ Test the delete_file function when os.remove raises an exception """ # GIVEN: A mocked os which returns True when os.path.exists is called and raises an OSError when os.remove is # called. with patch('openlp.core.common.os', **{'path.exists.return_value': True, 'path.exists.side_effect': OSError}), \ patch('openlp.core.common.log') as mocked_log: # WHEN: Calling delete_file with a file path result = delete_file('path/file.ext') # THEN: delete_file should log and exception and return False self.assertEqual(mocked_log.exception.call_count, 1) self.assertFalse(result, 'delete_file should return False when os.remove raises an OSError')
def _write_theme(self, theme, image_from, image_to): """ Writes the theme to the disk and handles the background image if necessary :param theme: The theme data object. :param image_from: Where the theme image is currently located. :param image_to: Where the Theme Image is to be saved to """ name = theme.theme_name theme_pretty_xml = theme.extract_formatted_xml() theme_dir = os.path.join(self.path, name) check_directory_exists(theme_dir) theme_file = os.path.join(theme_dir, name + '.xml') if self.old_background_image and image_to != self.old_background_image: delete_file(self.old_background_image) out_file = None try: out_file = open(theme_file, 'w', encoding='utf-8') out_file.write(theme_pretty_xml.decode('utf-8')) except IOError: self.log_exception('Saving theme to file failed') finally: if out_file: out_file.close() if image_from and os.path.abspath(image_from) != os.path.abspath(image_to): try: # Windows is always unicode, so no need to encode filenames if is_win(): shutil.copyfile(image_from, image_to) else: encoding = get_filesystem_encoding() shutil.copyfile(image_from.encode(encoding), image_to.encode(encoding)) except IOError as xxx_todo_changeme: shutil.Error = xxx_todo_changeme self.log_exception('Failed to save theme image') self.generate_and_save_image(name, theme)
def test_delete_file_path_exception(self): """ Test the delete_file function when an exception is raised """ # GIVEN: A test `Path` object with a patched exists method which raises an OSError # called. with patch.object(Path, 'exists') as mocked_exists, \ patch('openlp.core.common.log') as mocked_log: mocked_exists.side_effect = OSError # WHEN: Calling delete_file with a the test Path object result = delete_file(Path('path', 'file.ext')) # THEN: The exception should be logged and `delete_file` should return False assert mocked_log.exception.called assert result is False, 'delete_file should return False when an OSError is raised'