Exemplo n.º 1
0
    def __init__(self, settings=None, use_from_host=True):
        settings = update_dict_recur(
            settings or {},
            self.get_for_host() if use_from_host else {})

        self.local_root = Path(inspect.getfile(self._local_root_class)).parent

        settings = update_dict_recur(self.DEFAULT, settings)
        self._data = validate_schema(self.SCHEMA, settings)
Exemplo n.º 2
0
    def __init__(self):
        key = self.__class__.KEY
        if not key:
            raise ValueError(f"Provide 'KEY' for settings")

        app_settings = {}
        if 'SETTINGS' in os.environ:
            module_path = os.environ['SETTINGS']
            try:
                module = importlib.import_module(module_path)
                app_settings = module.SETTINGS
            except ModuleNotFoundError:
                pass

        settings = update_dict_recur(
            self.__class__.DEFAULT, app_settings.get(self.__class__.KEY, {}))
        settings = validate_schema(self.__class__.SCHEMA, settings)

        self._data = settings
Exemplo n.º 3
0
def create_settings(settings: dict = None, update_with: dict = None):
    """Create app settings dict, overrided by env."""
    settings = settings or {}
    if update_with:
        settings = update_dict_recur(settings, update_with)

    for key, value in os.environ.items():
        if 'SETTINGS_' not in key:
            continue
        current_settings = settings
        parts = [
            part.lower() for part in key.replace('SETTINGS_', '').split('_')
        ]
        last_index = len(parts) - 1
        for index, part in enumerate(parts):
            if index == last_index:
                current_settings[part] = _convert_value(value)
            else:
                current_settings = current_settings.setdefault(part, {})
    return settings
Exemplo n.º 4
0
    def servers(self):
        if self._servers:
            return self._servers

        for scope, services in self.services.items():
            for info in services:
                for host in info['hosts']:
                    if host['provider'] != self.NAME:
                        continue
                    host = update_dict_recur(self.DEFAULT, host)
                    host = validate_schema(self.SCHEMA, host)
                    name = host['name']
                    for count in range(1, host['count'] + 1):
                        service_name = scope
                        if scope != name:
                            service_name = f"{scope}-{name}"
                        env = SETTINGS._data['env']
                        host['name'] = f"{env}-{service_name}-{count}"
                        host['components'] = info['components']
                        self._servers.append(host.copy())
        return self._servers
Exemplo n.º 5
0
class PythonSettings(AppSettings):
    NAME = 'python'
    SCHEMA = update_dict_recur(
        AppSettings.SCHEMA, {
            'root': {
                'type': 'string',
                'required': True
            },
            'version': {
                'type': 'string',
                'required': True
            },
            'build': {
                'type': 'dict',
                'schema': {
                    'fast': {
                        'type': 'boolean'
                    },
                    'path': {
                        'type': 'string'
                    }
                },
                'required': True
            }
        })
    DEFAULT = update_dict_recur(
        AppSettings.DEFAULT, {
            'bin': "python3 --version",
            'user': '******',
            'root': 'python',
            'version': '3.9.6',
            'build': {
                'fast': True,
                'path': 'build'
            },
            'systemd': {
                'config': ['Environment=PYTHONPATH={settings.home_abs}']
            }
        })

    @property
    def bin(self):
        return self.root_path / self._data['bin']

    @property
    def _local_root_class(self):
        return AppSettings

    @property
    def version(self):
        return self._data['version']

    @property
    def fast_build(self):
        return self._data['build']['fast']

    @property
    def build_path(self):
        return self.home_abs / self._data['build']['path']

    @property
    def site_packages_abs(self):
        return (self.root_abs / 'lib' / f'python{self.version[:3]}' /
                'site-packages')

    @property
    def root_path(self):
        return self.root_abs / 'bin'
Exemplo n.º 6
0
class WebAppSettings(AppSettings):
    NAME = 'web'
    SCHEMA = update_dict_recur(AppSettings.SCHEMA, {
        'host': {
            'type': 'string',
            'required': True
        },
        'port': {
            'type': 'integer',
            'required': True
        },
        'domain': {
            'type': 'string',
            'required': True
        },
        'use_https': {
            'type': 'boolean',
            'required': True
        },
        'ssl_certificate': {
            'type': 'string',
            'required': True
        },
        'ssl_certificate_key': {
            'type': 'string',
            'required': True
        },
        'nginx': {
            'type': 'dict',
            'schema': {
                'template': {
                    'type': 'string',
                    'required': True
                },
                'name': {
                    'type': 'string',
                    'required': True
                },
                'upstream_name': {
                    'type': 'string',
                    'required': True
                }
            },
            'required': True
        },
        'iptables': {
            'type': 'dict',
            'schema': {
                'v4': {
                    'type': 'string',
                    'required': True
                }
            },
            'required': True
        },
        'static': {
            'type': 'dict',
            'schema': {
                'link': {
                    'type': 'boolean',
                    'required': True
                },
                'url': {
                    'type': 'string',
                    'required': True
                },
                'dir': {
                    'type': 'string',
                    'required': True
                }
            },
            'required': True
        }
    },
                               copy=True)

    DEFAULT = update_dict_recur(AppSettings.DEFAULT, {
        'host': '0.0.0.0',
        'port': 8000,
        'domain': 'app.local',
        'use_https': True,
        'ssl_certificate': 'secure/certs/fullchain.pem',
        'ssl_certificate_key': 'secure/certs/privkey.pem',
        'nginx': {
            'template': 'nginx.conf',
            'name': 'web.conf',
            'upstream_name': 'app'
        },
        'iptables': {
            'v4': 'ipv4.rules'
        },
        'static': {
            'link': True,
            'url': '/static',
            'dir': 'static'
        }
    },
                                copy=True)

    @property
    def ssl_certificate(self):
        return self.home_abs / self._data['ssl_certificate']

    @property
    def ssl_certificate_key(self):
        return self.home_abs / self._data['ssl_certificate_key']

    @property
    def host(self):
        return self._data['host']

    @property
    def port(self):
        return self._data['port']

    @property
    def nginx_config(self):
        nginx = self._data['nginx']
        template, path = nginx['template'], nginx['name']
        if not template.startswith('/'):
            template = (self.local_root / template).resolve()
        return Path(template), path

    @property
    def nginx_upstream_name(self):
        return self._data['nginx']['upstream_name']

    @property
    def domain(self):
        return self._data['domain'].encode('idna').decode()

    @property
    def server_domains(self):
        """Return utf-8 domain and encoded by idna."""
        domains = [self.domain]
        if self._data['domain'] != self.domain:
            domains.append(self._data['domain'])
        return ' '.join(domains)

    @property
    def static_link(self):
        return self._data['static']['link']

    @property
    def static_dir(self):
        return self.home_abs / Path(self._data['static']['dir'])

    @property
    def static_url(self):
        return self._data['static']['url']

    @property
    def use_https(self):
        return self._data['use_https']

    @property
    def iptables_v4_rules(self):
        return (self.local_root / self._data['iptables']['v4']).read_text()