def render_config(*args):
    """Render the configuration for charm when all the interfaces are
    available.
    """
    with charm.provide_charm_instance() as charm_class:
        charm_class.upgrade_if_available(args)
    with charm.provide_charm_instance() as charm_class:
        charm_class.render_with_interfaces(args)
        charm_class.assess_status()
    reactive.set_state("config.rendered")
def setup_amqp_req(amqp):
    """Use the amqp interface to request access to the amqp broker using our
    local configuration.
    """
    amqp.request_access(username='******', vhost='openstack')
    with charm.provide_charm_instance() as instance:
        instance.assess_status()
def rejoin_instance(args):
    """Rejoin a given instance to the cluster.

    In the event an instance is removed from the cluster or fails to
    automatically rejoin, an instance can be rejoined to the cluster by an
    existing cluster member.

    Note: This action must be run on an instance that is already a member of
    the cluster. The action parameter, address, is the addresss of the instance
    that is being joined to the cluster.

    :param args: sys.argv
    :type args: sys.argv
    :side effect: Calls instance.rejoin_instance
    :returns: This function is called for its side effect
    :rtype: None
    :action param address: String address of the instance to be joined
    :action return: Dictionary with command output
    """
    address = ch_core.hookenv.action_get("address")
    try:
        with charm.provide_charm_instance() as instance:
            output = instance.rejoin_instance(address)
        ch_core.hookenv.action_set({"output": output, "outcome": "Success"})
    except subprocess.CalledProcessError as e:
        ch_core.hookenv.action_set({
            "output": e.stderr.decode("UTF-8"),
            "return-code": e.returncode,
            "traceback": traceback.format_exc()
        })
        ch_core.hookenv.action_fail("Rejoin instance failed")
示例#4
0
def configure_resources(*args):
    """Create/discover resources for management of load balancer instances."""
    if not reactive.is_flag_set('leadership.is_leader'):
        return ch_core.hookenv.action_fail('action must be run on the leader '
                                           'unit.')
    if not reactive.all_flags_set(
            'identity-service.available', 'neutron-api.available',
            'sdn-subordinate.available', 'amqp.available'):
        return ch_core.hookenv.action_fail('all required relations not '
                                           'available, please defer action'
                                           'until deployment is complete.')
    identity_service = reactive.endpoint_from_flag(
        'identity-service.available')
    try:
        (network, secgrp) = api_crud.get_mgmt_network(
            identity_service,
            create=reactive.is_flag_set('config.default.create-mgmt-network'),
        )
    except api_crud.APIUnavailable as e:
        ch_core.hookenv.action_fail(
            'Neutron API not available yet, deferring '
            'network creation/discovery. ("{}")'.format(e))
        return
    if network and secgrp:
        leadership.leader_set({
            'amp-boot-network-list': network['id'],
            'amp-secgroup-list': secgrp['id']
        })
    if reactive.is_flag_set('config.default.custom-amp-flavor-id'):
        # NOTE(fnordahl): custom flavor provided through configuration is
        # handled in the charm class configuration property.
        try:
            flavor = api_crud.get_nova_flavor(identity_service)
        except api_crud.APIUnavailable as e:
            ch_core.hookenv.action_fail('Nova API not available yet, '
                                        'deferring flavor '
                                        'creation. ("{}")'.format(e))
            return
        else:
            leadership.leader_set({'amp-flavor-id': flavor.id})

    amp_key_name = ch_core.hookenv.config('amp-ssh-key-name')
    if amp_key_name:
        identity_service = reactive.endpoint_from_flag(
            'identity-service.available')
        api_crud.create_nova_keypair(identity_service, amp_key_name)

    # Set qutotas to unlimited
    try:
        api_crud.set_service_quotas_unlimited(identity_service)
    except api_crud.APIUnavailable as e:
        ch_core.hookenv.action_fail(
            'Unbable to set quotas to unlimited: {}'.format(e))

    # execute port setup for leader, the followers will execute theirs on
    # `leader-settings-changed` hook
    with charm.provide_charm_instance() as octavia_charm:
        api_crud.setup_hm_port(identity_service, octavia_charm)
        octavia_charm.render_all_configs()
        octavia_charm._assess_status()
