From da9aab90ebe489d3214d189c84970e695cff96f3 Mon Sep 17 00:00:00 2001 From: admju Date: Fri, 6 Sep 2024 14:08:05 +0000 Subject: [PATCH] Ressources --- src/helm/chart.go | 12 +- src/helm/command.go | 38 +++ src/helm/ressources.go | 84 +++++ src/helm/ressources_test.go | 28 ++ src/install/install.go | 21 +- src/kubectl/command.go | 29 ++ src/kubectl/object.go | 40 +++ test/helm/helm_status.json | 663 ++++++++++++++++++++++++++++++++++++ 8 files changed, 907 insertions(+), 8 deletions(-) create mode 100644 src/helm/command.go create mode 100644 src/helm/ressources.go create mode 100644 src/helm/ressources_test.go create mode 100644 src/kubectl/command.go create mode 100644 test/helm/helm_status.json diff --git a/src/helm/chart.go b/src/helm/chart.go index b5b6697..93760f6 100644 --- a/src/helm/chart.go +++ b/src/helm/chart.go @@ -2,6 +2,7 @@ package helm import ( "fmt" + "strconv" "os" "os/exec" "strings" @@ -41,7 +42,6 @@ func (this HelmChart) Install() (string, error) { if err != nil { return "", err } - // existe := false if existe { return "Existe déjà", nil @@ -137,6 +137,7 @@ func (this HelmChart) exists() (bool, error) { cmd := exec.Command(cmd_args[0], cmd_args[1:]...) stdout, err := cmd.CombinedOutput() if err != nil { + log.Log().Debug().Msg(string(stdout)) return false, errors.New(string(stdout)) } @@ -144,6 +145,15 @@ func (this HelmChart) exists() (bool, error) { res = strings.TrimSuffix(res, "\n") log.Log().Debug().Msg(string(stdout)) + log.Log().Debug().Msg(strconv.FormatBool(res != "")) return res != "", nil } + +func (this HelmChart) GetRessources() (map[string]string, error) { + hs := HelmStatus{Name: this.Name} + hs.New(this.Bin) + data, _ := hs.getRessources() + + return data, nil +} \ No newline at end of file diff --git a/src/helm/command.go b/src/helm/command.go new file mode 100644 index 0000000..0f3fe96 --- /dev/null +++ b/src/helm/command.go @@ -0,0 +1,38 @@ +package helm + +import ( + "fmt" + "strings" + "errors" + "os/exec" + + log "oc-deploy/log_wrapper" +) + +type HelmCommandInterface interface { + Status(string) (string, error) +} + +type HelmCommandData struct { + bin string + // name string +} + +type RealHelmCommandStatus HelmCommandData + +func (this RealHelmCommandStatus) Status(name string) (string, error) { + + msg := fmt.Sprintf("%s status %s --show-resources -o json", this.bin, name) + log.Log().Debug().Msg(msg) + + cmd_args := strings.Split(msg, " ") + + cmd := exec.Command(cmd_args[0], cmd_args[1:]...) + stdout, err := cmd.CombinedOutput() + if err != nil { + log.Log().Debug().Msg(string(stdout)) + return "", errors.New(string(stdout)) + } + + return string(stdout), nil +} diff --git a/src/helm/ressources.go b/src/helm/ressources.go new file mode 100644 index 0000000..f7becb3 --- /dev/null +++ b/src/helm/ressources.go @@ -0,0 +1,84 @@ +package helm + +import ( + // "fmt" + "encoding/json" +) + +type HelmStatus struct { + Name string // Nom + command HelmCommandInterface +} + +func (this *HelmStatus) New(bin string) { + this.command = RealHelmCommandStatus{bin: bin} +} + +func (this *HelmStatus) NewMock(mock HelmCommandInterface) { + this.command = mock +} + +//// + +type parseStatusInfoResourcesMetadata struct { + Name string `json:"name"` +} + +// type parseStatusInfoResourcesPod struct { +// Api string `json:"apiVersion"` +// } + +type parseStatusInfoResourcesStatefulSet struct { + Api string `json:"apiVersion"` + Kind string `json:"kind"` + Metadata parseStatusInfoResourcesMetadata `json:"metadata"` +} + +type parseStatusInfoResourcesDeployment struct { + Api string `json:"apiVersion"` + Kind string `json:"kind"` + Metadata parseStatusInfoResourcesMetadata `json:"metadata"` +} + +type parseStatusInfoResources struct { + // Pod []parseStatusInfoResourcesPod `json:"v1/Pod(related)"` + StatefulSet []parseStatusInfoResourcesStatefulSet `json:"v1/StatefulSet"` + Deployment []parseStatusInfoResourcesDeployment `json:"v1/Deployment"` +} + +type parseStatusInfo struct { + Status string `json:"status"` + Resources parseStatusInfoResources `json:"Resources"` +} + + +type parseStatus struct { + Name string `json:"name"` + Info parseStatusInfo `json:"info"` +} + +func (this HelmStatus) getRessources() (map[string]string, error) { + + res := make(map[string]string) + + status, err := this.command.Status(this.Name) + if err != nil { + return res, err + } + + var objmap parseStatus + + err = json.Unmarshal([]byte(status), &objmap) + if err != nil { + return res, err + } + + for _, ele := range objmap.Info.Resources.StatefulSet { + res[ele.Metadata.Name] = ele.Kind + } + for _, ele := range objmap.Info.Resources.Deployment { + res[ele.Metadata.Name] = ele.Kind + } + + return res, nil +} \ No newline at end of file diff --git a/src/helm/ressources_test.go b/src/helm/ressources_test.go new file mode 100644 index 0000000..488f504 --- /dev/null +++ b/src/helm/ressources_test.go @@ -0,0 +1,28 @@ +package helm + +import ( + "os" + "path/filepath" + + "testing" + + "github.com/stretchr/testify/assert" +) + +type MockCommandStatus HelmCommandData + +func TestHelmStatus(t *testing.T){ + + hs := HelmStatus{Name: "oc-catalog"} + hs.NewMock(MockCommandStatus{}) + + data, _ := hs.getRessources() + assert.Equal(t, "StatefulSet", data["oc-catalog-oc-catalog"], "TestHelmStatus error") +} + +// Mock +func (this MockCommandStatus) Status(name string) (string, error) { + fileName := filepath.Join(TEST_SRC_DIR, "helm_status.json") + data, _ := os.ReadFile(fileName) + return string(data), nil +} \ No newline at end of file diff --git a/src/install/install.go b/src/install/install.go index f3cf495..e2f35e2 100644 --- a/src/install/install.go +++ b/src/install/install.go @@ -134,8 +134,6 @@ func (this *InstallClass) installChart(helm_bin string, kubectl_bin string, char Values: chart.Values, FileValues: chart.FileValues} - obj := kubectl.KubeObject{Bin: kubectl_bin, - Name: chart.Name} res, err := helmchart.Install() if err != nil { @@ -144,10 +142,19 @@ func (this *InstallClass) installChart(helm_bin string, kubectl_bin string, char } log.Log().Info().Msg(fmt.Sprintf(" >> %s (%s)", helmchart.Name, res)) - err = obj.Wait() - if err != nil { - log.Log().Error().Msg(fmt.Sprintf(" >> %s %s (%s)", chart.Name, "KO", err)) - } else { - log.Log().Info().Msg(fmt.Sprintf(" >> %s %s", chart.Name, "OK")) + ressources, _ := helmchart.GetRessources() + + for key, value := range ressources { + obj := kubectl.KubeObject{Bin: kubectl_bin, + Kind: value, + Name: key} + err := obj.Wait() + if err != nil { + log.Log().Error().Msg(fmt.Sprintf(" >> %s/%s KO (%s)", chart.Name, key, err)) + } else { + log.Log().Info().Msg(fmt.Sprintf(" >> %s/%s OK", chart.Name, key)) + } + } + } diff --git a/src/kubectl/command.go b/src/kubectl/command.go new file mode 100644 index 0000000..56ab060 --- /dev/null +++ b/src/kubectl/command.go @@ -0,0 +1,29 @@ +package kubectl + +// import ( +// "fmt" +// ) + +// type KubectlCommandInterface interface { +// // GetDeployment() (string, error) +// GetDeployment() (string, error) +// } + +// type KubectlCommandData struct { +// bin string +// command string +// } + +// type Real KubectlCommandStatus KubectlCommandData + +// // func (this KubectlCommandStatus) Status() (string, error) { +// // fmt.Println("BIN ", this.bin) +// // fmt.Println("COMMAND status") +// // return "Res de KubectlCommandStatus", nil +// // } + +// func (this KubectlCommandStatus) GetDeployment() (string, error) { +// fmt.Println("BIN ", this.bin) +// fmt.Println("COMMAND status") +// return "Res de GetDeployment", nil +// } diff --git a/src/kubectl/object.go b/src/kubectl/object.go index 9aff676..e2c3791 100644 --- a/src/kubectl/object.go +++ b/src/kubectl/object.go @@ -13,6 +13,7 @@ import ( type KubeObject struct { Bin string // Chemin vers le binaire Name string + Kind string } type getOutput struct { @@ -26,6 +27,12 @@ type getStatusOutput struct { } func (this KubeObject) Get() (map[string]any, error) { + if this.Kind == "Deployment" {return this.getDeployment()} + if this.Kind == "StatefulSet" {return this.getStatefulSet()} + return make(map[string]any), fmt.Errorf("Kind %s inconnu", this.Kind) +} + +func (this KubeObject) getDeployment() (map[string]any, error) { bin := this.Bin name := this.Name @@ -57,6 +64,38 @@ func (this KubeObject) Get() (map[string]any, error) { return m, nil } +func (this KubeObject) getStatefulSet() (map[string]any, error) { + bin := this.Bin + name := this.Name + + msg := fmt.Sprintf("%s get statefulset %s -o json", bin, name) + log.Log().Debug().Msg(msg) + + m := make(map[string]any) + + cmd_args := strings.Split(msg, " ") + + cmd := exec.Command(cmd_args[0], cmd_args[1:]...) + stdout, err := cmd.CombinedOutput() + if err != nil { + return m, errors.New(string(stdout)) + } + + var objmap getOutput + + json.Unmarshal(stdout, &objmap) + + kind := objmap.Kind + status := objmap.Status + + m["name"] = name + m["kind"] = kind + m["replicas"] = status.Replicas + m["UnavailableReplicas"] = status.UnavailableReplicas + + return m, nil +} + func (this KubeObject) Wait() (error) { boucle := 10 @@ -75,6 +114,7 @@ func (this KubeObject) Wait() (error) { return nil } + log.Log().Info().Msg(fmt.Sprintf(" >> %s (Unavailable : %d)...", this.Name, ko)) time.Sleep(sleep) } diff --git a/test/helm/helm_status.json b/test/helm/helm_status.json new file mode 100644 index 0000000..7215d20 --- /dev/null +++ b/test/helm/helm_status.json @@ -0,0 +1,663 @@ +{ + "name": "oc-catalog", + "info": { + "first_deployed": "2024-09-05T19:06:44.16497388+02:00", + "last_deployed": "2024-09-05T19:06:44.16497388+02:00", + "deleted": "", + "description": "Install complete", + "status": "deployed", + "resources": { + "v1/Pod(related)": [ + { + "apiVersion": "v1", + "items": [ + { + "apiVersion": "v1", + "kind": "Pod", + "metadata": { + "annotations": { + "cni.projectcalico.org/containerID": "bc524c3ff4a2fceaeb9a996a9324807c0fddfc4c3e02cd59d73a9945d27d5f1b", + "cni.projectcalico.org/podIP": "10.42.2.10/32", + "cni.projectcalico.org/podIPs": "10.42.2.10/32" + }, + "creationTimestamp": "2024-09-05T17:06:44Z", + "generateName": "oc-catalog-oc-catalog-", + "labels": { + "app": "oc-catalog", + "apps.kubernetes.io/pod-index": "0", + "controller-revision-hash": "oc-catalog-oc-catalog-7d7859dd76", + "statefulset.kubernetes.io/pod-name": "oc-catalog-oc-catalog-0" + }, + "managedFields": [ + { + "apiVersion": "v1", + "fieldsType": "FieldsV1", + "fieldsV1": { + "f:metadata": { + "f:annotations": { + ".": {}, + "f:cni.projectcalico.org/containerID": {}, + "f:cni.projectcalico.org/podIP": {}, + "f:cni.projectcalico.org/podIPs": {} + } + } + }, + "manager": "calico", + "operation": "Update", + "subresource": "status", + "time": "2024-09-05T17:06:44Z" + }, + { + "apiVersion": "v1", + "fieldsType": "FieldsV1", + "fieldsV1": { + "f:metadata": { + "f:generateName": {}, + "f:labels": { + ".": {}, + "f:app": {}, + "f:apps.kubernetes.io/pod-index": {}, + "f:controller-revision-hash": {}, + "f:statefulset.kubernetes.io/pod-name": {} + }, + "f:ownerReferences": { + ".": {}, + "k:{\"uid\":\"10aa222e-dc37-451e-a5ee-e88f88b4e136\"}": {} + } + }, + "f:spec": { + "f:containers": { + "k:{\"name\":\"oc-catalog\"}": { + ".": {}, + "f:env": { + ".": {}, + "k:{\"name\":\"MONGO_DATABASE\"}": { + ".": {}, + "f:name": {}, + "f:value": {} + }, + "k:{\"name\":\"MONGO_URI\"}": { + ".": {}, + "f:name": {}, + "f:value": {} + } + }, + "f:image": {}, + "f:imagePullPolicy": {}, + "f:name": {}, + "f:ports": { + ".": {}, + "k:{\"containerPort\":8080,\"protocol\":\"TCP\"}": { + ".": {}, + "f:containerPort": {}, + "f:protocol": {} + } + }, + "f:resources": {}, + "f:terminationMessagePath": {}, + "f:terminationMessagePolicy": {} + } + }, + "f:dnsPolicy": {}, + "f:enableServiceLinks": {}, + "f:hostname": {}, + "f:imagePullSecrets": { + ".": {}, + "k:{\"name\":\"regcred\"}": {} + }, + "f:restartPolicy": {}, + "f:schedulerName": {}, + "f:securityContext": {}, + "f:subdomain": {}, + "f:terminationGracePeriodSeconds": {} + } + }, + "manager": "kube-controller-manager", + "operation": "Update", + "time": "2024-09-05T17:06:44Z" + }, + { + "apiVersion": "v1", + "fieldsType": "FieldsV1", + "fieldsV1": { + "f:status": { + "f:conditions": { + "k:{\"type\":\"ContainersReady\"}": { + ".": {}, + "f:lastProbeTime": {}, + "f:lastTransitionTime": {}, + "f:status": {}, + "f:type": {} + }, + "k:{\"type\":\"Initialized\"}": { + ".": {}, + "f:lastProbeTime": {}, + "f:lastTransitionTime": {}, + "f:status": {}, + "f:type": {} + }, + "k:{\"type\":\"Ready\"}": { + ".": {}, + "f:lastProbeTime": {}, + "f:lastTransitionTime": {}, + "f:status": {}, + "f:type": {} + } + }, + "f:containerStatuses": {}, + "f:hostIP": {}, + "f:phase": {}, + "f:podIP": {}, + "f:podIPs": { + ".": {}, + "k:{\"ip\":\"10.42.2.10\"}": { + ".": {}, + "f:ip": {} + } + }, + "f:startTime": {} + } + }, + "manager": "kubelet", + "operation": "Update", + "subresource": "status", + "time": "2024-09-05T17:06:46Z" + } + ], + "name": "oc-catalog-oc-catalog-0", + "namespace": "default", + "ownerReferences": [ + { + "apiVersion": "apps/v1", + "blockOwnerDeletion": true, + "controller": true, + "kind": "StatefulSet", + "name": "oc-catalog-oc-catalog", + "uid": "10aa222e-dc37-451e-a5ee-e88f88b4e136" + } + ], + "resourceVersion": "7811984", + "uid": "f2b3e7d0-68de-4f60-a8b7-75446ee3ebf1" + }, + "spec": { + "containers": [ + { + "env": [ + { + "name": "MONGO_DATABASE", + "value": "DC_myDC" + }, + { + "name": "MONGO_URI", + "value": "mongodb://mongo:27017" + } + ], + "image": "harbor.dtf/dev/oc-catalog:1.0", + "imagePullPolicy": "IfNotPresent", + "name": "oc-catalog", + "ports": [ + { + "containerPort": 8080, + "protocol": "TCP" + } + ], + "resources": {}, + "terminationMessagePath": "/dev/termination-log", + "terminationMessagePolicy": "File", + "volumeMounts": [ + { + "mountPath": "/var/run/secrets/kubernetes.io/serviceaccount", + "name": "kube-api-access-lpks6", + "readOnly": true + } + ] + } + ], + "dnsPolicy": "ClusterFirst", + "enableServiceLinks": true, + "hostname": "oc-catalog-oc-catalog-0", + "imagePullSecrets": [ + { + "name": "regcred" + } + ], + "nodeName": "rke2-worker1", + "preemptionPolicy": "PreemptLowerPriority", + "priority": 0, + "restartPolicy": "Always", + "schedulerName": "default-scheduler", + "securityContext": {}, + "serviceAccount": "default", + "serviceAccountName": "default", + "subdomain": "oc-catalog-oc-catalog", + "terminationGracePeriodSeconds": 30, + "tolerations": [ + { + "effect": "NoExecute", + "key": "node.kubernetes.io/not-ready", + "operator": "Exists", + "tolerationSeconds": 300 + }, + { + "effect": "NoExecute", + "key": "node.kubernetes.io/unreachable", + "operator": "Exists", + "tolerationSeconds": 300 + } + ], + "volumes": [ + { + "name": "kube-api-access-lpks6", + "projected": { + "defaultMode": 420, + "sources": [ + { + "serviceAccountToken": { + "expirationSeconds": 3607, + "path": "token" + } + }, + { + "configMap": { + "items": [ + { + "key": "ca.crt", + "path": "ca.crt" + } + ], + "name": "kube-root-ca.crt" + } + }, + { + "downwardAPI": { + "items": [ + { + "fieldRef": { + "apiVersion": "v1", + "fieldPath": "metadata.namespace" + }, + "path": "namespace" + } + ] + } + } + ] + } + } + ] + }, + "status": { + "conditions": [ + { + "lastProbeTime": null, + "lastTransitionTime": "2024-09-05T17:06:44Z", + "status": "True", + "type": "Initialized" + }, + { + "lastProbeTime": null, + "lastTransitionTime": "2024-09-05T17:06:46Z", + "status": "True", + "type": "Ready" + }, + { + "lastProbeTime": null, + "lastTransitionTime": "2024-09-05T17:06:46Z", + "status": "True", + "type": "ContainersReady" + }, + { + "lastProbeTime": null, + "lastTransitionTime": "2024-09-05T17:06:44Z", + "status": "True", + "type": "PodScheduled" + } + ], + "containerStatuses": [ + { + "containerID": "containerd://b50252d915ab1bdf1ade5c9afff589e8f6b7cd98e1c507eb5f398c390d7f120c", + "image": "harbor.dtf/dev/oc-catalog:1.0", + "imageID": "harbor.dtf/dev/oc-catalog@sha256:b4e135ecc4e69b93636118f42e436eb0948f9781ffbec4911bb944b79fd415b3", + "lastState": {}, + "name": "oc-catalog", + "ready": true, + "restartCount": 0, + "started": true, + "state": { + "running": { + "startedAt": "2024-09-05T17:06:46Z" + } + } + } + ], + "hostIP": "172.17.40.249", + "phase": "Running", + "podIP": "10.42.2.10", + "podIPs": [ + { + "ip": "10.42.2.10" + } + ], + "qosClass": "BestEffort", + "startTime": "2024-09-05T17:06:44Z" + } + } + ], + "kind": "PodList", + "metadata": { + "resourceVersion": "8001092" + } + } + ], + "v1/Service": [ + { + "apiVersion": "v1", + "kind": "Service", + "metadata": { + "annotations": { + "meta.helm.sh/release-name": "oc-catalog", + "meta.helm.sh/release-namespace": "default" + }, + "creationTimestamp": "2024-09-05T17:06:44Z", + "labels": { + "app.kubernetes.io/managed-by": "Helm" + }, + "managedFields": [ + { + "apiVersion": "v1", + "fieldsType": "FieldsV1", + "fieldsV1": { + "f:metadata": { + "f:annotations": { + ".": {}, + "f:meta.helm.sh/release-name": {}, + "f:meta.helm.sh/release-namespace": {} + }, + "f:labels": { + ".": {}, + "f:app.kubernetes.io/managed-by": {} + } + }, + "f:spec": { + "f:externalTrafficPolicy": {}, + "f:internalTrafficPolicy": {}, + "f:ports": { + ".": {}, + "k:{\"port\":8087,\"protocol\":\"TCP\"}": { + ".": {}, + "f:port": {}, + "f:protocol": {}, + "f:targetPort": {} + } + }, + "f:selector": {}, + "f:sessionAffinity": {}, + "f:type": {} + } + }, + "manager": "helm", + "operation": "Update", + "time": "2024-09-05T17:06:44Z" + } + ], + "name": "oc-catalog-oc-catalog", + "namespace": "default", + "resourceVersion": "7811955", + "uid": "bb9f6cd3-298c-4d98-9f6a-59cbd70ddac2" + }, + "spec": { + "clusterIP": "10.43.6.251", + "clusterIPs": [ + "10.43.6.251" + ], + "externalTrafficPolicy": "Cluster", + "internalTrafficPolicy": "Cluster", + "ipFamilies": [ + "IPv4" + ], + "ipFamilyPolicy": "SingleStack", + "ports": [ + { + "nodePort": 32692, + "port": 8087, + "protocol": "TCP", + "targetPort": 8080 + } + ], + "selector": { + "app": "oc-catalog" + }, + "sessionAffinity": "None", + "type": "NodePort" + }, + "status": { + "loadBalancer": {} + } + } + ], + "v1/StatefulSet": [ + { + "apiVersion": "apps/v1", + "kind": "StatefulSet", + "metadata": { + "annotations": { + "meta.helm.sh/release-name": "oc-catalog", + "meta.helm.sh/release-namespace": "default" + }, + "creationTimestamp": "2024-09-05T17:06:44Z", + "generation": 1, + "labels": { + "app": "oc-catalog", + "app.kubernetes.io/managed-by": "Helm" + }, + "managedFields": [ + { + "apiVersion": "apps/v1", + "fieldsType": "FieldsV1", + "fieldsV1": { + "f:metadata": { + "f:annotations": { + ".": {}, + "f:meta.helm.sh/release-name": {}, + "f:meta.helm.sh/release-namespace": {} + }, + "f:labels": { + ".": {}, + "f:app": {}, + "f:app.kubernetes.io/managed-by": {} + } + }, + "f:spec": { + "f:persistentVolumeClaimRetentionPolicy": { + ".": {}, + "f:whenDeleted": {}, + "f:whenScaled": {} + }, + "f:podManagementPolicy": {}, + "f:replicas": {}, + "f:revisionHistoryLimit": {}, + "f:selector": {}, + "f:serviceName": {}, + "f:template": { + "f:metadata": { + "f:labels": { + ".": {}, + "f:app": {} + } + }, + "f:spec": { + "f:containers": { + "k:{\"name\":\"oc-catalog\"}": { + ".": {}, + "f:env": { + ".": {}, + "k:{\"name\":\"MONGO_DATABASE\"}": { + ".": {}, + "f:name": {}, + "f:value": {} + }, + "k:{\"name\":\"MONGO_URI\"}": { + ".": {}, + "f:name": {}, + "f:value": {} + } + }, + "f:image": {}, + "f:imagePullPolicy": {}, + "f:name": {}, + "f:ports": { + ".": {}, + "k:{\"containerPort\":8080,\"protocol\":\"TCP\"}": { + ".": {}, + "f:containerPort": {}, + "f:protocol": {} + } + }, + "f:resources": {}, + "f:terminationMessagePath": {}, + "f:terminationMessagePolicy": {} + } + }, + "f:dnsPolicy": {}, + "f:imagePullSecrets": { + ".": {}, + "k:{\"name\":\"regcred\"}": {} + }, + "f:restartPolicy": {}, + "f:schedulerName": {}, + "f:securityContext": {}, + "f:terminationGracePeriodSeconds": {} + } + }, + "f:updateStrategy": { + "f:rollingUpdate": { + ".": {}, + "f:partition": {} + }, + "f:type": {} + } + } + }, + "manager": "helm", + "operation": "Update", + "time": "2024-09-05T17:06:44Z" + }, + { + "apiVersion": "apps/v1", + "fieldsType": "FieldsV1", + "fieldsV1": { + "f:status": { + "f:availableReplicas": {}, + "f:collisionCount": {}, + "f:currentReplicas": {}, + "f:currentRevision": {}, + "f:observedGeneration": {}, + "f:readyReplicas": {}, + "f:replicas": {}, + "f:updateRevision": {}, + "f:updatedReplicas": {} + } + }, + "manager": "kube-controller-manager", + "operation": "Update", + "subresource": "status", + "time": "2024-09-05T17:06:46Z" + } + ], + "name": "oc-catalog-oc-catalog", + "namespace": "default", + "resourceVersion": "7811987", + "uid": "10aa222e-dc37-451e-a5ee-e88f88b4e136" + }, + "spec": { + "persistentVolumeClaimRetentionPolicy": { + "whenDeleted": "Retain", + "whenScaled": "Retain" + }, + "podManagementPolicy": "OrderedReady", + "replicas": 1, + "revisionHistoryLimit": 10, + "selector": { + "matchLabels": { + "app": "oc-catalog" + } + }, + "serviceName": "oc-catalog-oc-catalog", + "template": { + "metadata": { + "creationTimestamp": null, + "labels": { + "app": "oc-catalog" + } + }, + "spec": { + "containers": [ + { + "env": [ + { + "name": "MONGO_DATABASE", + "value": "DC_myDC" + }, + { + "name": "MONGO_URI", + "value": "mongodb://mongo:27017" + } + ], + "image": "harbor.dtf/dev/oc-catalog:1.0", + "imagePullPolicy": "IfNotPresent", + "name": "oc-catalog", + "ports": [ + { + "containerPort": 8080, + "protocol": "TCP" + } + ], + "resources": {}, + "terminationMessagePath": "/dev/termination-log", + "terminationMessagePolicy": "File" + } + ], + "dnsPolicy": "ClusterFirst", + "imagePullSecrets": [ + { + "name": "regcred" + } + ], + "restartPolicy": "Always", + "schedulerName": "default-scheduler", + "securityContext": {}, + "terminationGracePeriodSeconds": 30 + } + }, + "updateStrategy": { + "rollingUpdate": { + "partition": 0 + }, + "type": "RollingUpdate" + } + }, + "status": { + "availableReplicas": 1, + "collisionCount": 0, + "currentReplicas": 1, + "currentRevision": "oc-catalog-oc-catalog-7d7859dd76", + "observedGeneration": 1, + "readyReplicas": 1, + "replicas": 1, + "updateRevision": "oc-catalog-oc-catalog-7d7859dd76", + "updatedReplicas": 1 + } + } + ] + } + }, + "config": { + "image": { + "repository": "harbor.dtf/dev/oc-catalog", + "tag": "1.0" + } + }, + "manifest": "---\n# Source: oc-catalog/templates/service.yml\napiVersion: v1\nkind: Service\nmetadata:\n name: oc-catalog-oc-catalog\nspec:\n selector:\n app: oc-catalog\n ports:\n - protocol: TCP\n port: 8087\n targetPort: 8080\n type: NodePort\n---\n# Source: oc-catalog/templates/statefulset.yml\napiVersion: apps/v1\nkind: StatefulSet\nmetadata:\n name: oc-catalog-oc-catalog\n labels:\n app: oc-catalog\nspec:\n serviceName: \"oc-catalog-oc-catalog\"\n replicas: 1\n selector:\n matchLabels:\n app: oc-catalog\n template:\n metadata:\n labels:\n app: oc-catalog\n spec:\n containers:\n - name: oc-catalog\n image: \"harbor.dtf/dev/oc-catalog:1.0\"\n ports:\n - containerPort: 8080\n env:\n - name: MONGO_DATABASE\n value: \"DC_myDC\"\n - name: MONGO_URI\n value: \"mongodb://mongo:27017\"\n imagePullSecrets:\n - name: regcred\n", + "version": 1, + "namespace": "default" +}