# -*- coding: utf-8 -*- ########################################################################## # OpenLP - Open Source Lyrics Projection # # ---------------------------------------------------------------------- # # Copyright (c) 2008-2023 OpenLP Developers # # ---------------------------------------------------------------------- # # This program is free software: you can redistribute it and/or modify # # it under the terms of the GNU General Public License as published by # # the Free Software Foundation, either version 3 of the License, or # # (at your option) any later version. # # # # This program is distributed in the hope that it will be useful, # # but WITHOUT ANY WARRANTY; without even the implied warranty of # # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # # GNU General Public License for more details. # # # # You should have received a copy of the GNU General Public License # # along with this program. If not, see . # ########################################################################## """ The :mod:`openlp.core.common.applocation` module provides an utility for OpenLP receiving the data path etc. """ import logging import os import sys from pathlib import Path from appdirs import AppDirs import openlp from openlp.core.common import get_frozen_path from openlp.core.common.path import create_paths, resolve from openlp.core.common.platform import is_macosx, is_win from openlp.core.common.registry import Registry log = logging.getLogger(__name__) FROZEN_APP_PATH = Path(sys.argv[0]).parent APP_PATH = Path(openlp.__file__).parent class AppLocation(object): """ The :class:`AppLocation` class is a static class which retrieves a directory based on the directory type. """ AppDir = 1 DataDir = 2 PluginsDir = 3 VersionDir = 4 CacheDir = 5 LanguageDir = 6 @staticmethod def get_directory(dir_type=AppDir): """ Return the appropriate directory according to the directory type. :param dir_type: The directory type you want, for instance the data directory. Default *AppLocation.AppDir* :return: The requested path :rtype: Path """ if dir_type == AppLocation.AppDir or dir_type == AppLocation.VersionDir: path = get_frozen_path(FROZEN_APP_PATH, APP_PATH) elif dir_type == AppLocation.PluginsDir: path = get_frozen_path(FROZEN_APP_PATH, APP_PATH) / 'plugins' elif dir_type == AppLocation.LanguageDir: path = get_frozen_path(FROZEN_APP_PATH, _get_os_dir_path(dir_type)) / 'i18n' else: path = _get_os_dir_path(dir_type) return resolve(path) @staticmethod def get_data_path(): """ Return the path OpenLP stores all its data under. :return: The data path to use. :rtype: Path """ # Check if we have a different data location. if Registry().get('settings').contains('advanced/data path'): path = Path(Registry().get('settings').value('advanced/data path')) else: path = AppLocation.get_directory(AppLocation.DataDir) create_paths(path) return path @staticmethod def get_files(section=None, extension=''): """ Get a list of files from the data files path. :param None | str section: Defaults to *None*. The section of code getting the files - used to load from a section's data subdirectory. :param str extension: Defaults to ''. The extension to search for. For example:: '.png' :return: List of files found. :rtype: list[Path] """ path = AppLocation.get_data_path() if section: path = path / section try: file_paths = path.glob('*' + extension) return [file_path.relative_to(path) for file_path in file_paths] except OSError: return [] @staticmethod def get_section_data_path(section): """ Return the path a particular module stores its data under. :param str section: :rtype: Path """ path = AppLocation.get_data_path() / section create_paths(path) return path def _get_os_dir_path(dir_type): """ Return a path based on which OS and environment we are running in. :param dir_type: AppLocation Enum of the requested path type :return: The requested path :rtype: Path """ # If running from source, return the language directory from the source directory if dir_type == AppLocation.LanguageDir: directory = resolve(Path(openlp.__file__, '..', '..')) / 'resources' if directory.exists(): return directory if is_win(): openlp_folder_path = Path(os.getenv('APPDATA'), 'openlp') if dir_type == AppLocation.DataDir: return openlp_folder_path / 'data' elif dir_type == AppLocation.LanguageDir: return Path(openlp.__file__).parent return openlp_folder_path dirs = AppDirs('openlp', multipath=True) if is_macosx(): openlp_folder_path = Path(dirs.user_data_dir) if dir_type == AppLocation.DataDir: return openlp_folder_path / 'Data' elif dir_type == AppLocation.LanguageDir: return Path(openlp.__file__).parent return openlp_folder_path else: if dir_type == AppLocation.LanguageDir: site_dirs = dirs.site_data_dir.split(os.pathsep) for site_dir in site_dirs: if 'share/openlp' not in site_dir: continue directory = Path(site_dir) if directory.exists(): return directory return Path(site_dirs[0]) if dir_type == AppLocation.DataDir: return Path(dirs.user_data_dir) elif dir_type == AppLocation.CacheDir: return Path(dirs.user_cache_dir) if dir_type == AppLocation.DataDir: return Path(os.getenv('HOME'), '.openlp', 'data') return Path(os.getenv('HOME'), '.openlp')