From 12324beaed87a2dbdcb0cb69992870a23a7f07e1 Mon Sep 17 00:00:00 2001 From: Ankita Thomas Date: Thu, 9 Jul 2026 09:56:12 -0400 Subject: [PATCH] add products-data container and service to service products.json if present in graph-data image Signed-off-by: Ankita Thomas --- controllers/names.go | 6 ++ controllers/new.go | 100 ++++++++++++++++++ ...ture_Test_newKubeResources_deployment.yaml | 55 ++++++++++ controllers/updateservice_controller.go | 13 +++ dev/Dockerfile | 4 + 5 files changed, 178 insertions(+) diff --git a/controllers/names.go b/controllers/names.go index cf81bf32..484ffb1a 100644 --- a/controllers/names.go +++ b/controllers/names.go @@ -26,6 +26,8 @@ const ( namePullSecret = "pull-secret" // ClusterCAMountDir is the mount path for the dir containing cluster CA ClusterCAMountDir = "/etc/pki/ca-trust/extracted/cluster-ca/" + // NameProductsData is the Name property of the products data container + NameProductsData = "products-data" ) func nameDeployment(instance *cv1.UpdateService) string { @@ -77,3 +79,7 @@ func getMinAvailablePBD(instance *cv1.UpdateService) intstr.IntOrString { } return minAvailable } + +func NameProductsDataService(instance *cv1.UpdateService) string { + return instance.Name + "-products-data" +} diff --git a/controllers/new.go b/controllers/new.go index bb66a669..77d6c2d7 100644 --- a/controllers/new.go +++ b/controllers/new.go @@ -99,6 +99,8 @@ type kubeResources struct { pullSecret *corev1.Secret volumes []corev1.Volume graphBuilderVolumeMounts []corev1.VolumeMount + productsServiceContainer *corev1.Container + productsService *corev1.Service } func newKubeResources(instance *cv1.UpdateService, image string, pullSecret *corev1.Secret, caConfigMap *corev1.ConfigMap, clusterCA *corev1.ConfigMap) (*kubeResources, error) { @@ -132,12 +134,14 @@ func newKubeResources(instance *cv1.UpdateService, image string, pullSecret *cor k.graphBuilderContainer = k.newGraphBuilderContainer(instance, image) k.graphDataInitContainer = k.newGraphDataInitContainer(instance) k.policyEngineContainer = k.newPolicyEngineContainer(instance, image) + k.productsServiceContainer = k.newProductsServiceContainer(instance, image) k.deployment = k.newDeployment(instance) k.graphBuilderService = k.newGraphBuilderService(instance) k.policyEngineService = k.newPolicyEngineService(instance) k.policyEngineRoute = k.newPolicyEngineRoute(instance) k.policyEngineOldRoute = k.oldPolicyEngineRoute(instance) k.networkPolicy = k.newNetworkPolicy(instance) + k.productsService = k.newProductsService(instance) return &k, nil } @@ -610,6 +614,7 @@ func (k *kubeResources) newDeployment(instance *cv1.UpdateService) *appsv1.Deplo Containers: []corev1.Container{ *k.graphBuilderContainer, *k.policyEngineContainer, + *k.productsServiceContainer, }, }, }, @@ -1031,3 +1036,98 @@ func checksumMap(m map[string]string) (string, error) { return fmt.Sprintf("%x", hash.Sum(nil)), nil } + +func (k *kubeResources) newProductsServiceContainer(instance *cv1.UpdateService, image string) *corev1.Container { + return &corev1.Container{ + Name: NameProductsData, + Image: image, + ImagePullPolicy: corev1.PullIfNotPresent, + Command: []string{ + "/usr/bin/products-service", // New binary to add to Cincinnati + }, + Args: []string{ + "--data-directory", + "/var/lib/cincinnati/graph-data/products", + "--address", + "::", + "--port", + "8082", + }, + Ports: []corev1.ContainerPort{ + { + Name: "products", + ContainerPort: 8082, + Protocol: corev1.ProtocolTCP, + }, + }, + VolumeMounts: k.newGraphBuilderVolumeMounts(instance), + Resources: corev1.ResourceRequirements{ + Limits: corev1.ResourceList{ + corev1.ResourceCPU: *resource.NewMilliQuantity(250, resource.DecimalSI), + corev1.ResourceMemory: *resource.NewQuantity(128*1024*1024, resource.BinarySI), + }, + Requests: corev1.ResourceList{ + corev1.ResourceCPU: *resource.NewMilliQuantity(50, resource.DecimalSI), + corev1.ResourceMemory: *resource.NewQuantity(32*1024*1024, resource.BinarySI), + }, + }, + LivenessProbe: &corev1.Probe{ + FailureThreshold: 3, + SuccessThreshold: 1, + InitialDelaySeconds: 5, + PeriodSeconds: 30, + TimeoutSeconds: 3, + ProbeHandler: corev1.ProbeHandler{ + HTTPGet: &corev1.HTTPGetAction{ + Path: "/healthz", + Port: intstr.FromInt32(8082), + Scheme: corev1.URISchemeHTTP, + }, + }, + }, + ReadinessProbe: &corev1.Probe{ + FailureThreshold: 3, + SuccessThreshold: 1, + InitialDelaySeconds: 3, + PeriodSeconds: 30, + TimeoutSeconds: 3, + ProbeHandler: corev1.ProbeHandler{ + HTTPGet: &corev1.HTTPGetAction{ + Path: "/healthz", + Port: intstr.FromInt32(8082), + Scheme: corev1.URISchemeHTTP, + }, + }, + }, + } +} + +func (k *kubeResources) newProductsService(instance *cv1.UpdateService) *corev1.Service { + name := NameProductsDataService(instance) + return &corev1.Service{ + ObjectMeta: metav1.ObjectMeta{ + Name: name, + Namespace: instance.Namespace, + Annotations: map[string]string{ + DescriptionAnnotation: "This Service exposes product lifecycle information from the graph-data.", + }, + Labels: map[string]string{ + "app": name, + }, + }, + Spec: corev1.ServiceSpec{ + Type: corev1.ServiceTypeClusterIP, + Ports: []corev1.ServicePort{ + { + Name: "products", + Port: 8082, + TargetPort: intstr.FromInt32(8082), + Protocol: corev1.ProtocolTCP, + }, + }, + Selector: map[string]string{ + "deployment": nameDeployment(instance), + }, + }, + } +} diff --git a/controllers/testdata/resources/zz_fixture_Test_newKubeResources_deployment.yaml b/controllers/testdata/resources/zz_fixture_Test_newKubeResources_deployment.yaml index 92c3e543..5fb2788d 100644 --- a/controllers/testdata/resources/zz_fixture_Test_newKubeResources_deployment.yaml +++ b/controllers/testdata/resources/zz_fixture_Test_newKubeResources_deployment.yaml @@ -172,6 +172,61 @@ spec: requests: cpu: 150m memory: 64Mi + - args: + - --data-directory + - /var/lib/cincinnati/graph-data/products + - --address + - '::' + - --port + - "8082" + command: + - /usr/bin/products-service + image: image + imagePullPolicy: IfNotPresent + livenessProbe: + failureThreshold: 3 + httpGet: + path: /healthz + port: 8082 + scheme: HTTP + initialDelaySeconds: 5 + periodSeconds: 30 + successThreshold: 1 + timeoutSeconds: 3 + name: products-data + ports: + - containerPort: 8082 + name: products + protocol: TCP + readinessProbe: + failureThreshold: 3 + httpGet: + path: /healthz + port: 8082 + scheme: HTTP + initialDelaySeconds: 3 + periodSeconds: 30 + successThreshold: 1 + timeoutSeconds: 3 + resources: + limits: + cpu: 250m + memory: 128Mi + requests: + cpu: 50m + memory: 32Mi + volumeMounts: + - mountPath: /etc/configs + name: configs + readOnly: true + - mountPath: /var/lib/cincinnati/graph-data + name: cincinnati-graph-data + - mountPath: /var/lib/cincinnati/registry-credentials + name: pull-secret + readOnly: true + - mountPath: /etc/pki/ca-trust/extracted/pem + name: trusted-ca + readOnly: true initContainers: - image: example.com/library/graph-data@sha256:123 imagePullPolicy: Always diff --git a/controllers/updateservice_controller.go b/controllers/updateservice_controller.go index 31c78ecb..7c7515e9 100644 --- a/controllers/updateservice_controller.go +++ b/controllers/updateservice_controller.go @@ -169,6 +169,7 @@ func (r *UpdateServiceReconciler) Reconcile(ctx context.Context, req ctrl.Reques r.ensurePodDisruptionBudget, r.ensurePolicyEngineRoute, r.ensureNetworkPolicy, + r.ensureProductsDataService, } { err = f(ctx, reqLogger, instanceCopy, resources) if err != nil { @@ -884,3 +885,15 @@ func (r *UpdateServiceReconciler) SetupWithManager(mgr ctrl.Manager, namespace s ). Complete(r) } + +func (r *UpdateServiceReconciler) ensureProductsDataService(ctx context.Context, reqLogger logr.Logger, instance *cv1.UpdateService, resources *kubeResources) error { + service := resources.productsService + if err := controllerutil.SetControllerReference(instance, service, r.Scheme); err != nil { + return err + } + if err := r.ensureService(ctx, reqLogger, service); err != nil { + handleErr(reqLogger, &instance.Status, "EnsureServiceFailed", err) + return err + } + return nil +} diff --git a/dev/Dockerfile b/dev/Dockerfile index ce4ee878..43ea15b8 100644 --- a/dev/Dockerfile +++ b/dev/Dockerfile @@ -4,4 +4,8 @@ RUN curl -L -o cincinnati-graph-data.tar.gz https://api.openshift.com/api/upgrad RUN mkdir -p /var/lib/cincinnati-graph-data && tar xvzf cincinnati-graph-data.tar.gz -C /var/lib/cincinnati-graph-data/ --no-overwrite-dir --no-same-owner +RUN curl -L -o products.json https://access.redhat.com/product-life-cycles/api/v2/products || echo "{}" > products.json + +RUN mkdir -p /var/lib/cincinnati-graph-data/products && mv products.json /var/lib/cincinnati-graph-data/products/ || true + CMD ["/bin/bash", "-c" ,"exec cp -rpv /var/lib/cincinnati-graph-data/* /var/lib/cincinnati/graph-data"]