def init_db():
    """Run initial DB migrations when config is rendered."""
    with charm.provide_charm_instance() as octavia_charm:
        octavia_charm.db_sync()
        octavia_charm.restart_all()
        reactive.set_state('db.synced')
        octavia_charm.assess_status()
def default_setup_endpoint_available(tls):
    """When the identity-service interface is available, this default
    handler switches on the SSL support.
    """
    with charm.provide_charm_instance() as instance:
        instance.configure_ssl(tls)
        instance.assess_status()
示例#7
0
    def test_remove_config(self, unlink, exists, config):
        exists.return_value = True

        self.patch_object(keystone_ldap.ch_host, 'file_hash')

        reply = {
            'ldap-server': 'myserver',
            'ldap-user': '******',
            'ldap-password': '******',
            'ldap-suffix': 'suffix',
            'domain-name': 'userdomain',
        }

        def mock_config(key=None):
            if key:
                return reply.get(key)
            return reply
        config.side_effect = mock_config

        with provide_charm_instance() as kldap_charm:
            # Ensure a basic level of function from render_config
            cf = keystone_ldap.DOMAIN_CONF.format(reply['domain-name'])
            kldap_charm.remove_config()
            exists.assert_called_once_with(cf)
            unlink.assert_called_once_with(cf)
def configure_pools():
    local = reactive.endpoint_from_flag('ceph-local.available')
    remote = reactive.endpoint_from_flag('ceph-remote.available')
    with charm.provide_charm_instance() as charm_instance:
        for pool, attrs in charm_instance.eligible_pools(local.pools).items():
            if not (charm_instance.mirror_pool_enabled(pool)
                    and charm_instance.mirror_pool_has_peers(pool)):
                charm_instance.mirror_pool_enable(pool)
            pg_num = attrs['parameters'].get('pg_num', None)
            max_bytes = attrs['quota'].get('max_bytes', None)
            max_objects = attrs['quota'].get('max_objects', None)
            if 'erasure_code_profile' in attrs['parameters']:
                ec_profile = attrs['parameters'].get('erasure_code_profile',
                                                     None)
                remote.create_erasure_pool(pool,
                                           erasure_profile=ec_profile,
                                           pg_num=pg_num,
                                           app_name='rbd',
                                           max_bytes=max_bytes,
                                           max_objects=max_objects)
            else:
                size = attrs['parameters'].get('size', None)
                remote.create_replicated_pool(pool,
                                              replicas=size,
                                              pg_num=pg_num,
                                              app_name='rbd',
                                              max_bytes=max_bytes,
                                              max_objects=max_objects)
示例#9
0
def render(*args):
    hookenv.log("about to call the render_configs with {}".format(args))
    with charm.provide_charm_instance() as ironic_charm:
        ironic_charm.render_with_interfaces(charm.optional_interfaces(args))
        ironic_charm.configure_tls()
        ironic_charm.assess_status()
    reactive.set_state('config.complete')
