Ejemplo n.º 1
0
 def __init__(self, hostname, protocol="https", port=6443, entry='api/v1', **kwargs):
     self.hostname = hostname
     self.username = kwargs.get('username', '')
     self.password = kwargs.get('password', '')
     self.token = kwargs.get('token', '')
     self.auth = self.token if self.token else (self.username, self.password)
     self.api = ContainerClient(hostname, self.auth, protocol, port, entry)
Ejemplo n.º 2
0
 def __init__(self,
         hostname, protocol="http", port=8080, **kwargs):
     super(Hawkular, self).__init__(kwargs)
     self.hostname = hostname
     self.username = kwargs.get('username', '')
     self.password = kwargs.get('password', '')
     self.tenant_id = kwargs.get('tenant_id', 'hawkular')
     self.auth = self.username, self.password
     self.inv_api = ContainerClient(hostname, self.auth, protocol, port, "hawkular/inventory")
     self.alerts_api = ContainerClient(hostname, self.auth, protocol, port, "hawkular/alerts")
Ejemplo n.º 3
0
class Openshift(Kubernetes):
    def __init__(self,
            hostname, protocol="https", port=8443, k_entry="api/v1", o_entry="oapi/v1", **kwargs):
        self.hostname = hostname
        self.username = kwargs.get('username', '')
        self.password = kwargs.get('password', '')
        self.token = kwargs.get('token', '')
        self.auth = self.token if self.token else (self.username, self.password)
        self.k_api = ContainerClient(hostname, self.auth, protocol, port, k_entry)
        self.o_api = ContainerClient(hostname, self.auth, protocol, port, o_entry)
        self.api = self.k_api  # default api is the kubernetes one for Kubernetes-class requests

    def list_route(self):
        """Returns list of routes"""
        entities = []
        entities_j = self.o_api.get('route')[1]['items']
        for entity_j in entities_j:
            meta = entity_j['metadata']
            entity = Route(meta['name'], meta['namespace'])
            entities.append(entity)
        return entities

    def list_service(self):
        """Returns list of services"""
        entities = []
        entities_j = self.api.get('service')[1]['items']
        for entity_j in entities_j:
            meta, spec = entity_j['metadata'], entity_j['spec']
            entity = Service(
                meta['name'], meta['namespace'], spec['portalIP'], spec['sessionAffinity'])
            entities.append(entity)
        return entities

    def list_image_registry(self):
        """Returns list of image registries (image streams)"""
        entities = []
        entities_j = self.o_api.get('imagestream')[1]['items']
        for entity_j in entities_j:
            reg_raw = entity_j['status']['dockerImageRepository'].split('/')[0]
            host, port = reg_raw.split(':') if ':' in reg_raw else (reg_raw, '')
            entity = ImageRegistry(host, port)
            if entity not in entities:
                entities.append(entity)
        return entities

    def list_project(self):
        """Returns list of projects"""
        entities = []
        entities_j = self.o_api.get('project')[1]['items']
        for entity_j in entities_j:
            meta = entity_j['metadata']
            entity = Project(meta['name'])
            entities.append(entity)
        return entities
Ejemplo n.º 4
0
 def __init__(self,
              hostname,
              protocol="https",
              port=8443,
              k_entry="api/v1",
              o_entry="oapi/v1",
              **kwargs):
     self.hostname = hostname
     self.username = kwargs.get('username', '')
     self.password = kwargs.get('password', '')
     self.token = kwargs.get('token', '')
     self.auth = self.token if self.token else (self.username,
                                                self.password)
     self.k_api = ContainerClient(hostname, self.auth, protocol, port,
                                  k_entry)
     self.o_api = ContainerClient(hostname, self.auth, protocol, port,
                                  o_entry)
     self.api = self.k_api  # default api is the kubernetes one for Kubernetes-class requests
Ejemplo n.º 5
0
 def __init__(self,
         hostname, protocol="https", port=8443, k_entry="api/v1", o_entry="oapi/v1", **kwargs):
     self.hostname = hostname
     self.username = kwargs.get('username', '')
     self.password = kwargs.get('password', '')
     self.token = kwargs.get('token', '')
     self.auth = self.token if self.token else (self.username, self.password)
     self.k_api = ContainerClient(hostname, self.auth, protocol, port, k_entry)
     self.o_api = ContainerClient(hostname, self.auth, protocol, port, o_entry)
     self.api = self.k_api  # default api is the kubernetes one for Kubernetes-class requests
Ejemplo n.º 6
0
 def __init__(self, hostname, protocol="http", port=8080, **kwargs):
     super(Hawkular, self).__init__(kwargs)
     self.hostname = hostname
     self.username = kwargs.get('username', '')
     self.password = kwargs.get('password', '')
     self.tenant_id = kwargs.get('tenant_id', 'hawkular')
     self.auth = self.username, self.password
     self.inv_api = ContainerClient(hostname, self.auth, protocol, port,
                                    "hawkular/inventory")
     self.alerts_api = ContainerClient(hostname, self.auth, protocol, port,
                                       "hawkular/alerts")
     self.metrics_api = ContainerClient(hostname, self.auth, protocol, port,
                                        "hawkular/metrics")
