Example #1
0
    def _resource_completion(self, short_mode=True):
        results = []
        headers = ('NAME', 'SERVER', 'CLUSTER', 'CONTEXT')
        yaml = YAML()
        results.append(headers)
        if os.path.exists(settings.OMC_KUBE_CONFIG_DIR):
            resources = os.listdir(settings.OMC_KUBE_CONFIG_DIR)
            for one_resource in resources:
                try:
                    with open(
                            os.path.join(settings.OMC_KUBE_CONFIG_DIR,
                                         one_resource, 'config')) as f:
                        content = yaml.load(f)
                        one_item = (one_resource,
                                    ObjectUtils.get_node(
                                        content, "clusters[0].cluster.server"),
                                    ObjectUtils.get_node(
                                        content, "clusters[0].name"),
                                    ObjectUtils.get_node(
                                        content, "current-context"))
                        results.append(one_item)
                except Exception as e:
                    logger.error(e, exc_info=True)

        return CompletionContent(Formatter.format_completions(results))
Example #2
0
    def _save(self):
        'save configuration in file cache to be restored'
        resource_name = self._get_one_resource_value()
        namespace = self.client.get_namespace(
            self._get_kube_api_resource_type(), resource_name)
        kube_instance = self._get_one_resource_value("kube")
        if not kube_instance:
            kube_instance = 'local'
        cache_folder = os.path.join(settings.OMC_KUBE_CACHE_DIR, kube_instance,
                                    namespace, self._get_kube_resource_type())

        result = self._read_namespaced_resource(resource_name,
                                                namespace,
                                                _preload_content=False)
        stream = StringIO()
        the_result = json.loads(result.data.decode('UTF-8'))
        ObjectUtils.delete_node(the_result, 'metadata.creationTimestamp')
        ObjectUtils.delete_node(the_result, 'metadata.resourceVersion')
        yaml = YAML()
        yaml.dump(the_result, stream)
        content = stream.getvalue()

        make_directory(cache_folder)
        with open(os.path.join(cache_folder, resource_name + '.yaml'),
                  'w') as f:
            f.write(content)
Example #3
0
    def event(self):
        'show event on the resource'
        # https://kubernetes.docker.internal:6443/api/v1/namespaces/default/events?fieldSelector=
        # involvedObject.uid=4bb31f4d-99f1-4acc-a024-8e2484573733,
        # involvedObject.name=itom-xruntime-rabbitmq-6464654786-vnjxz,
        # involvedObject.namespace=default

        resource = self._get_one_resource_value()
        namespace = self.client.get_namespace(
            self._get_kube_api_resource_type(), resource)
        result = self._read_namespaced_resource(resource, namespace)

        uid = ObjectUtils.get_node(result, 'metadata.uid')
        name = ObjectUtils.get_node(result, 'metadata.name')

        the_selector = {
            "involvedObject.uid": uid,
            "involvedObject.namespace": namespace,
            "involvedObject.name": name,
        }

        console.log(
            self.client.list_namespaced_event(
                namespace,
                field_selector=self._build_field_selector(the_selector)))
Example #4
0
 def _get_config_key_completion(self):
     resource = self._get_one_resource_value()
     namespace = self.client.get_namespace(
         self._get_kube_api_resource_type(), resource)
     result = self._read_namespaced_resource(resource, namespace)
     prompts = []
     ObjectUtils.get_nodes(result.to_dict(), prompts)
     return CompletionContent(self._get_completion(prompts))
Example #5
0
    def _resource_completion(self, short_mode=True):
        ret = self._list_resource_for_all_namespaces(
            timeout_seconds=settings.COMPETION_TIMEOUT)
        results = Formatter.format_completions([(
            ObjectUtils.get_node(one, 'metadata.name'),
            ObjectUtils.get_node(one, 'metadata.namespace'),
            self._get_ready_status(one),
            time_util.calculate_age(
                time_util.fromisotime(
                    ObjectUtils.get_node(one, 'metadata.creationTimestamp'))),
        ) for one in ret.get('items')])

        return CompletionContent(results)
