Exemplo n.º 1
0
 def find_candidate(self, app, prevent_docker=None):
     if prevent_docker is None:
         prevent_docker = ucr_is_true('appcenter/prudence/docker/%s' %
                                      app.id)
     if app.docker:
         prevent_docker = False
     app_version = LooseVersion(app.version)
     apps = list(reversed(self.get_all_apps_with_id(app.id)))
     not_permitted_app = None
     for _app in apps:
         if prevent_docker and _app.docker and not (
                 _app.docker_migration_works or _app.docker_migration_link):
             continue
         if _app <= app:
             continue
         if _app.required_app_version_upgrade:
             if LooseVersion(
                     _app.required_app_version_upgrade) > app_version:
                 continue
         if not _app.install_permissions_exist():
             # do not consider app without permission...
             # ... until it is the only one (and then fail eventually...)
             if not_permitted_app is None:
                 not_permitted_app = _app
             continue
         return _app
     if not_permitted_app:
         return not_permitted_app
Exemplo n.º 2
0
 def get_apps(cls):
     ret = []
     apps = Apps().get_all_apps()
     blacklist = ucr_get('repository/app_center/blacklist')
     whitelist = ucr_get('repository/app_center/whitelist')
     if blacklist:
         blacklist = re.split('\s*,\s*', blacklist)
     if whitelist:
         whitelist = re.split('\s*,\s*', whitelist)
     for app in apps:
         if blacklist or whitelist:
             unlocalised_app = app.get_app_cache_obj().copy(
                 locale='en').find_by_component_id(app.component_id)
             if cls._blacklist_includes_app(
                     blacklist,
                     unlocalised_app) and not cls._blacklist_includes_app(
                         whitelist, unlocalised_app):
                 continue
         if app.end_of_life and not app.is_installed():
             continue
         if ucr_is_true('ad/member') and app.ad_member_issue_hide:
             continue
         if ucr_get('server/role') not in app.server_role:
             continue
         if app._docker_prudence_is_true():
             _apps = [
                 _app for _app in Apps().get_all_apps_with_id(app.id)
                 if _app.docker_migration_works or not _app.docker
             ]
             try:
                 app = sorted(_apps)[-1]
             except IndexError:
                 continue
         ret.append(app)
     return ret
Exemplo n.º 3
0
	def create(self, hostname, env):
		ports = []
		for app_id, container_port, host_port, protocol in app_ports_with_protocol():
			if app_id == self.app.id:
				port_definition = '%d:%d/%s' % (host_port, container_port, protocol)
				ports.append(port_definition)
		volumes = set(self.app.docker_volumes[:])
		for app_volume in [self.app.get_data_dir(), self.app.get_conf_dir()]:
			app_volume = '%s:%s' % (app_volume, app_volume)
			volumes.add(app_volume)
		if self.app.host_certificate_access:
			cert_dir = '/etc/univention/ssl/%s.%s' % (ucr_get('hostname'), ucr_get('domainname'))
			cert_volume = '%s:%s:ro' % (cert_dir, cert_dir)
			volumes.add(cert_volume)
		volumes.add('/sys/fs/cgroup:/sys/fs/cgroup:ro')                     # systemd
		if ucr_is_true('appcenter/docker/container/proxy/settings', default=True):
			if os.path.isfile('/etc/apt/apt.conf.d/80proxy'):
				volumes.add('/etc/apt/apt.conf.d/80proxy:/etc/apt/apt.conf.d/80proxy:ro')  # apt proxy
		env_file = self.ucr_filter_env_file(env)
		command = None
		if self.app.docker_script_init:
			command = shlex.split(self.app.docker_script_init)
		args = shlex.split(ucr_get(self.app.ucr_docker_params_key, ''))
		for tmpfs in ("/run", "/run/lock"):                                 # systemd
			args.extend(["--tmpfs", tmpfs])
		seccomp_profile = "/etc/docker/seccomp-systemd.json"
		args.extend(["--security-opt", "seccomp:%s" % seccomp_profile])     # systemd
		args.extend(["-e", "container=docker"])                             # systemd
		container = create(self.image, command, hostname, ports, volumes, env_file, args)
		ucr_save({self.app.ucr_container_key: container})
		self.container = container
		return container