示例#10
0
def configure_neutron():
    neutron = reactive.endpoint_from_flag('neutron-plugin.connected')
    ovsdb = reactive.endpoint_from_flag('ovsdb-cms.available')
    ch_core.hookenv.log('DEBUG: neutron_config_data="{}"'.format(
        neutron.neutron_config_data))
    service_plugins = neutron.neutron_config_data.get('service_plugins',
                                                      '').split(',')
    service_plugins = [svc for svc in service_plugins if svc not in ['router']]
    service_plugins.append('networking_ovn.l3.l3_ovn.OVNL3RouterPlugin')
    tenant_network_types = neutron.neutron_config_data.get(
        'tenant_network_types', '').split(',')
    tenant_network_types.insert(0, 'geneve')

    def _split_if_str(s):
        _s = s or ''
        return _s.split()

    with charm.provide_charm_instance() as instance:
        options = instance.adapters_instance.options
        sections = {
            'ovn': [
                ('ovn_nb_connection', ','.join(ovsdb.db_nb_connection_strs)),
                ('ovn_nb_private_key', options.ovn_key),
                ('ovn_nb_certificate', options.ovn_cert),
                ('ovn_nb_ca_cert', options.ovn_ca_cert),
                ('ovn_sb_connection', ','.join(ovsdb.db_sb_connection_strs)),
                ('ovn_sb_private_key', options.ovn_key),
                ('ovn_sb_certificate', options.ovn_cert),
                ('ovn_sb_ca_cert', options.ovn_ca_cert),
                ('ovn_l3_scheduler', options.ovn_l3_scheduler),
                ('ovn_metadata_enabled', options.ovn_metadata_enabled),
                ('enable_distributed_floating_ip',
                 options.enable_distributed_floating_ip),
                ('dns_servers', ','.join(_split_if_str(options.dns_servers))),
                ('dhcp_default_lease_time', options.dhcp_default_lease_time),
                ('ovn_dhcp4_global_options',
                 ','.join(_split_if_str(options.ovn_dhcp4_global_options))),
                ('ovn_dhcp6_global_options',
                 ','.join(_split_if_str(options.ovn_dhcp6_global_options))),
            ],
            'ml2_type_geneve': [
                ('vni_ranges',
                 ','.join(_split_if_str(options.geneve_vni_ranges))),
                ('max_header_size', '38'),
            ],
        }
        neutron.configure_plugin(
            'ovn',
            service_plugins=','.join(service_plugins),
            mechanism_drivers='ovn',
            tenant_network_types=','.join(tenant_network_types),
            subordinate_configuration={
                'neutron-api': {
                    '/etc/neutron/plugins/ml2/ml2_conf.ini': {
                        'sections': sections,
                    },
                },
            },
        )
        instance.assess_status()
def db_monitor_respond():
    """Response to db-monitor relation changed."""
    ch_core.hookenv.log("db-monitor connected", ch_core.hookenv.DEBUG)
    db_monitor = reactive.endpoint_from_flag("db-monitor.connected")

    # get related application name = user
    username = related_app = ch_core.hookenv.remote_service_name()

    # get or create db-monitor user password
    db_monitor_stored_passwd_key = "db-monitor.{}.passwd".format(related_app)
    password = leadership.leader_get(db_monitor_stored_passwd_key)
    if not password:
        password = ch_core.host.pwgen()
        leadership.leader_set({db_monitor_stored_passwd_key: password})

    # provide relation data
    with charm.provide_charm_instance() as instance:
        # NOTE (rgildein): Create a custom user with administrator privileges,
        # but read-only access.
        if not instance.create_cluster_user(db_monitor.relation_ip, username,
                                            password, True):
            ch_core.hookenv.log("db-monitor user was not created.",
                                ch_core.hookenv.WARNING)
            return

        db_monitor.provide_access(
            port=instance.cluster_port,
            user=username,
            password=password,
        )

        instance.assess_status()
示例#12
0
def plugin_info_barbican_publish():
    barbican = reactive.endpoint_from_flag('endpoint.secrets.joined')
    secrets_storage = reactive.endpoint_from_flag('secrets-storage.available')
    with charm.provide_charm_instance() as barbican_vault_charm:
        if secrets_storage.vault_ca:
            ch_core.hookenv.log('Installing vault CA certificate')
            barbican_vault_charm.install_ca_cert(secrets_storage.vault_ca)
        ch_core.hookenv.log('Retrieving secret-id from vault ({})'.format(
            secrets_storage.vault_url),
                            level=ch_core.hookenv.INFO)
        secret_id = vault_utils.retrieve_secret_id(secrets_storage.vault_url,
                                                   secrets_storage.unit_token)
        vault_data = {
            'approle_role_id': secrets_storage.unit_role_id,
            'approle_secret_id': secret_id,
            'vault_url': secrets_storage.vault_url,
            'kv_mountpoint': barbican_vault_charm.secret_backend_name,
        }
        if barbican_vault_charm.installed_ca_name:
            vault_data.update(
                {'ssl_ca_crt_file': barbican_vault_charm.installed_ca_name})
        ch_core.hookenv.log('Publishing vault plugin info to barbican',
                            level=ch_core.hookenv.INFO)
        barbican.publish_plugin_info('vault', vault_data)
        reactive.clear_flag('endpoint.secrets-storage.changed')
