Beispiel #1
0
def sync_server_topology():
    """Sync servers into buckets in the masterapi.
    """
    admin_srv = admin.Server(context.GLOBAL.ldap.conn)
    servers = admin_srv.list({'cell': context.GLOBAL.cell})
    zkclient = context.GLOBAL.zk.conn

    # Cells are composed of buckets. The topology is ~1000 servers per pod
    # with each pod composed of racks, each ~40 servers.
    def _server_pod_rack(servername):
        # In the absence of any information about the server and topology, we
        # simply hash the servername and use the value to place the server in
        # a fictive topology of at most 4 pods, each with 16 racks.
        svr_hash = hashlib.md5(servername.encode()).hexdigest()
        svr_id = int(svr_hash, 16)  # That is a 128 bit number
        pod = (svr_id >> (128 - 2))  # First 2 bits -> pod
        # below the first 2 bits, we take the rest, modulo 16
        rack = (svr_id % (1 << (128 - 2))) % 16
        return (pod, rack)

    for server in servers:
        servername = server['_id']
        partition = server.get('partition')

        (pod, rack) = _server_pod_rack(servername)
        pod_bucket = 'pod:{:04X}'.format(pod)
        rack_bucket = 'rack:{:04X}'.format(rack)

        _LOGGER.info('Update: %r(partition:%r) -> %r, %r',
                     servername, partition, pod_bucket, rack_bucket)

        masterapi.create_bucket(zkclient, pod_bucket, parent_id=None)
        masterapi.cell_insert_bucket(zkclient, pod_bucket)
        masterapi.create_bucket(zkclient, rack_bucket, parent_id=pod_bucket)
        masterapi.create_server(
            zkclient,
            servername,
            rack_bucket,
            partition=partition
        )

    ldap_servers = set(server['_id'] for server in servers)
    zk_servers = set(masterapi.list_servers(zkclient))
    zk_server_presence = set(zkclient.get_children(z.SERVER_PRESENCE))
    for servername in zk_servers - ldap_servers:
        if servername in zk_server_presence:
            _LOGGER.warning('%s not in LDAP but node still present, skipping.',
                            servername)
        else:
            _LOGGER.info('Delete: %s', servername)
            masterapi.delete_server(zkclient, servername)
Beispiel #2
0
 def delete(server):
     """Delete server configuration"""
     masterapi.delete_server(context.GLOBAL.zk.conn, server)