Example #6
0
    def _resource_completion(self, short_mode=True):
        results = []

        kube_resource_type = self._get_kube_resource_type()
        completion_file_name = pkg_resources.resource_filename(
            'omc_kube.assets',
            '_%(kube_resource_type)s_completion.json' % locals())
        prompts = []
        # get_all_dict_Keys(result.to_dict(), prompts)
        with open(completion_file_name) as f:
            result = json.load(f)
            ObjectUtils.get_nodes(result, prompts)
            results.extend(self._get_completion(prompts))

        return CompletionContent(results)
Example #7
0
 def _get_cert_dir(self, config_file):
     import yaml
     with open(config_file) as f:
         result = yaml.load(f, yaml.FullLoader)
         path = (ObjectUtils.get_node(
             result, 'clusters[0].cluster.certificate-authority'))
         return os.path.dirname(path)
Example #8
0
    def get(self):
        'get resource by configuration key'
        parent_resource = self._get_one_resource_value(
            self._get_kube_resource_type())
        namespace = self.client.get_namespace(
            self._get_kube_api_resource_type(), parent_resource)
        result = self._read_namespaced_resource(parent_resource, namespace)

        # config resource is the item
        resource = self._get_one_resource_value()

        if not resource:
            console.log(ObjectUtils.format(result))
        else:
            console.log(
                ObjectUtils.format(ObjectUtils.get_node(result, resource)))
Example #9
0
    def delete(self):
        'delete node by configuration key'
        # todo@rain: to support delete entired resource and completion cache
        if 'completion' in self._get_params():
            resource = self._get_one_resource_value()
            namespace = self.client.get_namespace(
                self._get_kube_api_resource_type(), resource)
            result = self._read_namespaced_resource(resource, namespace)
            prompts = []
            ObjectUtils.get_nodes(result.to_dict(), prompts)
            self._print_completion(prompts)
            return

        config_key = self._get_one_resource_value()
        parent_resource = self._get_one_resource_value(
            self._get_kube_resource_type())
        namespace = self.client.get_namespace(
            self._get_kube_api_resource_type(), parent_resource)
        the_result = self._read_namespaced_resource(parent_resource,
                                                    namespace,
                                                    _preload_content=False)
        result = json.loads(the_result.data.decode('UTF-8'))
        params = self._get_action_params()
        config_value = params[0] if len(params) > 0 else None
        # orig_value = ObjectUtils.get_node(result, config_key)
        # # convert type
        # config_value = type(orig_value)(config_value)
        # set_obj_value(result, config_key, config_value)

        # todo: use apply instead once apply provided
        patch_func = getattr(
            self.client,
            'patch_namespaced_' + self._get_kube_api_resource_type())
        # patch_object = utils.build_object(config_key, config_value)
        patch_object = StrategicMergePatch.get_instance(
        ).gen_strategic_merge_patch(result, config_key.split('.'),
                                    config_value, 'delete', [])
        new_result = patch_func(parent_resource, namespace, patch_object)
        console.log(new_result)