示例#13
0
def configure_ceph(ceph):
    with charm.provide_charm_instance() as charm_instance:
        key = ceph.key
        if key and isinstance(key, str):
            charm_instance.configure_ceph_keyring(key)
        else:
            hookenv.log("No ceph keyring data is available")
def enable_metadata():
    nova_compute = reactive.endpoint_from_flag('nova-compute.connected')
    nova_compute.publish_shared_secret()
    with charm.provide_charm_instance() as charm_instance:
        ch_core.hookenv.log('DEBUG: {} {} {} {}'.format(
            charm_instance, charm_instance.packages, charm_instance.services,
            charm_instance.restart_map),
                            level=ch_core.hookenv.INFO)
        charm_instance.enable_metadata()
    with charm.provide_charm_instance() as charm_instance:
        ch_core.hookenv.log('DEBUG: {} {} {} {}'.format(
            charm_instance, charm_instance.packages, charm_instance.services,
            charm_instance.restart_map),
                            level=ch_core.hookenv.INFO)
        charm_instance.install()
        charm_instance.assess_status()
def render_config_with_certs(amqp, keystone, shared_db, certs):
    with charm.provide_charm_instance() as magnum_charm:
        magnum_charm.configure_tls(certs)
        magnum_charm.render_with_interfaces(
            [amqp, keystone, shared_db, certs])
        magnum_charm.assess_status()
    reactive.set_state('config.complete')
def enable_openstack():
    reactive.set_flag('charm.ovn-chassis.enable-openstack')
    nova_compute = reactive.endpoint_from_flag('nova-compute.connected')
    nova_compute.publish_shared_secret()
    with charm.provide_charm_instance() as charm_instance:
        charm_instance.install()
        charm_instance.assess_status()
def config_changed():
    with charm.provide_charm_instance() as charm_instance:
        charm_instance.upgrade_if_available([
            reactive.endpoint_from_flag('ceph-local.available'),
            reactive.endpoint_from_flag('ceph-remote.available'),
        ])
        charm_instance.assess_status()
def maybe_enable_ovn_driver():
    ovsdb = reactive.endpoint_from_flag('ovsdb-subordinate.available')
    if ovsdb.ovn_configured:
        reactive.set_flag('charm.octavia.enable-ovn-driver')
        with charm.provide_charm_instance() as charm_instance:
            charm_instance.install()
            charm_instance.assess_status()
def render():
    ovsdb_peer = reactive.endpoint_from_flag('ovsdb-peer.available')
    with charm.provide_charm_instance() as ovn_charm:
        ovn_charm.render_with_interfaces([ovsdb_peer])
        # NOTE: The upstream ctl scripts currently do not support passing
        # multiple connection strings to the ``ovsdb-tool join-cluster``
        # command.
        #
        # This makes it harder to bootstrap a cluster in the event
        # one of the units are not available.  Thus the charm performs the
        # ``join-cluster`` command expliclty before handing off to the
        # upstream scripts.
        #
        # Replace this with functionality in ``ovn-ctl`` when support has been
        # added upstream.
        ovn_charm.join_cluster(
            '/var/lib/openvswitch/ovnnb_db.db', 'OVN_Northbound',
            ovsdb_peer.db_connection_strs((ovsdb_peer.cluster_local_addr, ),
                                          ovsdb_peer.db_nb_cluster_port),
            ovsdb_peer.db_connection_strs(ovsdb_peer.cluster_remote_addrs,
                                          ovsdb_peer.db_nb_cluster_port))
        ovn_charm.join_cluster(
            '/var/lib/openvswitch/ovnsb_db.db', 'OVN_Southbound',
            ovsdb_peer.db_connection_strs((ovsdb_peer.cluster_local_addr, ),
                                          ovsdb_peer.db_sb_cluster_port),
            ovsdb_peer.db_connection_strs(ovsdb_peer.cluster_remote_addrs,
                                          ovsdb_peer.db_sb_cluster_port))
        if ovn_charm.enable_services():
            reactive.set_flag('config.rendered')
        ovn_charm.assess_status()
def keystone_departed():
    """
    Service restart should be handled on the keystone side
    in this case.
    """
    with charm.provide_charm_instance() as charm_instance:
        charm_instance.remove_config()