Ejemplo n.º 7
0
class Hawkular(MgmtSystemAPIBase):
    """Hawkular management system

    Hawkular REST API method calls.
    Will be used by cfme_tests project to verify Hawkular content shown in CFME UI

    Args:
        hostname: The Hawkular hostname.
        protocol: Hawkular REST API protocol. Default value: 'http'
        port: Hawkular REST API port on provided host. Default value: '8080'.
        entry: Hawkular REST API entry point URI. Default value: 'hawkular/inventory'
        username: The username to connect with.
        password: The password to connect with.

    """

    _stats_available = {
        'num_server': lambda self: len(self.list_server()),
        'num_deployment': lambda self: len(self.list_server_deployment()),
        'num_datasource': lambda self: len(self.list_server_datasource()),
    }

    def __init__(self,
            hostname, protocol="http", port=8080, **kwargs):
        super(Hawkular, self).__init__(kwargs)
        self.hostname = hostname
        self.username = kwargs.get('username', '')
        self.password = kwargs.get('password', '')
        self.tenant_id = kwargs.get('tenant_id', 'hawkular')
        self.auth = self.username, self.password
        self.inv_api = ContainerClient(hostname, self.auth, protocol, port, "hawkular/inventory")
        self.alerts_api = ContainerClient(hostname, self.auth, protocol, port, "hawkular/alerts")

    def _check_inv_version(self, version):
        return version in self._get_inv_json('status')['Implementation-Version']

    def info(self):
        raise NotImplementedError('info not implemented.')

    def clone_vm(self, source_name, vm_name):
        raise NotImplementedError('clone_vm not implemented.')

    def create_vm(self, vm_name):
        raise NotImplementedError('create_vm not implemented.')

    def current_ip_address(self, vm_name):
        raise NotImplementedError('current_ip_address not implemented.')

    def delete_vm(self, vm_name):
        raise NotImplementedError('delete_vm not implemented.')

    def deploy_template(self, template, *args, **kwargs):
        raise NotImplementedError('deploy_template not implemented.')

    def disconnect(self):
        pass

    def does_vm_exist(self, name):
        raise NotImplementedError('does_vm_exist not implemented.')

    def get_ip_address(self, vm_name):
        raise NotImplementedError('get_ip_address not implemented.')

    def is_vm_running(self, vm_name):
        raise NotImplementedError('is_vm_running not implemented.')

    def is_vm_stopped(self, vm_name):
        raise NotImplementedError('is_vm_stopped not implemented.')

    def is_vm_suspended(self, vm_name):
        raise NotImplementedError('is_vm_suspended not implemented.')

    def list_flavor(self):
        raise NotImplementedError('list_flavor not implemented.')

    def list_template(self):
        raise NotImplementedError('list_template not implemented.')

    def list_vm(self, **kwargs):
        raise NotImplementedError('list_vm not implemented.')

    def remove_host_from_cluster(self, hostname):
        raise NotImplementedError('remove_host_from_cluster not implemented.')

    def restart_vm(self, vm_name):
        raise NotImplementedError('restart_vm not implemented.')

    def start_vm(self, vm_name):
        raise NotImplementedError('start_vm not implemented.')

    def stop_vm(self, vm_name):
        raise NotImplementedError('stop_vm not implemented.')

    def suspend_vm(self, vm_name):
        raise NotImplementedError('restart_vm not implemented.')

    def vm_status(self, vm_name):
        raise NotImplementedError('vm_status not implemented.')

    def wait_vm_running(self, vm_name, num_sec):
        raise NotImplementedError('wait_vm_running not implemented.')

    def wait_vm_stopped(self, vm_name, num_sec):
        raise NotImplementedError('wait_vm_stopped not implemented.')

    def wait_vm_suspended(self, vm_name, num_sec):
        raise NotImplementedError('wait_vm_suspended not implemented.')

    def list_server_deployment(self, feed_id=None):
        """Returns list of server deployments. Possible filters: `feed_id`"""
        resources = self.list_resource(feed_id=feed_id, resource_type_id='Deployment')
        deployments = []
        if resources:
            for resource in resources:
                deployments.append(Deployment(resource.id, resource.name, resource.path))
        return deployments

    def list_server(self, feed_id=None):
        """Returns list of middleware servers. Possible filters: `feed_id`"""
        resources = self.list_resource(feed_id=feed_id, resource_type_id='WildFly Server')
        servers = []
        if resources:
            for resource in resources:
                resource_data = self.get_config_data(
                    feed_id=resource.path.feed_id, resource_id=resource.id)
                server_data = resource_data.value
                servers.append(Server(resource.id, resource.name, resource.path, server_data))
        return servers

    def list_resource(self, resource_type_id, feed_id=None):
        """Returns list of resources. Possible filters: `feed_id`, `type_id`"""
        if not feed_id:
            resources = []
            for feed in self.list_feed():
                resources.extend(self._list_resource(feed_id=feed.path.feed_id,
                                                    resource_type_id=resource_type_id))
            return resources
        else:
            return self._list_resource(feed_id=feed_id, resource_type_id=resource_type_id)

    def list_child_resource(self, feed_id, resource_id, recursive=False):
        """Returns list of resources. Possible filters: `feed_id`, `type_id`"""
        if not feed_id or not resource_id:
            raise KeyError("'feed_id' and 'resource_id' are a mandatory field!")
        resources = []
        if recursive:
            entities_j = self._get_inv_json('traversal/f;{}/r;{}/recursive;over=isParentOf;type=r'
                                          .format(feed_id, resource_id))
        else:
            entities_j = self._get_inv_json('traversal/f;{}/r;{}/type=r'
                                            .format(feed_id, resource_id))
        if entities_j:
            for entity_j in entities_j:
                resources.append(Resource(entity_j['id'], entity_j['name'],
                                          CanonicalPath(entity_j['path'])))
        return resources

    def _list_resource(self, feed_id, resource_type_id=None):
        """Returns list of resources by provided `type_id` and `feed_id`"""
        if not feed_id:
            raise KeyError("'feed_id' is a mandatory field!")
        entities = []
        if resource_type_id:
            entities_j = self._get_inv_json('traversal/f;{}/rt;{}/rl;defines/type=r'
                                        .format(feed_id, resource_type_id))
        else:
            entities_j = self._get_inv_json('traversal/f;{}/type=r'.format(feed_id))
        if entities_j:
            for entity_j in entities_j:
                entities.append(Resource(entity_j['id'], entity_j['name'],
                                         CanonicalPath(entity_j['path'])))
        return entities

    def get_config_data(self, feed_id, resource_id):
        """Returns the data/configuration information about resource by provided\
         `feed_id` and `resource_id`."""
        if not feed_id or not resource_id:
            raise KeyError("'feed_id' and 'resource_id' are mandatory field!")
        entity_j = self._get_inv_json('entity/f;{}/r;{}/d;configuration'
                                      .format(feed_id, resource_id))
        if entity_j:
            return ResourceData(entity_j['name'], CanonicalPath(entity_j['path']),
                                entity_j['value'])
        return None

    def list_feed(self):
        """Returns list of feeds"""
        entities = []
        entities_j = self._get_inv_json('traversal/type=f')
        if entities_j:
            for entity_j in entities_j:
                entities.append(Feed(entity_j['id'], CanonicalPath(entity_j['path'])))
        return entities

    def list_resource_type(self, feed_id):
        """Returns list of resource types by provided `feed_id`"""
        if not feed_id:
            raise KeyError("'feed_id' is a mandatory field!")
        entities = []
        entities_j = self._get_inv_json('traversal/f;{}/type=rt'.format(feed_id))
        if entities_j:
            for entity_j in entities_j:
                entities.append(ResourceType(entity_j['id'], entity_j['name'], entity_j['path']))
        return entities

    def list_operation_definition(self, feed_id, resource_type_id):
        if feed_id is None or resource_type_id is None:
            raise KeyError("'feed_id' and 'resource_type_id' are mandatory fields!")
        res_j = self._get_inv_json('traversal/f;{}/rt;{}/type=ot'.format(feed_id, resource_type_id))
        operations = []
        if res_j:
            for res in res_j:
                operations.append(OperationType(res['id'], res['name'], CanonicalPath(res['path'])))
        return operations

    def list_server_datasource(self, feed_id=None):
        """Returns list of datasources. Possible filters: `feed_id`"""
        resources = self.list_resource(feed_id=feed_id, resource_type_id='Datasource')
        datasources = []
        if resources:
            for resource in resources:
                datasources.append(Datasource(resource.id, resource.name, resource.path))
        return datasources

    def edit_config_data(self, resource_data, **kwargs):
        """Edits the data.value information for resource by provided\
         `feed_id` and `resource_id`."""
        if not isinstance(resource_data, ResourceData) or not resource_data.value:
            raise KeyError(
                "'resource_data' should be ResourceData with 'value' attribute")
        if not kwargs or 'feed_id' not in kwargs or 'resource_id' not in kwargs:
            raise KeyError("'feed_id' and 'resource_id' are mandatory field!")
        r = self._put_inv_status('entity/f;{}/r;{}/d;configuration'
                .format(kwargs['feed_id'], kwargs['resource_id']), {"value": resource_data.value})
        return r

    def create_resource(self, resource, resource_data, resource_type, **kwargs):
        """Creates new resource and creates it's data by provided\
         `feed_id` and `resource_id`."""
        if not isinstance(resource, Resource):
            raise KeyError("'resource' should be an instance of Resource")
        if not isinstance(resource_data, ResourceData) or not resource_data.value:
            raise KeyError(
                "'resource_data' should be ResourceData with 'value' attribute")
        if not isinstance(resource_type, ResourceType):
            raise KeyError("'resource_type' should be an instance of ResourceType")
        if not kwargs or 'feed_id' not in kwargs:
            raise KeyError('Variable "feed_id" id mandatory field!')

        resource_id = urlquote(resource.id, safe='')
        r = self._post_inv_status('entity/f;{}/resource'.format(kwargs['feed_id']),
                                data={"name": resource.name, "id": resource.id,
                                "resourceTypePath": "rt;{}"
                                  .format(resource_type.path.resource_type_id)})
        if r:
            r = self._post_inv_status('entity/f;{}/r;{}/data'
                                    .format(kwargs['feed_id'], resource_id),
                                    data={'role': 'configuration', "value": resource_data.value})
        else:
            # if resource or it's data was not created correctly, delete resource
            self._delete_inv_status('entity/f;{}/r;{}'.format(kwargs['feed_id'], resource_id))
        return r

    def delete_resource(self, feed_id, resource_id):
        """Removed the resource by provided `feed_id` and `resource_id`."""
        if not feed_id or not resource_id:
            raise KeyError("'feed_id' and 'resource_id' are mandatory fields!")
        r = self._delete_inv_status('entity/f;{}/r;{}'.format(feed_id, resource_id))
        return r

    def list_event(self, start_time=0, end_time=sys.maxsize):
        """Returns the list of events filtered by provided start time and end time.
        Or lists all events if no argument provided.
        This information is wrapped into Event."""
        entities = []
        entities_j = self._get_alerts_json('events?startTime={}&endTime={}'
                                     .format(start_time, end_time))
        if entities_j:
            for entity_j in entities_j:
                entity = Event(entity_j['id'], entity_j['eventType'], entity_j['ctime'],
                               entity_j['dataSource'], entity_j['dataId'],
                               entity_j['category'], entity_j['text'])
                entities.append(entity)
        return entities

    def _get_inv_json(self, path):
        return self.inv_api.get_json(path, headers={"Hawkular-Tenant": self.tenant_id})

    def _post_inv_status(self, path, data):
        return self.inv_api.post_status(path, data,
                                        headers={"Hawkular-Tenant": self.tenant_id,
                                                "Content-Type": "application/json"})

    def _put_inv_status(self, path, data):
        return self.inv_api.put_status(path, data, headers={"Hawkular-Tenant": self.tenant_id,
                                                       "Content-Type": "application/json"})

    def _delete_inv_status(self, path):
        return self.inv_api.delete_status(path, headers={"Hawkular-Tenant": self.tenant_id})

    def _get_alerts_json(self, path):
        return self.alerts_api.get_json(path, headers={"Hawkular-Tenant": self.tenant_id})