Example #10
0
    def set(self):
        'update restore by configuration key'
        # https://github.com/kubernetes/kubernetes/blob/cea1d4e20b4a7886d8ff65f34c6d4f95efcb4742/staging/src/k8s.io/apimachinery/pkg/util/strategicpatch/patch.go
        # implement Strategic merge patch myself
        # https://stackoverflow.com/questions/36307950/kubernetes-api-call-equivalent-to-kubectl-apply
        if 'completion' in self._get_params():
            resource = self._get_one_resource_value()
            namespace = self.client.get_namespace(
                self._get_kube_api_resource_type(), resource)
            result = self._read_namespaced_resource(resource, namespace)
            prompts = []
            ObjectUtils.get_nodes(result.to_dict(), prompts)
            self._print_completion(prompts)
            return

        config_key = self._get_one_resource_value()
        parent_resource = self._get_one_resource_value(
            self._get_kube_resource_type())
        namespace = self.client.get_namespace(
            self._get_kube_api_resource_type(), parent_resource)
        result = self._read_namespaced_resource(parent_resource, namespace)
        params = self._get_action_params()
        config_value = params[0]
        orig_value = ObjectUtils.get_node(result, config_key)
        # convert type
        config_value = type(orig_value)(config_value)
        ObjectUtils.set_node(result, config_key, config_value)

        # todo: use apply instead once apply provided
        patch_func = getattr(
            self.client,
            'patch_namespaced_' + self._get_kube_api_resource_type())
        # patch_object = utils.build_object(config_key, config_value)
        patch_object = StrategicMergePatch.get_instance(
        ).gen_strategic_merge_patch(result, config_key.split('.'),
                                    config_value, 'set', [])
        new_result = patch_func(parent_resource, namespace, patch_object)
        console.log(new_result)
Example #11
0
    def _resource_completion(self, short_mode=True):
        results = []

        pod_name = self._get_one_resource_value('pod')
        namespace = self.client.get_namespace('pod', pod_name)
        result = self.client.read_namespaced_pod(pod_name, namespace)
        # for one_container in result.spec.containers:
        results.extend(
            self._get_completion(
                [(one.get('name'), one.get('image'))
                 for one in ObjectUtils.get_node(result, 'spec.containers')],
                False))

        return CompletionContent(results)
Example #12
0
 def _get_ready_status(self, one):
     replicas = 0 if ObjectUtils.get_node(
         one, 'status.replicas') is None else ObjectUtils.get_node(
             one, 'status.replicas')
     unavailable_replicas = 0 if ObjectUtils.get_node(
         one,
         'status.unavailableReplicas') is None else ObjectUtils.get_node(
             one, 'status.unavailableReplicas')
     updated_replicas = 0 if ObjectUtils.get_node(
         one, 'status.updatedReplicas') is None else ObjectUtils.get_node(
             one, 'status.updatedReplicas')
     available_replicas = replicas - unavailable_replicas
     return str(available_replicas) + '/' + str(replicas)
Example #13
0
    def _before_sub_resource(self):
        try:
            if self._have_resource_value():
                resource_value = self._get_one_resource_value()
                client = KubernetesClient(
                    os.path.join(settings.OMC_KUBE_CONFIG_DIR, resource_value,
                                 'config'))
            else:
                client = KubernetesClient()

            self.context['common'] = {'client': client}
        except Exception as e:
            # some action no need to create load config, get config action e.g.
            raise Exception('invalid kubenetes config')


if __name__ == '__main__':
    client = KubernetesClient()
    ret = client.list_service_for_all_namespaces(watch=False)
    yaml = YAML()
    with open('/Users/luganlin/.omc/config/kube/cd150/config') as f:
        content = yaml.load(f)
        print(ObjectUtils.get_node(content, "clusters[0].cluster.server"))

    # print(client.read_namespaced_pod("postgres-svc-5685d4bc7-l6j4m", 'default'))
    # print(client.read_namespaced_pod_template("postgres-svc-5685d4bc7-l6j4m", 'default'))
    # print(client.read_namspaced_event("postgres-svc-5685d4bc7-l6j4m", 'default'))
    console.log(ret)
    # for i in ret.items:
    #     print("%s\t%s\t%s" % (i.status.pod_ip, i.metadata.namespace, i.metadata.name))