Exemplo n.º 4
0
 def main(self, args):
     from univention.appcenter.actions import get_action
     if args.update:
         get_action('update').call()
     apps = args.app
     if not apps:
         apps = Apps().get_all_locally_installed_apps()
     for app in apps:
         self.debug('Checking %s' % app)
         if not app.is_installed():
             continue
         upgrade_available = self._check_for_upgrades(app)
         if upgrade_available is True:
             ucr_save({app.ucr_upgrade_key: 'yes'})
         elif upgrade_available is False:
             ucr_save({app.ucr_upgrade_key: None})
     return any(ucr_is_true(app.ucr_upgrade_key) for app in apps)
Exemplo n.º 5
0
 def find_candidate(self, app, prevent_docker=None):
     if prevent_docker is None:
         prevent_docker = ucr_is_true('appcenter/prudence/docker/%s' %
                                      app.id)
     if app.docker:
         prevent_docker = False
     app_version = LooseVersion(app.version)
     apps = list(reversed(self.get_all_apps_with_id(app.id)))
     for _app in apps:
         if prevent_docker and _app.docker and not (
                 _app.docker_migration_works or _app.docker_migration_link):
             continue
         if _app <= app:
             break
         if _app.required_app_version_upgrade:
             if LooseVersion(
                     _app.required_app_version_upgrade) > app_version:
                 continue
         return _app
Exemplo n.º 6
0
 def sanitize_value(self, app, value):
     super(BoolSetting, self).sanitize_value(app, value)
     if isinstance(value, bool):
         return value
     return ucr_is_true(self.name, value=value)
	def iter_upgradable_apps(self):
		for app in Apps().get_all_locally_installed_apps():
			if ucr_is_true(app.ucr_upgrade_key):
				yield app
    def _start_docker_image(self, app, hostdn, password, args):
        docker = self._get_docker(app)
        if not docker:
            return

        self.log('Verifying Docker registry manifest for app image %s' %
                 docker.image)
        docker.verify()

        if args.pull_image:
            docker.pull()

        self.log('Initializing app image')
        hostname = explode_dn(hostdn, 1)[0]
        set_vars = (args.set_vars or {}).copy()
        after_image_configuration = {}
        for setting in app.get_settings():
            if setting.should_go_into_image_configuration(app):
                if setting.name not in set_vars:
                    set_vars[setting.name] = setting.get_initial_value(app)
            else:
                try:
                    after_image_configuration[setting.name] = set_vars.pop(
                        setting.name)
                except KeyError:
                    after_image_configuration[
                        setting.name] = setting.get_initial_value(app)
        set_vars['docker/host/name'] = '%s.%s' % (ucr_get('hostname'),
                                                  ucr_get('domainname'))
        set_vars['ldap/hostdn'] = hostdn
        if app.docker_env_ldap_user:
            set_vars[app.docker_env_ldap_user] = hostdn
        set_vars['server/role'] = app.docker_server_role
        set_vars['update/warning/releasenotes'] = 'no'
        ucr_keys_list = list(ucr_keys())
        for var in [
                'nameserver.*', 'repository/online/server',
                'repository/app_center/server', 'update/secure_apt',
                'appcenter/index/verify', 'ldap/base', 'ldap/server.*',
                'ldap/master.*', 'locale.*', 'domainname'
        ]:
            for key in ucr_keys_list:
                if re.match(var, key):
                    set_vars[key] = ucr_get(key)
        if ucr_is_true('appcenter/docker/container/proxy/settings',
                       default=True):
            if ucr_get('proxy/http'):
                set_vars['proxy/http'] = ucr_get('proxy/http')
                set_vars['http_proxy'] = ucr_get('proxy/http')
            if ucr_get('proxy/https'):
                set_vars['proxy/https'] = ucr_get('proxy/https')
                set_vars['https_proxy'] = ucr_get('proxy/https')
            if ucr_get('proxy/no_proxy'):
                set_vars['proxy/no_proxy'] = ucr_get('proxy/no_proxy')
                set_vars['no_proxy'] = ucr_get('proxy/no_proxy')
        set_vars['updater/identify'] = 'Docker App'
        database_connector = DatabaseConnector.get_connector(app)
        database_password_file = None
        if database_connector:
            try:
                database_password = database_connector.get_db_password()
                database_password_file = database_connector.get_db_password_file(
                )
                if database_password:
                    set_vars[
                        app.
                        docker_env_database_host] = database_connector.get_db_host(
                        )
                    db_port = database_connector.get_db_port()
                    if db_port:
                        set_vars[app.docker_env_database_port] = db_port
                    set_vars[
                        app.
                        docker_env_database_name] = database_connector.get_db_name(
                        )
                    set_vars[
                        app.
                        docker_env_database_user] = database_connector.get_db_user(
                        )
                    if app.docker_env_database_password_file:
                        set_vars[
                            app.
                            docker_env_database_password_file] = database_password_file
                    else:
                        set_vars[
                            app.
                            docker_env_database_password] = database_password
                autostart_variable = database_connector.get_autostart_variable(
                )
                if autostart_variable:
                    set_vars[autostart_variable] = 'no'
            except DatabaseError as exc:
                raise DatabaseConnectorError(str(exc))

        container = docker.create(hostname, set_vars)
        self.log('Preconfiguring container %s' % container)
        autostart = 'yes'
        if not Start.call(app=app):
            raise DockerCouldNotStartContainer(str(Status.get_status(app)))
        time.sleep(3)
        if not docker.is_running():
            dlogs = docker.dockerd_logs()
            clogs = docker.logs()
            inspect = docker.inspect_container()
            msg = """
The container for {app} could not be started!

docker logs {container}:
{clogs}

dockerd logs:
{dlogs}

docker inspect:
{state}
{graphdriver}""".format(app=app,
                        container=docker.container,
                        clogs=clogs,
                        dlogs=dlogs,
                        state=inspect.get('State'),
                        graphdriver=inspect.get('GraphDriver'))
            raise AppCenterErrorContainerStart(msg)
        # copy password files
        if os.path.isfile(app.secret_on_host):
            # we can not use docker-cp here, as we support read-only containers too :-(
            f_name = docker.path('/etc/machine.secret')
            f_dir = os.path.dirname(f_name)
            # if the container start takes a little longer the f_dir may not exist yet
            # so wait max 60s
            for i in xrange(0, 12):
                if os.path.isdir(f_dir):
                    break
                time.sleep(5)
            try:
                with open(f_name, 'w+b') as f:
                    os.chmod(f_name, 0o600)
                    f.write(password)
            except Exception as exc:
                raise DockerCouldNotStartContainer(
                    'Could not copy machine.secret to container: %s (%s)' %
                    (str(exc), docker.logs()))
        if database_password_file:
            docker.cp_to_container(database_password_file,
                                   database_password_file)
        # update timezone in container
        logfile_logger = get_logfile_logger('docker.base')
        docker.execute('rm',
                       '-f',
                       '/etc/timezone',
                       '/etc/localtime',
                       _logger=logfile_logger)
        docker.cp_to_container('/etc/timezone',
                               '/etc/timezone',
                               _logger=logfile_logger)
        docker.cp_to_container('/etc/localtime',
                               '/etc/localtime',
                               _logger=logfile_logger)
        # configure app
        after_image_configuration.update(set_vars)
        configure = get_action('configure')
        configure.call(app=app,
                       autostart=autostart,
                       run_script='no',
                       set_vars=after_image_configuration)