def add_instance(args):
    """Add an instance to the cluster.

    If a new instance is not able to be joined to the cluster, this action will
    configure and add the unit to the cluster.

    :param args: sys.argv
    :type args: sys.argv
    :side effect: Calls instance.configure_and_add_instance
    :returns: This function is called for its side effect
    :rtype: None
    :action param address: String address of the instance to be joined
    :action return: Dictionary with command output
    """
    # Note: Due to issues/# reactive does not initiate Endpoints during an
    # action execution.  This is here to work around that until the issue is
    # resolved.
    reactive.Endpoint._startup()
    address = ch_core.hookenv.action_get("address")
    try:
        with charm.provide_charm_instance() as instance:
            output = instance.configure_and_add_instance(address)
        ch_core.hookenv.action_set({"output": output, "outcome": "Success"})
    except subprocess.CalledProcessError as e:
        ch_core.hookenv.action_set({
            "output": e.stderr.decode("UTF-8"),
            "return-code": e.returncode,
            "traceback": traceback.format_exc()
        })
        ch_core.hookenv.action_fail("Add instance failed")
示例#22
0
def configure_instances_for_clustering(cluster):
    """Configure cluster peers for clustering.

    Prepare peers to be added to the cluster.

    :param cluster: Cluster interface
    :type cluster: MySQLInnoDBClusterPeers object
    """
    ch_core.hookenv.log("Configuring instances for clustering.", "DEBUG")
    with charm.provide_charm_instance() as instance:
        for unit in cluster.all_joined_units:
            if unit.received['unit-configure-ready']:
                instance.configure_instance(
                    unit.received['cluster-address'])
                instance.add_instance_to_cluster(
                    unit.received['cluster-address'])
        # Verify all are configured
        for unit in cluster.all_joined_units:
            if not reactive.is_flag_set(
                    "leadership.set.cluster-instance-configured-{}"
                    .format(unit.received['cluster-address'])):
                return
        # All have been configured
        leadership.leader_set(
            {"cluster-instances-configured": True})
        instance.assess_status()
def set_cluster_option(args):
    """Set cluster option.

    Set an option on the InnoDB cluster. Action parameter key is the name of
    the option and action parameter value is the value to be set.

    :param args: sys.argv
    :type args: sys.argv
    :side effect: Calls instance.set_cluster_option
    :returns: This function is called for its side effect
    :rtype: None
    :action param key: String option name
    :action param value: String option value
    :action return: Dictionary with command output
    """
    key = ch_core.hookenv.action_get("key")
    value = ch_core.hookenv.action_get("value")
    try:
        with charm.provide_charm_instance() as instance:
            output = instance.set_cluster_option(key, value)
        ch_core.hookenv.action_set({"output": output, "outcome": "Success"})
    except subprocess.CalledProcessError as e:
        ch_core.hookenv.action_set({
            "output": e.stderr.decode("UTF-8"),
            "return-code": e.returncode,
            "traceback": traceback.format_exc()
        })
        ch_core.hookenv.action_fail("Set cluster option failed")
def remove_instance(args):
    """Remove an instance from the cluster.

    This action cleanly removes an instance from the cluster. If an instance
    has died and is unrecoverable it shows up in metadata as MISSING. This
    action will remove an instance from the metadata using the force option
    even if it is unreachable.

    :param args: sys.argv
    :type args: sys.argv
    :side effect: Calls instance.remove_instance
    :returns: This function is called for its side effect
    :rtype: None
    :action param address: String address of the instance to be removed
    :action param force: Boolean force removal of missing instance
    :action return: Dictionary with command output
    """
    address = ch_core.hookenv.action_get("address")
    force = ch_core.hookenv.action_get("force")
    try:
        with charm.provide_charm_instance() as instance:
            output = instance.remove_instance(address, force=force)
        ch_core.hookenv.action_set({"output": output, "outcome": "Success"})
    except subprocess.CalledProcessError as e:
        ch_core.hookenv.action_set({
            "output": e.stderr.decode("UTF-8"),
            "return-code": e.returncode,
            "traceback": traceback.format_exc()
        })
        ch_core.hookenv.action_fail("Remove instance failed")
