Пример #1
0
class Config(object):
    """The base Cachito Flask configuration."""

    DEBUG = False
    # Additional loggers to set to the level defined in CACHITO_LOG_LEVEL
    CACHITO_ADDITIONAL_LOGGERS: List[str] = ["cachito.common.packages_data"]
    CACHITO_DEFAULT_PACKAGE_MANAGERS: List[str] = ["gomod"]
    # This sets the level of the "flask.app" logger, which is accessed from current_app.logger
    CACHITO_LOG_LEVEL = "INFO"
    CACHITO_LOG_FORMAT = "[%(asctime)s %(name)s %(levelname)s %(module)s.%(funcName)s] %(message)s"
    CACHITO_MAX_PER_PAGE = 100
    # Pairs of mutually exclusive package managers (cannot process the same package)
    CACHITO_MUTUALLY_EXCLUSIVE_PACKAGE_MANAGERS = [("npm", "yarn")]
    CACHITO_PACKAGE_MANAGERS = ["gomod"]
    CACHITO_REQUEST_FILE_LOGS_DIR: Optional[str] = None
    # Users that are allowed to use the "user" property when creating a request
    CACHITO_USER_REPRESENTATIVES: List[str] = []
    CACHITO_WORKER_USERNAMES: List[str] = []
    LOGIN_DISABLED = False
    TESTING = False

    # Temp dir used by the Prometheus Flask Exporter to coalesce the metrics from the threads
    if "PROMETHEUS_MULTIPROC_DIR" not in os.environ.keys():
        raise ConfigError(
            "The environment variable PROMETHEUS_MULTIPROC_DIR must be set prior to execution"
        )
    else:
        PROMETHEUS_METRICS_TEMP_DIR = os.environ["PROMETHEUS_MULTIPROC_DIR"]
Пример #2
0
def validate_celery_config(conf, **kwargs):
    """
    Perform basic validatation on the Celery configuration when the worker is initialized.

    :param celery.app.utils.Settings conf: the Celery application configuration to validate
    :raises ConfigError: if the configuration is invalid
    """
    for required_dir_conf in ('cachito_bundles_dir', 'cachito_sources_dir'):
        required_dir = conf.get(required_dir_conf)
        if not required_dir or not os.path.isdir(required_dir):
            raise ConfigError(
                f'The configuration "{required_dir_conf}" must be set to an existing directory'
            )

    if not conf.get('cachito_api_url'):
        raise ConfigError('The configuration "cachito_api_url" must be set')
Пример #3
0
def validate_cachito_config(config, cli=False):
    """
    Perform basic validatation on the Cachito configuration.

    :param dict config: a dictionary of configuration values
    :param bool cli: a boolean that denotes if the configuration should be validated for the CLI
    :raises ConfigError: if the configuration is invalid
    """
    # Validate the required config variables
    for config_var in (
            "CACHITO_DEFAULT_PACKAGE_MANAGERS",
            "CACHITO_LOG_LEVEL",
            "CACHITO_MAX_PER_PAGE",
            "CACHITO_MUTUALLY_EXCLUSIVE_PACKAGE_MANAGERS",
            "CACHITO_LOG_FORMAT",
            "CACHITO_BUNDLES_DIR",
            "SQLALCHEMY_DATABASE_URI",
            "PROMETHEUS_METRICS_TEMP_DIR",
    ):
        if config_var == "CACHITO_BUNDLES_DIR":
            if cli:
                # Don't verify CACHITO_BUNDLES_DIR if this is coming from the CLI since it's not
                # used and requires the CACHITO_BUNDLES_DIR to exist. This is a hassle for hooks
                # in the deployments for OpenShift/Kubernetes.
                continue

            required_dir = config.get(config_var)
            if not required_dir or not os.path.isdir(required_dir):
                raise ConfigError(
                    f'The configuration "{config_var}" must be set to an existing directory'
                )
        elif config_var == "CACHITO_MUTUALLY_EXCLUSIVE_PACKAGE_MANAGERS":
            mutually_exclusive = config.get(config_var)
            if mutually_exclusive is None:
                raise ConfigError(
                    f'The configuration "{config_var}" must be set')

            if not all(
                    isinstance(pair, (tuple, list)) and len(pair) == 2
                    for pair in mutually_exclusive):
                raise ConfigError(
                    f'All values in "{config_var}" must be pairs (2-tuples or 2-item lists)'
                )
        elif not config.get(config_var):
            raise ConfigError(f'The configuration "{config_var}" must be set')