Ejemplo n.º 8
0
class Kubernetes(ContainerMgmtSystemAPIBase):

    _stats_available = {
        'num_container':
        lambda self: len(self.list_container()),
        'num_pod':
        lambda self: len(self.list_container_group()),
        'num_service':
        lambda self: len(self.list_service()),
        'num_replication_controller':
        lambda self: len(self.list_replication_controller()),
        'num_replication_controller_labels':
        lambda self: len(self.list_replication_controller_labels()),
        'num_image':
        lambda self: len(self.list_image()),
        'num_node':
        lambda self: len(self.list_node()),
        'num_image_registry':
        lambda self: len(self.list_image_registry()),
        'num_project':
        lambda self: len(self.list_project()),
    }

    def __init__(self,
                 hostname,
                 protocol="https",
                 port=6443,
                 entry='api/v1',
                 **kwargs):
        self.hostname = hostname
        self.username = kwargs.get('username', '')
        self.password = kwargs.get('password', '')
        self.token = kwargs.get('token', '')
        self.auth = self.token if self.token else (self.username,
                                                   self.password)
        self.api = ContainerClient(hostname, self.auth, protocol, port, entry)

    def disconnect(self):
        pass

    def _parse_image_info(self, image_str):
        """Splits full image name into registry, name and tag

        Both registry and tag are optional, name is always present.

        Example:
            localhost:5000/nginx:latest => localhost:5000, nginx, latest
        """
        registry, image_str = image_str.split(
            '/', 1) if '/' in image_str else ('', image_str)
        name, tag = image_str.split(':') if ':' in image_str else (image_str,
                                                                   '')
        return registry, name, tag

    def info(self):
        """Returns information about the cluster - number of CPUs and memory in GB"""
        aggregate_cpu, aggregate_mem = 0, 0
        for node in self.list_node():
            aggregate_cpu += node.cpu
            aggregate_mem += node.memory
        return {'cpu': aggregate_cpu, 'memory': aggregate_mem}

    def list_container(self):
        """Returns list of containers (derived from pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            conts_j = entity_j['spec']['containers']
            for cont_j in conts_j:
                cont = Container(cont_j['name'], entity_j['metadata']['name'],
                                 cont_j['image'])
                if cont not in entities:
                    entities.append(cont)
        return entities

    def list_container_group(self):
        """Returns list of container groups (pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            meta, spec = entity_j['metadata'], entity_j['spec']
            entity = ContainerGroup(meta['name'], meta['namespace'],
                                    spec['restartPolicy'], spec['dnsPolicy'])
            entities.append(entity)
        return entities

    def list_service(self):
        """Returns list of services"""
        entities = []
        entities_j = self.api.get('service')[1]['items']
        for entity_j in entities_j:
            meta, spec = entity_j['metadata'], entity_j['spec']
            entity = Service(meta['name'], meta['namespace'],
                             spec['clusterIP'], spec['sessionAffinity'])
            entities.append(entity)
        return entities

    def list_replication_controller(self):
        """Returns list of replication controllers"""
        entities = []
        entities_j = self.api.get('replicationcontroller')[1]['items']
        for entity_j in entities_j:
            meta, spec, status = entity_j['metadata'], entity_j[
                'spec'], entity_j['status']
            entity = ReplicationController(meta['name'], meta['namespace'],
                                           spec['replicas'],
                                           status['replicas'])
            entities.append(entity)
        return entities

    def list_replication_controller_label(self):
        """Returns list of replication controller labels - all objects"""
        entities = []
        entities_j = self.api.get('replicationcontroller')[1]['items']
        for entity_j in entities_j:
            entities.append(entity_j['metadata']['labels'])
        return entities

    def list_pod_label(self):
        """Returns list of pod labels"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            entities.append(entity_j['metadata']['labels'])
        return entities

    def list_service_label(self):
        """Returns list of service labels"""
        entities = []
        entities_j = self.api.get('service')[1]['items']
        for entity_j in entities_j:
            entities.append(entity_j['metadata']['labels'])
        return entities

    def list_node_label(self):
        """Returns list of node labels"""
        entities = []
        entities_j = self.api.get('node')[1]['items']
        for entity_j in entities_j:
            entities.append(entity_j['metadata']['labels'])
        return entities

    def list_replication_controller_selector(self):
        """Returns list of replication controller selectors - rc only"""
        entities = []
        entities_j = self.api.get('replicationcontroller')[1]['items']
        for entity_j in entities_j:
            entities.append(entity_j['spec']['selector'])
        return entities

    def list_image(self):
        """Returns list of images (derived from pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            imgs_j = entity_j['status'].get('containerStatuses', [])
            for img_j in imgs_j:
                _, name, tag = self._parse_image_info(img_j['image'])
                img = Image(name, tag, img_j['imageID'])
                if img not in entities:
                    entities.append(img)
        return entities

    def list_node(self):
        """Returns list of nodes"""
        entities = []
        entities_j = self.api.get('node')[1]['items']
        for entity_j in entities_j:
            meta, status = entity_j['metadata'], entity_j['status']
            cond, cap = status['conditions'][0], status['capacity']
            cpu = int(cap['cpu'])
            memory = int(round(int(cap['memory'][:-2]) *
                               0.00000102400))  # KiB to GB
            entity = Node(meta['name'], cond['status'], cpu, memory)
            entities.append(entity)
        return entities

    def list_image_registry(self):
        """Returns list of image registries (derived from pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            imgs_j = entity_j['status'].get('containerStatuses', [])
            for img_j in imgs_j:
                registry, _, _ = self._parse_image_info(img_j['image'])
                if not registry:
                    continue
                host, port = registry.split(':') if ':' in registry else (
                    registry, '')
                entity = ImageRegistry(host, port)
                if entity not in entities:
                    entities.append(entity)
        return entities

    def list_project(self):
        """Returns list of projects (namespaces in k8s)"""
        entities = []
        entities_j = self.api.get('namespace')[1]['items']
        for entity_j in entities_j:
            meta = entity_j['metadata']
            entity = Project(meta['name'])
            entities.append(entity)
        return entities
Ejemplo n.º 9
0
class Openshift(Kubernetes):
    def __init__(self,
                 hostname,
                 protocol="https",
                 port=8443,
                 k_entry="api/v1",
                 o_entry="oapi/v1",
                 **kwargs):
        self.hostname = hostname
        self.username = kwargs.get('username', '')
        self.password = kwargs.get('password', '')
        self.token = kwargs.get('token', '')
        self.auth = self.token if self.token else (self.username,
                                                   self.password)
        self.k_api = ContainerClient(hostname, self.auth, protocol, port,
                                     k_entry)
        self.o_api = ContainerClient(hostname, self.auth, protocol, port,
                                     o_entry)
        self.api = self.k_api  # default api is the kubernetes one for Kubernetes-class requests

    def list_route(self):
        """Returns list of routes"""
        entities = []
        entities_j = self.o_api.get('route')[1]['items']
        for entity_j in entities_j:
            meta = entity_j['metadata']
            entity = Route(meta['name'], meta['namespace'])
            entities.append(entity)
        return entities

    def list_service(self):
        """Returns list of services"""
        entities = []
        entities_j = self.api.get('service')[1]['items']
        for entity_j in entities_j:
            meta, spec = entity_j['metadata'], entity_j['spec']
            entity = Service(meta['name'], meta['namespace'], spec['portalIP'],
                             spec['sessionAffinity'])
            entities.append(entity)
        return entities

    def list_image_registry(self):
        """Returns list of image registries (image streams)"""
        entities = []
        entities_j = self.o_api.get('imagestream')[1]['items']
        for entity_j in entities_j:
            reg_raw = entity_j['status']['dockerImageRepository'].split('/')[0]
            host, port = reg_raw.split(':') if ':' in reg_raw else (reg_raw,
                                                                    '')
            entity = ImageRegistry(host, port)
            if entity not in entities:
                entities.append(entity)
        return entities

    def list_project(self):
        """Returns list of projects"""
        entities = []
        entities_j = self.o_api.get('project')[1]['items']
        for entity_j in entities_j:
            meta = entity_j['metadata']
            entity = Project(meta['name'])
            entities.append(entity)
        return entities
Ejemplo n.º 10
0
class Kubernetes(ContainerMgmtSystemAPIBase):

    _stats_available = {
        'num_container': lambda self: len(self.list_container()),
        'num_pod': lambda self: len(self.list_container_group()),
        'num_service': lambda self: len(self.list_service()),
        'num_replication_controller':
            lambda self: len(self.list_replication_controller()),
        'num_image': lambda self: len(self.list_image()),
        'num_node': lambda self: len(self.list_node()),
        'num_image_registry': lambda self: len(self.list_image_registry()),
        'num_project': lambda self: len(self.list_project()),
    }

    def __init__(self, hostname, protocol="https", port=6443, entry='api/v1', **kwargs):
        self.hostname = hostname
        self.username = kwargs.get('username', '')
        self.password = kwargs.get('password', '')
        self.token = kwargs.get('token', '')
        self.auth = self.token if self.token else (self.username, self.password)
        self.api = ContainerClient(hostname, self.auth, protocol, port, entry)

    def disconnect(self):
        pass

    def _parse_image_info(self, image_str):
        """Splits full image name into registry, name and tag

        Both registry and tag are optional, name is always present.

        Example:
            localhost:5000/nginx:latest => localhost:5000, nginx, latest
        """
        registry, image_str = image_str.split('/', 1) if '/' in image_str else ('', image_str)
        name, tag = image_str.split(':') if ':' in image_str else (image_str, '')
        return registry, name, tag

    def info(self):
        """Returns information about the cluster - number of CPUs and memory in GB"""
        aggregate_cpu, aggregate_mem = 0, 0
        for node in self.list_node():
            aggregate_cpu += node.cpu
            aggregate_mem += node.memory
        return {'cpu': aggregate_cpu, 'memory': aggregate_mem}

    def list_container(self):
        """Returns list of containers (derived from pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            conts_j = entity_j['spec']['containers']
            for cont_j in conts_j:
                cont = Container(cont_j['name'], entity_j['metadata']['name'], cont_j['image'])
                if cont not in entities:
                    entities.append(cont)
        return entities

    def list_container_group(self):
        """Returns list of container groups (pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            meta, spec = entity_j['metadata'], entity_j['spec']
            entity = ContainerGroup(
                meta['name'], meta['namespace'], spec['restartPolicy'], spec['dnsPolicy'])
            entities.append(entity)
        return entities

    def list_service(self):
        """Returns list of services"""
        entities = []
        entities_j = self.api.get('service')[1]['items']
        for entity_j in entities_j:
            meta, spec = entity_j['metadata'], entity_j['spec']
            entity = Service(
                meta['name'], meta['namespace'], spec['clusterIP'], spec['sessionAffinity'])
            entities.append(entity)
        return entities

    def list_replication_controller(self):
        """Returns list of replication controllers"""
        entities = []
        entities_j = self.api.get('replicationcontroller')[1]['items']
        for entity_j in entities_j:
            meta, spec, status = entity_j['metadata'], entity_j['spec'], entity_j['status']
            entity = ReplicationController(
                meta['name'], meta['namespace'], spec['replicas'], status['replicas'])
            entities.append(entity)
        return entities

    def list_image(self):
        """Returns list of images (derived from pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            imgs_j = entity_j['status'].get('containerStatuses', [])
            for img_j in imgs_j:
                _, name, tag = self._parse_image_info(img_j['image'])
                img = Image(name, tag, img_j['imageID'])
                if img not in entities:
                    entities.append(img)
        return entities

    def list_node(self):
        """Returns list of nodes"""
        entities = []
        entities_j = self.api.get('node')[1]['items']
        for entity_j in entities_j:
            meta, status = entity_j['metadata'], entity_j['status']
            cond, cap = status['conditions'][0], status['capacity']
            cpu = int(cap['cpu'])
            memory = int(round(int(cap['memory'][:-2]) * 0.00000102400))  # KiB to GB
            entity = Node(meta['name'], cond['status'], cpu, memory)
            entities.append(entity)
        return entities

    def list_image_registry(self):
        """Returns list of image registries (derived from pods)"""
        entities = []
        entities_j = self.api.get('pod')[1]['items']
        for entity_j in entities_j:
            imgs_j = entity_j['status'].get('containerStatuses', [])
            for img_j in imgs_j:
                registry, _, _ = self._parse_image_info(img_j['image'])
                if not registry:
                    continue
                host, port = registry.split(':') if ':' in registry else (registry, '')
                entity = ImageRegistry(host, port)
                if entity not in entities:
                    entities.append(entity)
        return entities

    def list_project(self):
        """Returns list of projects (namespaces in k8s)"""
        entities = []
        entities_j = self.api.get('namespace')[1]['items']
        for entity_j in entities_j:
            meta = entity_j['metadata']
            entity = Project(meta['name'])
            entities.append(entity)
        return entities
Ejemplo n.º 11
0
class Hawkular(MgmtSystemAPIBase):
    """Hawkular management system

    Hawkular REST API method calls.
    Will be used by cfme_tests project to verify Hawkular content shown in CFME UI

    Args:
        hostname: The Hawkular hostname.
        protocol: Hawkular REST API protocol. Default value: 'http'
        port: Hawkular REST API port on provided host. Default value: '8080'.
        entry: Hawkular REST API entry point URI. Default value: 'hawkular/inventory'
        username: The username to connect with.
        password: The password to connect with.

    """

    _stats_available = {
        'num_server': lambda self: len(self.list_server()),
        'num_domain': lambda self: len(self.list_domain()),
        'num_deployment': lambda self: len(self.list_server_deployment()),
        'num_datasource': lambda self: len(self.list_server_datasource()),
    }

    def __init__(self, hostname, protocol="http", port=8080, **kwargs):
        super(Hawkular, self).__init__(kwargs)
        self.hostname = hostname
        self.username = kwargs.get('username', '')
        self.password = kwargs.get('password', '')
        self.tenant_id = kwargs.get('tenant_id', 'hawkular')
        self.auth = self.username, self.password
        self.inv_api = ContainerClient(hostname, self.auth, protocol, port,
                                       "hawkular/inventory")
        self.alerts_api = ContainerClient(hostname, self.auth, protocol, port,
                                          "hawkular/alerts")
        self.metrics_api = ContainerClient(hostname, self.auth, protocol, port,
                                           "hawkular/metrics")

    def _check_inv_version(self, version):
        return version in self._get_inv_json(
            'status')['Implementation-Version']

    def info(self):
        raise NotImplementedError('info not implemented.')

    def clone_vm(self, source_name, vm_name):
        raise NotImplementedError('clone_vm not implemented.')

    def create_vm(self, vm_name):
        raise NotImplementedError('create_vm not implemented.')

    def current_ip_address(self, vm_name):
        raise NotImplementedError('current_ip_address not implemented.')

    def delete_vm(self, vm_name):
        raise NotImplementedError('delete_vm not implemented.')

    def deploy_template(self, template, *args, **kwargs):
        raise NotImplementedError('deploy_template not implemented.')

    def disconnect(self):
        pass

    def does_vm_exist(self, name):
        raise NotImplementedError('does_vm_exist not implemented.')

    def get_ip_address(self, vm_name):
        raise NotImplementedError('get_ip_address not implemented.')

    def is_vm_running(self, vm_name):
        raise NotImplementedError('is_vm_running not implemented.')

    def is_vm_stopped(self, vm_name):
        raise NotImplementedError('is_vm_stopped not implemented.')

    def is_vm_suspended(self, vm_name):
        raise NotImplementedError('is_vm_suspended not implemented.')

    def list_flavor(self):
        raise NotImplementedError('list_flavor not implemented.')

    def list_template(self):
        raise NotImplementedError('list_template not implemented.')

    def list_vm(self, **kwargs):
        raise NotImplementedError('list_vm not implemented.')

    def remove_host_from_cluster(self, hostname):
        raise NotImplementedError('remove_host_from_cluster not implemented.')

    def restart_vm(self, vm_name):
        raise NotImplementedError('restart_vm not implemented.')

    def start_vm(self, vm_name):
        raise NotImplementedError('start_vm not implemented.')

    def stop_vm(self, vm_name):
        raise NotImplementedError('stop_vm not implemented.')

    def suspend_vm(self, vm_name):
        raise NotImplementedError('restart_vm not implemented.')

    def vm_status(self, vm_name):
        raise NotImplementedError('vm_status not implemented.')

    def wait_vm_running(self, vm_name, num_sec):
        raise NotImplementedError('wait_vm_running not implemented.')

    def wait_vm_stopped(self, vm_name, num_sec):
        raise NotImplementedError('wait_vm_stopped not implemented.')

    def wait_vm_suspended(self, vm_name, num_sec):
        raise NotImplementedError('wait_vm_suspended not implemented.')

    def list_server_deployment(self, feed_id=None):
        """Returns list of server deployments.

        Args:
            feed_id: Feed id of the resource (optional)
        """
        resources = self.list_resource(feed_id=feed_id,
                                       resource_type_id='Deployment')
        deployments = []
        if resources:
            for resource in resources:
                deployments.append(
                    Deployment(resource.id, resource.name, resource.path))
        return deployments

    def list_server(self, feed_id=None):
        """Returns list of middleware servers.

          Args:
            feed_id: Feed id of the resource (optional)
        """
        resources = self.list_resource(feed_id=feed_id,
                                       resource_type_id='WildFly Server')
        resources.extend(
            self.list_resource(feed_id=feed_id,
                               resource_type_id='Domain WildFly Server'))
        servers = []
        if resources:
            for resource in resources:
                resource_data = self.get_config_data(
                    feed_id=resource.path.feed_id,
                    resource_id=self._get_resource_id(
                        resource.path.resource_id))
                server_data = resource_data.value
                servers.append(
                    Server(resource.id, resource.name, resource.path,
                           server_data))
        return servers

    def list_domain(self, feed_id=None):
        """Returns list of middleware domains.

          Args:
            feed_id: Feed id of the resource (optional)
        """
        resources = self.list_resource(feed_id=feed_id,
                                       resource_type_id='Host Controller')
        domains = []
        if resources:
            for resource in resources:
                resource_data = self.get_config_data(
                    feed_id=resource.path.feed_id, resource_id=resource.id)
                domain_data = resource_data.value
                domains.append(
                    Domain(resource.id, resource.name, resource.path,
                           domain_data))
        return domains

    def list_server_group(self, feed_id):
        """Returns list of middleware domain's server groups.

          Args:
            feed_id: Feed id of the resource (optional)
        """
        resources = self.list_resource(feed_id=feed_id,
                                       resource_type_id='Domain Server Group')
        server_groups = []
        if resources:
            for resource in resources:
                resource_data = self.get_config_data(
                    feed_id=resource.path.feed_id,
                    resource_id=self._get_resource_id(
                        resource.path.resource_id))
                server_group_data = resource_data.value
                server_groups.append(
                    ServerGroup(resource.id, resource.name, resource.path,
                                server_group_data))
        return server_groups

    def list_resource(self, resource_type_id, feed_id=None):
        """Returns list of resources.

          Args:
            feed_id: Feed id of the resource (optional)
            resource_type_id: Resource type id
        """
        if not feed_id:
            resources = []
            for feed in self.list_feed():
                resources.extend(
                    self._list_resource(feed_id=feed.path.feed_id,
                                        resource_type_id=resource_type_id))
            return resources
        else:
            return self._list_resource(feed_id=feed_id,
                                       resource_type_id=resource_type_id)

    def list_child_resource(self, feed_id, resource_id, recursive=False):
        """Returns list of resources.

          Args:
            feed_id: Feed id of the resource
            resource_id: Resource id
            recursive: should be True when you want to get recursively, Default False
        """
        if not feed_id or not resource_id:
            raise KeyError(
                "'feed_id' and 'resource_id' are a mandatory field!")
        resources = []
        if recursive:
            entities_j = self._get_inv_json(
                'traversal/f;{}/r;{}/recursive;over=isParentOf;type=r'.format(
                    feed_id, resource_id))
        else:
            entities_j = self._get_inv_json(
                'traversal/f;{}/r;{}/type=r'.format(feed_id, resource_id))
        if entities_j:
            for entity_j in entities_j:
                resources.append(
                    Resource(entity_j['id'], entity_j['name'],
                             CanonicalPath(entity_j['path'])))
        return resources

    def _list_resource(self, feed_id, resource_type_id=None):
        """Returns list of resources.

         Args:
            feed_id: Feed id of the resource
            resource_type_id: Resource type id (optional)
        """
        if not feed_id:
            raise KeyError("'feed_id' is a mandatory field!")
        entities = []
        if resource_type_id:
            entities_j = self._get_inv_json(
                'traversal/f;{}/rt;{}/rl;defines/type=r'.format(
                    feed_id, resource_type_id))
        else:
            entities_j = self._get_inv_json(
                'traversal/f;{}/type=r'.format(feed_id))
        if entities_j:
            for entity_j in entities_j:
                entities.append(
                    Resource(entity_j['id'], entity_j['name'],
                             CanonicalPath(entity_j['path'])))
        return entities

    def get_config_data(self, feed_id, resource_id):
        """Returns the data/configuration information about resource by provided

        Args:
            feed_id: Feed id of the resource
            resource_id: Resource id
         """
        if not feed_id or not resource_id:
            raise KeyError("'feed_id' and 'resource_id' are mandatory field!")
        entity_j = self._get_inv_json(
            'entity/f;{}/r;{}/d;configuration'.format(
                feed_id, self._get_resource_id(resource_id)))
        if entity_j:
            return ResourceData(entity_j['name'],
                                CanonicalPath(entity_j['path']),
                                entity_j['value'])
        return None

    def list_feed(self):
        """Returns list of feeds"""
        entities = []
        entities_j = self._get_inv_json('traversal/type=f')
        if entities_j:
            for entity_j in entities_j:
                entities.append(
                    Feed(entity_j['id'], CanonicalPath(entity_j['path'])))
        return entities

    def list_resource_type(self, feed_id):
        """Returns list of resource types.

         Args:
            feed_id: Feed id of the resource type
        """
        if not feed_id:
            raise KeyError("'feed_id' is a mandatory field!")
        entities = []
        entities_j = self._get_inv_json(
            'traversal/f;{}/type=rt'.format(feed_id))
        if entities_j:
            for entity_j in entities_j:
                entities.append(
                    ResourceType(entity_j['id'], entity_j['name'],
                                 entity_j['path']))
        return entities

    def list_operation_definition(self, feed_id, resource_type_id):
        """Lists operations definitions

        Args:
            feed_id: Feed id of the operation
            resource_type_id: Resource type id of the operation
        """
        if feed_id is None or resource_type_id is None:
            raise KeyError(
                "'feed_id' and 'resource_type_id' are mandatory fields!")
        res_j = self._get_inv_json('traversal/f;{}/rt;{}/type=ot'.format(
            feed_id, resource_type_id))
        operations = []
        if res_j:
            for res in res_j:
                operations.append(
                    OperationType(res['id'], res['name'],
                                  CanonicalPath(res['path'])))
        return operations

    def list_server_datasource(self, feed_id=None):
        """Returns list of datasources.

         Args:
             feed_id: Feed id of the datasource (optional)
        """
        resources = self.list_resource(feed_id=feed_id,
                                       resource_type_id='Datasource')
        datasources = []
        if resources:
            for resource in resources:
                datasources.append(
                    Datasource(resource.id, resource.name, resource.path))
        return datasources

    def edit_config_data(self, resource_data, **kwargs):
        """Edits the data.value information for resource by provided

        Args:
            resource_data: Resource data
        """
        if not isinstance(resource_data,
                          ResourceData) or not resource_data.value:
            raise KeyError(
                "'resource_data' should be ResourceData with 'value' attribute"
            )
        if not kwargs or 'feed_id' not in kwargs or 'resource_id' not in kwargs:
            raise KeyError("'feed_id' and 'resource_id' are mandatory field!")
        r = self._put_inv_status(
            'entity/f;{}/r;{}/d;configuration'.format(kwargs['feed_id'],
                                                      kwargs['resource_id']),
            {"value": resource_data.value})
        return r

    def create_resource(self, resource, resource_data, resource_type,
                        **kwargs):
        """Creates new resource and creates it's data by provided
        Args:
            resource: resource
            kwargs: feed_id, resource_id and required fields
            resource_data: Resource data
            resource_type: Resource type
        """
        if not isinstance(resource, Resource):
            raise KeyError("'resource' should be an instance of Resource")
        if not isinstance(resource_data,
                          ResourceData) or not resource_data.value:
            raise KeyError(
                "'resource_data' should be ResourceData with 'value' attribute"
            )
        if not isinstance(resource_type, ResourceType):
            raise KeyError(
                "'resource_type' should be an instance of ResourceType")
        if not kwargs or 'feed_id' not in kwargs:
            raise KeyError('Variable "feed_id" id mandatory field!')

        resource_id = urlquote(resource.id, safe='')
        r = self._post_inv_status(
            'entity/f;{}/resource'.format(kwargs['feed_id']),
            data={
                "name":
                resource.name,
                "id":
                resource.id,
                "resourceTypePath":
                "rt;{}".format(resource_type.path.resource_type_id)
            })
        if r:
            r = self._post_inv_status('entity/f;{}/r;{}/data'.format(
                kwargs['feed_id'], resource_id),
                                      data={
                                          'role': 'configuration',
                                          "value": resource_data.value
                                      })
        else:
            # if resource or it's data was not created correctly, delete resource
            self._delete_inv_status('entity/f;{}/r;{}'.format(
                kwargs['feed_id'], resource_id))
        return r

    def delete_resource(self, feed_id, resource_id):
        """Removed a resource.
        Args:
            feed_id: Feed id of the data source
            resource_id: Resource id of the datasource
        """
        if not feed_id or not resource_id:
            raise KeyError("'feed_id' and 'resource_id' are mandatory fields!")
        r = self._delete_inv_status('entity/f;{}/r;{}'.format(
            feed_id, resource_id))
        return r

    def list_event(self, start_time=0, end_time=sys.maxsize):
        """Returns the list of events.
        Filtered by provided start time and end time. Or lists all events if no argument provided.
        This information is wrapped into Event.

         Args:
             start_time: Start time as timestamp
             end_time: End time as timestamp
         """
        entities = []
        entities_j = self._get_alerts_json(
            'events?startTime={}&endTime={}'.format(start_time, end_time))
        if entities_j:
            for entity_j in entities_j:
                entity = Event(entity_j['id'], entity_j['eventType'],
                               entity_j['ctime'], entity_j['dataSource'],
                               entity_j['dataId'], entity_j['category'],
                               entity_j['text'])
                entities.append(entity)
        return entities

    def _get_inv_json(self, path):
        return self.inv_api.get_json(
            path, headers={"Hawkular-Tenant": self.tenant_id})

    def _post_inv_status(self, path, data):
        return self.inv_api.post_status(path,
                                        data,
                                        headers={
                                            "Hawkular-Tenant": self.tenant_id,
                                            "Content-Type": "application/json"
                                        })

    def _put_inv_status(self, path, data):
        return self.inv_api.put_status(path,
                                       data,
                                       headers={
                                           "Hawkular-Tenant": self.tenant_id,
                                           "Content-Type": "application/json"
                                       })

    def _delete_inv_status(self, path):
        return self.inv_api.delete_status(
            path, headers={"Hawkular-Tenant": self.tenant_id})

    def _get_alerts_json(self, path):
        return self.alerts_api.get_json(
            path, headers={"Hawkular-Tenant": self.tenant_id})

    def _get_metrics_json(self, path, params=None):
        return self.metrics_api.get_json(
            path, headers={"Hawkular-Tenant": self.tenant_id}, params=params)

    def _get_resource_id(self, resource_id):
        if isinstance(resource_id, list):
            return "{}".format('/r;'.join(resource_id))
        else:
            return resource_id

    def status_alerts(self):
        """returns status of alerts service"""
        return self._get_alerts_json(path='status')

    def status_inventory(self):
        """Returns status of inventory service"""
        return self._get_inv_json(path='status')

    def status_metrics(self):
        """Returns status of metrics service"""
        return self._get_metrics_json(path='status')

    def status(self):
        """Returns status of alerts, inventory and metrics services"""
        return {
            'alerts': self.status_alerts(),
            'inventory': self.status_inventory(),
            'metrics': self.status_metric()
        }

    def list_metric_availability_feed(self, feed_id, **kwargs):
        """Returns list of DataPoint of a feed
        Args:
            feed_id: Feed id of the metric resource
            kwargs: Refer ``list_metric_availability``
        """
        metric_id = "hawkular-feed-availability-{}".format(feed_id)
        return self.list_metric_availability(metric_id=metric_id, **kwargs)

    def list_metric_availability_server(self, feed_id, server_id, **kwargs):
        """Returns list of `DataPoint` of a server
        Args:
            feed_id: Feed id of the server
            server_id: Server id
            kwargs: Refer ``list_metric_availability``
        """
        metric_id = "AI~R~[{}/{}~~]~AT~Server Availability~Server Availability" \
            .format(feed_id, server_id)
        return self.list_metric_availability(metric_id=metric_id, **kwargs)

    def list_metric_availability_deployment(self, feed_id, server_id,
                                            resource_id, **kwargs):
        """Returns list of `DataPoint` of a deployment
        Args:
            feed_id: Feed id of the deployment
            server_id: Server id of the deployment
            resource_id: deployment id
            kwargs: Refer ``list_metric_availability``
        """
        metric_id = "AI~R~[{}/{}~/deployment={}]~AT~Deployment Status~Deployment Status" \
            .format(feed_id, server_id, resource_id)
        return self.list_metric_availability(metric_id=metric_id, **kwargs)

    def list_metric_availability(self, metric_id, **kwargs):
        """Returns list of `DataPoint` of a metric
        Args:
            metric_id: Metric id
            kwargs: refer optional query params and query type

        Optional query params:
            start: timestamp, Defaults to now: 8 hours
            end: timestamp, Defaults to now
            buckets: Total number of buckets
            bucketDuration: Bucket duration
            distinct: Set to true to return only distinct, contiguous values
            limit: Limit the number of data points returned
            order: Data point sort order, based on timestamp [values: ASC, DESC]

        Query type:
            raw: set True when you want to get raw data, Default False which returns stats
        """
        prefix_id = "availability/{}".format(urlquote(metric_id, safe=''))
        return self._list_metric_data(prefix_id=prefix_id, **kwargs)

    def list_metric_gauge_datasource(self, feed_id, server_id, resource_id,
                                     metric_enum, **kwargs):
        """Returns list of NumericBucketPoint of datasource metric
            Args:
                feed_id: feed id of the datasource
                server_id: server id of the datasource
                resource_id: resource id, here which is datasource id
                metric_enum: Any one of *DS_* Enum value from ``MetricEnumGauge``
                kwargs: Refer ``list_metric_gauge``
            """
        if not isinstance(metric_enum, MetricEnumGauge):
            raise KeyError(
                "'metric_enum' should be a type of 'MetricEnumGauge' Enum class"
            )
        return self._list_metric_gauge_datasource(
            feed_id=feed_id,
            server_id=server_id,
            resource_id=resource_id,
            metric_type=metric_enum.metric_type,
            metric_sub_type=metric_enum.sub_type,
            **kwargs)

    def _list_metric_gauge_datasource(self, feed_id, server_id, resource_id,
                                      metric_type, metric_sub_type, **kwargs):
        metric_id = "MI~R~[{}/{}~/subsystem=datasources/data-source={}]~MT~{}~{}" \
            .format(feed_id, server_id, resource_id, metric_type, metric_sub_type)
        return self.list_metric_gauge(metric_id=metric_id, **kwargs)

    def list_metric_gauge_server(self, feed_id, server_id, metric_enum,
                                 **kwargs):
        """Returns list of `NumericBucketPoint` of server metric
            Args:
                feed_id: feed id of the server
                server_id: server id
                metric_enum: Any one of *SVR_* ``Enum`` value from ``MetricEnumGauge``
                kwargs: Refer ``list_metric_gauge``
            """
        if not isinstance(metric_enum, MetricEnumGauge):
            raise KeyError(
                "'metric_enum' should be a type of 'MetricEnumGauge' Enum class"
            )
        return self._list_metric_gauge_server(
            feed_id=feed_id,
            server_id=server_id,
            metric_type=metric_enum.metric_type,
            metric_sub_type=metric_enum.sub_type,
            **kwargs)

    def _list_metric_gauge_server(self, feed_id, server_id, metric_type,
                                  metric_sub_type, **kwargs):
        metric_id = "MI~R~[{}/{}~~]~MT~{}~{}".format(feed_id, server_id,
                                                     metric_type,
                                                     metric_sub_type)
        return self.list_metric_gauge(metric_id=metric_id, **kwargs)

    def list_metric_gauge(self, metric_id, **kwargs):
        """Returns list of `NumericBucketPoint` of a metric
            Args:
                metric_id: Metric id
                kwargs: Refer optional query params and query type

            Optional query params:
                start: timestamp, Defaults to now: 8 hours
                end: timestamp, Defaults to now
                buckets: Total number of buckets
                bucketDuration: Bucket duration
                distinct: Set to true to return only distinct, contiguous values
                limit: Limit the number of data points returned
                order: Data point sort order, based on timestamp [values: ASC, DESC]

            Query type:
                raw: set True when you want to get raw data, Default False which returns stats
                rate: set True when you want rate data default False
                stats: return stats data default True
            """
        prefix_id = "gauges/{}".format(urlquote(metric_id, safe=''))
        return self._list_metric_data(prefix_id=prefix_id, **kwargs)

    def list_metric_counter_server(self, feed_id, server_id, metric_enum,
                                   **kwargs):
        """Returns list of `NumericBucketPoint` of server metric
            Args:
                feed_id: feed id of the server
                server_id: server id
                metric_enum: Any one of *SVR_* ``Enum`` value from ``MetricEnumCounter``
                kwargs: Refer ``list_metric_counter``
            """
        if not isinstance(metric_enum, MetricEnumCounter):
            raise KeyError(
                "'metric_enum' should be a type of 'MetricEnumCounter' Enum class"
            )
        return self._list_metric_counter_server(
            feed_id=feed_id,
            server_id=server_id,
            metric_type=metric_enum.metric_type,
            metric_sub_type=metric_enum.sub_type,
            **kwargs)

    def _list_metric_counter_server(self, feed_id, server_id, metric_type,
                                    metric_sub_type, **kwargs):
        if MetricEnumCounter.SVR_TXN_NUMBER_OF_TRANSACTIONS.metric_type == metric_type:
            metric_id = "MI~R~[{}/{}~/subsystem=transactions]~MT~{}~{}"\
                .format(feed_id, server_id, metric_type, metric_sub_type)
        else:
            metric_id = "MI~R~[{}/{}~~]~MT~{}~{}".format(
                feed_id, server_id, metric_type, metric_sub_type)
        return self.list_metric_counter(metric_id=metric_id, **kwargs)

    def list_metric_counter_deployment(self, feed_id, server_id, resource_id,
                                       metric_enum, **kwargs):
        """Returns list of `NumericBucketPoint` of server metric
            Args:
                feed_id: feed id of the deployment
                server_id: server id of the deployment
                resource_id: resource id, that's deployment id
                metric_enum: Any one of *DEP_* ``Enum`` value from ``MetricEnumCounter``
                kwargs: Refer ``list_metric_counter``
            """
        if not isinstance(metric_enum, MetricEnumCounter):
            raise KeyError(
                "'metric_enum' should be a type of 'MetricEnumCounter' Enum class"
            )
        return self._list_metric_counter_deployment(
            feed_id=feed_id,
            server_id=server_id,
            resource_id=resource_id,
            metric_type=metric_enum.metric_type,
            metric_sub_type=metric_enum.sub_type,
            **kwargs)

    def _list_metric_counter_deployment(self, feed_id, server_id, resource_id,
                                        metric_type, metric_sub_type,
                                        **kwargs):
        metric_id = "MI~R~[{}/{}~/deployment={}]~MT~{}~{}"\
            .format(feed_id, server_id, resource_id, metric_type, metric_sub_type)
        return self.list_metric_counter(metric_id=metric_id, **kwargs)

    def list_metric_counter(self, metric_id, **kwargs):
        """Returns list of `NumericBucketPoint` of a metric
            Args:
                metric_id: metric id
                kwargs: Refer optional query params and query type

            Optional query params:
                start: timestamp, Defaults to now: 8 hours
                end: timestamp, Defaults to now
                buckets: Total number of buckets
                bucketDuration: Bucket duration
                distinct: Set to true to return only distinct, contiguous values
                limit: Limit the number of data points returned
                order: Data point sort order, based on timestamp [values: ASC, DESC]

            Query type:
                raw: set True when you want to get raw data, Default False which returns stats
                rate: set True when you want rate data default False
                stats: return stats data default True
            """
        prefix_id = "counters/{}".format(urlquote(metric_id, safe=''))
        return self._list_metric_data(prefix_id=prefix_id, **kwargs)

    def list_metric_availability_definition(self):
        """Lists all availability type metric definitions"""
        return self._get_metrics_json(path='availability')

    def list_metric_gauge_definition(self):
        """Lists all gauge type metric definitions"""
        return self._get_metrics_json(path='gauges')

    def list_metric_counter_definition(self):
        """Lists all counter type metric definitions"""
        return self._get_metrics_json(path='counters')

    def list_metric_definition(self):
        """Lists all metric definitions"""
        return self._get_metrics_json(path='metrics')

    def _list_metric_data(self, prefix_id, **kwargs):
        params = {
            'start': kwargs.get('start', None),
            'end': kwargs.get('end', None),
            'bucketDuration': kwargs.get('bucketDuration', None),
            'buckets': kwargs.get('buckets', None),
            'percentiles': kwargs.get('percentiles', None),
            'limit': kwargs.get('limit', None),
            'order': kwargs.get('order', None),
        }
        raw = kwargs.get('raw', False)
        rate = kwargs.get('rate', False)
        if not raw and params['bucketDuration'] is None and params[
                'buckets'] is None:
            raise KeyError(
                "Either the 'buckets' or 'bucketDuration' parameter must be used"
            )
        if rate:
            return self._get_metrics_json(
                path='{}/rate/stats'.format(prefix_id), params=params)
        elif raw:
            return self._get_metrics_json(path='{}/raw'.format(prefix_id),
                                          params=params)
        else:
            return self._get_metrics_json(path='{}/stats'.format(prefix_id),
                                          params=params)