def restore_mysqldump(args):
    """Restore a mysqldump backup.

    Execute mysqldump of the database(s).  The mysqldump action will take
    in the databases action parameter. If the databases parameter is unset all
    databases will be dumped, otherwise only the named databases will be
    dumped. The action will use the basedir action parameter to dump the
    database into the base directory.

    A successful mysqldump backup will set the action results key,
    mysqldump-file, with the full path to the dump file.

    :param args: sys.argv
    :type args: sys.argv
    :side effect: Calls instance.restore_mysqldump
    :returns: This function is called for its side effect
    :rtype: None
    :action param dump-file: Path to mysqldump file to restore.
    :action return:
    """
    dump_file = ch_core.hookenv.action_get("dump-file")
    try:
        with charm.provide_charm_instance() as instance:
            instance.restore_mysqldump(dump_file)
        ch_core.hookenv.action_set({"outcome": "Success"})
    except subprocess.CalledProcessError as e:
        ch_core.hookenv.action_set({
            "output": e.stderr.decode("UTF-8"),
            "return-code": e.returncode,
            "traceback": traceback.format_exc()
        })
        ch_core.hookenv.action_fail(
            "Restore mysqldump of {} failed".format(dump_file))
def setup_hm_port():
    """Create a per unit Neutron and OVS port for Octavia Health Manager.

    This is used to plug the unit into the overlay network for direct
    communication with the octavia managed load balancer instances running
    within the deployed cloud.
    """
    neutron_ovs = reactive.endpoint_from_flag('neutron-openvswitch.connected')
    ovsdb = reactive.endpoint_from_flag('ovsdb-subordinate.available')
    host_id = neutron_ovs.host() if neutron_ovs else ovsdb.chassis_name
    with charm.provide_charm_instance() as octavia_charm:
        identity_service = reactive.endpoint_from_flag(
            'identity-service.available')
        try:
            if api_crud.setup_hm_port(
                    identity_service,
                    octavia_charm,
                    host_id=host_id):
                # trigger config render to make systemd-networkd bring up
                # automatic IP configuration of the new port right now.
                reactive.set_flag('config.changed')
                if reactive.is_flag_set('charm.octavia.action_setup_hm_port'):
                    reactive.clear_flag('charm.octavia.action_setup_hm_port')
        except api_crud.APIUnavailable as e:
            ch_core.hookenv.log('Neutron API not available yet, deferring '
                                'port discovery. ("{}")'
                                .format(e),
                                level=ch_core.hookenv.DEBUG)
            return
示例#27
0
def configure_websso(websso_fid_sp):
    with charm.provide_charm_instance() as charm_instance:
        if charm_instance.configuration_complete():
            # publish config options for all remote units of a given rel
            options = charm_instance.options
            websso_fid_sp.publish(options.protocol_name, options.idp_name,
                                  options.user_facing_name)
def default_config_changed():
    """Default handler for config.changed state from reactive.  Just see if
    our status has changed.  This is just to clear any errors that may have
    got stuck due to missing async handlers, etc.
    """
    with charm.provide_charm_instance() as instance:
        instance.config_changed()
        instance.assess_status()
def create_ea_definitions():
    principal_neutron = \
        endpoint_from_flag('neutron.available')
    if principal_neutron.principal_charm_state() == "True":
        with provide_charm_instance() as charm_class:
            charm_class.create_ea_definitions()
        status_set('active', 'Unit is ready')
        set_flag('create-ea-definitions.done')
def configure_neutron(principle):
    with provide_charm_instance() as charm_class:
        config = charm_class.get_neutron_conf()
        principal_neutron = \
            endpoint_from_flag('neutron.available')
        principal_neutron.configure_principal(config)
        clear_flag('create-ea-definitions.done')
        set_flag('neutron.configured')