Example #14
0
        ssl_dir = self._get_cert_dir(
            os.path.join(the_kube_config_dir, 'config'))

        # download ssl files
        console.log("downloading ssl certificate to %s" % the_kube_config_dir)
        certificate_download_cmd = 'scp -r %s:%s %s' % (k8s_resource, ssl_dir,
                                                        the_kube_config_dir)
        self.run_cmd(certificate_download_cmd)

        kube_config_file = os.path.join(the_kube_config_dir, 'config')
        file_utils.inplace_replace(kube_config_file, ssl_dir,
                                   os.path.join(the_kube_config_dir, 'ssl'))

    def _get_cert_dir(self, config_file):
        import yaml
        with open(config_file) as f:
            result = yaml.load(f, yaml.FullLoader)
            path = (ObjectUtils.get_node(
                result, 'clusters[0].cluster.certificate-authority'))
            return os.path.dirname(path)


if __name__ == '__main__':
    import yaml
    with open('/Users/luganlin/.omc/config/kube/cd219/config') as f:
        result = yaml.load(f, yaml.FullLoader)
        path = (ObjectUtils.get_node(
            result, 'clusters[0].cluster.certificate-authority'))
        console.log(os.path.dirname(path))
        console.log(result)
Example #15
0
 def get_namespace(self, resource_type: str, resource_name: str):
     list_namespaces = getattr(self, "list_%s_for_all_namespaces" % resource_type)
     all_namespaces = list_namespaces()
     for one in all_namespaces.get('items'):
         if ObjectUtils.get_node(one, 'metadata.name') == resource_name:
             return ObjectUtils.get_node(one, 'metadata.namespace')
Example #16
0
    def gen_strategic_merge_patch(self, origin, key_array, value, action, path):
        '''
        'spec.template.spec.containers[0].env[1]',
         {'name': 'name1', 'value': 'value1'}
        '''
        keys = key_array.copy()
        one_key = keys.pop(0)
        current_path = path.copy()  # raw path, with array index
        current_path.append(one_key)

        the_key, is_array, index = self.parse_one_key(one_key)
        current_key_path = '.'.join(
            [*path, the_key])  # with old array index, without current index, for get object value
        current_flatten_path = self.flatten_key('.'.join([*path, the_key]))  # no array index, only for api spec usage

        if not is_array:
            if not keys:
                # no key any more
                if action == 'set':
                    return {the_key: value}
                elif action == 'delete':
                    return {the_key: None}
            else:
                return {the_key: self.gen_strategic_merge_patch(origin, keys, value, action, current_path)}
        else:

            the_value = value

            if current_flatten_path in self.api_spec:
                # for array, we have stratgic merge rule
                current_value = ObjectUtils.get_node(origin, current_key_path)

                merge_key = self.api_spec[current_flatten_path]['x-kubernetes-patch-merge-key']
                patch_strategy = self.api_spec[current_flatten_path]['x-kubernetes-patch-strategy']
                results = {}

                '''
                 "$setElementOrder/containers": [
                    {
                        "name": "idm"
                    }
                ],
                '''
                if keys:
                    # has children
                    results['$setElementOrder/%s' % the_key] = [{merge_key: one.get(merge_key)} for one in
                                                                current_value]
                    results[the_key] = [
                        {
                            merge_key: current_value[index].get(merge_key),
                            **self.gen_strategic_merge_patch(origin, keys, the_value, action, current_path)
                        }
                    ]

                if not keys:
                    results['$setElementOrder/%s' % the_key] = [{merge_key: one.get(merge_key)} for one in
                                                                current_value]
                    if action == 'set':
                        one_item = []
                        if isinstance(value, dict):
                            value = {**value, merge_key: current_value[index].get(merge_key)}
                        one_item.insert(index, value)
                        results[the_key] = one_item
                    elif action == 'delete':
                        one_item = []
                        # one_item.insert(index, value)
                        one_item.append({"$patch": 'delete', **value})
                        results[the_key] = one_item
                return results

            else:
                # if no merge rule, merge normally
                current_value = ObjectUtils.get_node(origin, current_key_path)
                current_value = current_value if current_value else []
                current_value.insert(index, the_value)