Пример #4
0
def validate_nexus_config():
    """
    Perform validation on the Celery configuration for package managers that require Nexus.

    :raise ConfigError: if the Celery configuration isn't configured for Nexus
    """
    conf = get_worker_config()
    for nexus_conf in ("cachito_nexus_password", "cachito_nexus_url", "cachito_nexus_username"):
        if not conf.get(nexus_conf):
            raise ConfigError(
                f'The configuration "{nexus_conf}" must be set for this package manager'
            )
Пример #5
0
def validate_npm_config():
    """
    Perform validation on the Celery configuration for the npm package manager.

    :raise ConfigError: if the Celery configuration isn't configured for npm
    """
    validate_nexus_config()
    conf = get_worker_config()
    if not conf.get("cachito_nexus_npm_proxy_repo_url"):
        raise ConfigError(
            'The configuration "cachito_nexus_npm_proxy_repo_url" must be set for this package '
            "manager")
Пример #6
0
def validate_pip_config():
    """
    Perform validation on the Celery configuration for the pip package manager.

    :raise ConfigError: if the Celery configuration isn't configured for pip
    """
    validate_nexus_config()
    conf = get_worker_config()
    for pip_config in ("cachito_nexus_pypi_proxy_url", "cachito_nexus_pip_raw_repo_name"):
        if not conf.get(pip_config):
            raise ConfigError(
                f'The configuration "{pip_config}" must be set for this package manager'
            )
Пример #7
0
def validate_celery_config(conf, **kwargs):
    """
    Perform basic validation on the Celery configuration when the worker is initialized.

    :param celery.app.utils.Settings conf: the Celery application configuration to validate
    :raises ConfigError: if the configuration is invalid
    """
    for required_dir_conf in ("cachito_bundles_dir", "cachito_sources_dir"):
        required_dir = conf.get(required_dir_conf)
        if not required_dir or not os.path.isdir(required_dir):
            raise ConfigError(
                f'The configuration "{required_dir_conf}" must be set to an existing directory'
            )

    if not conf.get("cachito_api_url"):
        raise ConfigError('The configuration "cachito_api_url" must be set')

    hoster_username = conf.get("cachito_nexus_hoster_username")
    hoster_password = conf.get("cachito_nexus_hoster_password")
    if (hoster_username or hoster_password) and not (hoster_username and hoster_password):
        raise ConfigError(
            'If "cachito_nexus_hoster_username" or "cachito_nexus_hoster_password" is set, '
            "the other must also be set"
        )

    if conf.get("cachito_auth_type") == "cert" and conf.get("cachito_auth_cert") is None:
        raise ConfigError('cachito_auth_cert configuration must be set for "cert" authentication')

    if not isinstance(conf.get("cachito_default_environment_variables"), dict):
        raise ConfigError(
            'The configuration "cachito_default_environment_variables" must be a dictionary'
        )

    default_env_vars = conf.cachito_default_environment_variables
    for pkg_manager_value in default_env_vars.values():
        if not isinstance(pkg_manager_value, dict):
            raise ConfigError(
                'The configuration "cachito_default_environment_variables" must be a '
                "dictionary of dictionaries"
            )
        for env_var_info in pkg_manager_value.values():
            if not isinstance(env_var_info, dict):
                raise ConfigError(
                    'The configuration "cachito_default_environment_variables" must be a '
                    "dictionary of dictionaries of dictionaries!"
                )
            if set(env_var_info.keys()) != {"value", "kind"}:
                raise ConfigError(
                    'Each environment variable in the "cachito_default_environment_variables" '
                    'configuration must contain the "value" and "kind" keys'
                )

    invalid_gomod_env_vars = default_env_vars.get("gomod", {}).keys() & {"GOCACHE", "GOPATH"}
    if invalid_gomod_env_vars:
        raise ConfigError(
            'The configuration "cachito_default_environment_variables.gomod" cannot overwrite the '
            f"following environment variables: {', '.join(invalid_gomod_env_vars)}"
        )

    cachito_request_file_logs_dir = conf.get("cachito_request_file_logs_dir")
    if cachito_request_file_logs_dir:
        if not os.path.isdir(cachito_request_file_logs_dir):
            raise ConfigError(
                f"cachito_request_file_logs_dir, {cachito_request_file_logs_dir},"
                " must exist and be a directory"
            )
        if not os.access(cachito_request_file_logs_dir, os.W_OK):
            raise ConfigError(
                f"cachito_request_file_logs_dir, {cachito_request_file_logs_dir}, is not writable!"
            )