def config_changed():
    if reactive.is_flag_set('leadership.is_leader'):
        with charm.provide_charm_instance() as instance:
            instance.render_all_configs()
            instance.wait_until_cluster_available()
            if reactive.is_flag_set('config.changed.auto-rejoin-tries'):
                instance.set_cluster_option("autoRejoinTries",
                                            instance.options.auto_rejoin_tries)
    else:
        with charm.provide_charm_instance() as instance:
            try:
                instance.wait_until_cluster_available()
            except Exception:
                ch_core.hookenv.log("Cluster was not availble as expected.",
                                    "WARNING")
        ch_core.hookenv.log("Non-leader requst to restart.", "DEBUG")
        coordinator.acquire('config-changed-restart')
def update_unit_acls(args):
    """Update IP allow list on each node in cluster.

    Update IP allow list on each node in cluster. At present this can only
    be done when replication is stopped.
    """
    with charm.provide_charm_instance() as instance:
        instance.update_acls()
def default_setup_certificates(tls):
    """When the identity-service interface is available, this default
    handler switches on the SSL support.
    """
    with charm.provide_charm_instance() as instance:
        for cn, req in instance.get_certificate_requests().items():
            tls.add_request_server_cert(cn, req['sans'])
        tls.request_server_certs()
        instance.assess_status()
def default_amqp_connection(amqp):
    """Handle the default amqp connection.

    This requires that the charm implements get_amqp_credentials() to
    provide a tuple of the (user, vhost) for the amqp server
    """
    with charm.provide_charm_instance() as instance:
        user, vhost = instance.get_amqp_credentials()
        amqp.request_access(username=user, vhost=vhost)
        instance.assess_status()
def render_stuff(*args):
    """Render the configuration for Barbican when all the interfaces are
    available.

    Note that the HSM interface is optional and thus is only used if it is
    available.
    """
    hookenv.log("about to call the render_configs with {}".format(args))
    with charm.provide_charm_instance() as barbican_charm:
        barbican_charm.render_with_interfaces(
            charm.optional_interfaces(args, 'hsm.available'))
        barbican_charm.assess_status()
def default_setup_database(database):
    """Handle the default database connection setup

    This requires that the charm implements get_database_setup() to provide
    a list of dictionaries;
    [{'database': ..., 'username': ..., 'hostname': ..., 'prefix': ...}]

    The prefix can be missing: it defaults to None.
    """
    with charm.provide_charm_instance() as instance:
        for db in instance.get_database_setup():
            database.configure(**db)
        instance.assess_status()
def default_setup_endpoint_connection(keystone):
    """When the keystone interface connects, register this unit into the
    catalog.  This is the default handler, and calls on the charm class to
    provide the endpoint information.  If multiple endpoints are needed,
    then a custom endpoint handler will be needed.
    """
    with charm.provide_charm_instance() as instance:
        keystone.register_endpoints(instance.service_type,
                                    instance.region,
                                    instance.public_url,
                                    instance.internal_url,
                                    instance.admin_url)
        instance.assess_status()
def default_install():
    """Provide a default install handler

    The instance automagically becomes the derived OpenStackCharm instance.
    The kv() key charmers.openstack-release-version' is used to cache the
    release being used for this charm.  It is determined by the
    default_select_release() function below, unless this is overridden by
    the charm author
    """
    unitdata.kv().unset(defaults.OPENSTACK_RELEASE_KEY)
    with charm.provide_charm_instance() as instance:
        instance.install()
    reactive.set_state('charm.installed')
def cluster_connected(hacluster):
    """Configure HA resources in corosync."""
    with charm.provide_charm_instance() as barbican_charm:
        barbican_charm.configure_ha_resources(hacluster)
        barbican_charm.assess_status()
def run_default_upgrade_charm():
    with charm.provide_charm_instance() as instance:
        instance.upgrade_charm()
    reactive.remove_state('run-default-upgrade-charm')
def run_default_update_status():
    with charm.provide_charm_instance() as instance:
        instance.assess_status()
    reactive.remove_state('run-default-update-status')
def run_storage_backend():
    with charm.provide_charm_instance() as instance:
        instance.send_storage_backend_data()
def default_pre_series_upgrade():
    """Default handler for pre-series-upgrade.
    """
    with charm.provide_charm_instance() as instance:
        instance.series_upgrade_prepare()
def default_post_series_upgrade():
    """Default handler for post-series-upgrade.
    """
    with charm.provide_charm_instance() as instance:
        instance.series_upgrade_complete()