Exemplo n.º 9
0
 def test_install(self, app):
     return not app.docker or ucr_is_true('appcenter/docker', True)
Exemplo n.º 10
0
    if master_version is None:
        raise KeyError
except KeyError:
    print('App "{}" is not installed on DC master.'.format(app_name))
    sys.exit(2)

ret = LooseVersion(app.version) > LooseVersion(master_version)

if '-v' in sys.argv:
    print('Version of app "{}" on this host: "{}"'.format(
        app_name, app.version))
    print('Version of app "{}" on DC master: "{}"'.format(
        app_name, master_version))
    if ret:
        print(
            'Error: local version of app "{}" higher than DC masters versions!'
            .format(app_name))
    else:
        print(
            'OK: local version of app "{}" is lower or equal to that of the DC master.'
            .format(app_name))

ucrv = 'ucsschool/join/ignore-version-mismatch/{}/{}'.format(
    master_version, app.version)
if ucr_is_true(ucrv):
    if '-v' in sys.argv:
        print('Ignoring version mismatch, because "{}" is set.'.format(ucrv))
    sys.exit(0)

sys.exit(int(ret))
    def _start_docker_image(self, app, hostdn, password, args):
        docker = self._get_docker(app)
        if not docker:
            return

        self.log('Verifying Docker registry manifest for app image %s' %
                 docker.image)
        docker.verify()

        if args.pull_image:
            self.log('Downloading app image %s' % docker.image)
            if not docker.pull():
                raise DockerImagePullFailed(docker.image)

        self.log('Initializing app image')
        hostname = explode_dn(hostdn, 1)[0]
        set_vars = (args.set_vars or {}).copy()
        after_image_configuration = {}
        for setting in app.get_settings():
            if setting.should_go_into_image_configuration(app):
                if setting.name not in set_vars:
                    set_vars[setting.name] = setting.get_initial_value()
            else:
                try:
                    after_image_configuration[setting.name] = set_vars.pop(
                        setting.name)
                except KeyError:
                    pass
        set_vars['docker/host/name'] = '%s.%s' % (ucr_get('hostname'),
                                                  ucr_get('domainname'))
        set_vars['ldap/hostdn'] = hostdn
        if app.docker_env_ldap_user:
            set_vars[app.docker_env_ldap_user] = hostdn
        set_vars['server/role'] = app.docker_server_role
        set_vars['update/warning/releasenotes'] = 'no'
        ucr_keys_list = list(ucr_keys())
        for var in [
                'nameserver.*', 'repository/online/server',
                'repository/app_center/server', 'update/secure_apt',
                'appcenter/index/verify', 'ldap/master.*', 'locale.*',
                'domainname'
        ]:
            for key in ucr_keys_list:
                if re.match(var, key):
                    set_vars[key] = ucr_get(key)
        if ucr_is_true('appcenter/docker/container/proxy/settings',
                       default=True):
            if ucr_get('proxy/http'):
                set_vars['proxy/http'] = ucr_get('proxy/http')
                set_vars['http_proxy'] = ucr_get('proxy/http')
            if ucr_get('proxy/https'):
                set_vars['proxy/https'] = ucr_get('proxy/https')
                set_vars['https_proxy'] = ucr_get('proxy/https')
            if ucr_get('proxy/no_proxy'):
                set_vars['proxy/no_proxy'] = ucr_get('proxy/no_proxy')
                set_vars['no_proxy'] = ucr_get('proxy/no_proxy')
        set_vars['updater/identify'] = 'Docker App'
        database_connector = DatabaseConnector.get_connector(app)
        database_password_file = None
        if database_connector:
            try:
                database_password = database_connector.get_db_password()
                database_password_file = database_connector.get_db_password_file(
                )
                if database_password:
                    set_vars[
                        app.
                        docker_env_database_host] = database_connector.get_db_host(
                        )
                    db_port = database_connector.get_db_port()
                    if db_port:
                        set_vars[app.docker_env_database_port] = db_port
                    set_vars[
                        app.
                        docker_env_database_name] = database_connector.get_db_name(
                        )
                    set_vars[
                        app.
                        docker_env_database_user] = database_connector.get_db_user(
                        )
                    if app.docker_env_database_password_file:
                        set_vars[
                            app.
                            docker_env_database_password_file] = database_password_file
                    else:
                        set_vars[
                            app.
                            docker_env_database_password] = database_password
                autostart_variable = database_connector.get_autostart_variable(
                )
                if autostart_variable:
                    set_vars[autostart_variable] = 'no'
            except DatabaseError as exc:
                raise DatabaseConnectorError(str(exc))

        container = docker.create(hostname, set_vars)
        self.log('Preconfiguring container %s' % container)
        autostart = 'yes'
        if not Start.call(app=app):
            raise DockerCouldNotStartContainer()
        time.sleep(3)
        if not docker.is_running():
            dlogs = docker.dockerd_logs()
            clogs = docker.logs()
            inspect = docker.inspect_container()
            msg = """
The container for {app} could not be started!

docker logs {container}:
{clogs}

dockerd logs:
{dlogs}

docker inspect:
{state}
{graphdriver}""".format(app=app,
                        container=docker.container,
                        clogs='\n'.join(clogs),
                        dlogs='\n'.join(dlogs),
                        state=inspect.get('State'),
                        graphdriver=inspect.get('GraphDriver'))
            raise AppCenterErrorContainerStart(msg)
        if password:
            with open(docker.path('/etc/machine.secret'), 'w+b') as f:
                f.write(password)
        docker.cp_to_container('/etc/timezone', '/etc/timezone')
        docker.cp_to_container('/etc/localtime', '/etc/localtime')
        if database_password_file:
            docker.cp_to_container(database_password_file,
                                   database_password_file)
        after_image_configuration.update(set_vars)
        configure = get_action('configure')
        configure.call(app=app,
                       autostart=autostart,
                       run_script='no',
                       set_vars=after_image_configuration)