Source code for sunpy.util.config

"""
This module provides SunPy's configuration file functionality.
"""
import os
import configparser
from pathlib import Path

import sunpy
from sunpy.extern.appdirs import AppDirs

__all__ = ['load_config', 'print_config', 'CONFIG_DIR']

# This is to avoid creating a new config dir for each new dev version.
# We use AppDirs to locate and create the config directory.
dirs = AppDirs("sunpy", "sunpy")
# Default one set by AppDirs
CONFIG_DIR = dirs.user_config_dir


[docs]def load_config(): """ Read the "sunpyrc" configuration file. If one does not exists in the user's home directory then read in the defaults from "sunpy/data/sunpyrc". """ config = configparser.RawConfigParser() # Get locations of SunPy configuration files to be loaded config_files = _find_config_files() # Read in configuration files config.read(config_files) # Specify the working directory as a default so that the user's home # directory can be located in an OS-independent manner if not config.has_option('general', 'working_dir'): config.set('general', 'working_dir', str(Path.home() / "sunpy")) # Specify the database url as a default so that the user's home # directory can be located in an OS-independent manner if not config.has_option('database', 'url'): config.set('database', 'url', "sqlite:///" + str(Path.home() / "sunpy" / "sunpydb.sqlite")) # Set the download_dir to be relative to the working_dir working_dir = Path(config.get('general', 'working_dir')) download_dir = Path(config.get('downloads', 'download_dir')) sample_dir = config.get('downloads', 'sample_dir', fallback=dirs.user_data_dir) config.set('downloads', 'sample_dir', Path(sample_dir).expanduser().resolve().as_posix()) config.set('downloads', 'download_dir', (working_dir / download_dir).expanduser().resolve().as_posix()) return config
def _find_config_files(): """ Finds locations of SunPy configuration files. """ config_files = [] config_filename = 'sunpyrc' # find default configuration file module_dir = Path(sunpy.__file__).parent config_files.append(str(module_dir / 'data' / 'sunpyrc')) # if a user configuration file exists, add that to list of files to read # so that any values set there will override ones specified in the default # config file config_path = Path(_get_user_configdir()) if config_path.joinpath(config_filename).exists(): config_files.append(str(config_path.joinpath(config_filename))) return config_files def get_and_create_download_dir(): """ Get the config of download directory and create one if not present. """ download_dir = os.environ.get('SUNPY_DOWNLOADDIR') if download_dir: return download_dir download_dir = Path(sunpy.config.get('downloads', 'download_dir')).expanduser().resolve() if not _is_writable_dir(download_dir): raise RuntimeError(f'Could not write to SunPy downloads directory="{download_dir}"') return sunpy.config.get('downloads', 'download_dir') def get_and_create_sample_dir(): """ Get the config of download directory and create one if not present. """ sample_dir = Path(sunpy.config.get('downloads', 'sample_dir')).expanduser().resolve() if not _is_writable_dir(sample_dir): raise RuntimeError(f'Could not write to SunPy sample data directory="{sample_dir}"') return sunpy.config.get('downloads', 'sample_dir') def _is_writable_dir(p): """ Checks to see if a directory is writable. """ # Worried about multiple threads creating the directory at the same time. try: Path(p).mkdir(parents=True, exist_ok=True) except FileExistsError: # raised if there's an existing file instead of a directory return False else: return Path(p).is_dir() and os.access(p, os.W_OK) def _get_user_configdir(): """ Return the string representing the configuration dir. The default is set by "AppDirs" and can be accessed by importing ``sunpy.util.config.CONFIG_DIR``. You can override this with the "SUNPY_CONFIGDIR" environment variable. """ configdir = os.environ.get('SUNPY_CONFIGDIR', CONFIG_DIR) if not _is_writable_dir(configdir): raise RuntimeError(f'Could not write to SUNPY_CONFIGDIR="{configdir}"') return configdir