From 9cb5deaf56c95b024e82335dfc5d24680058f353 Mon Sep 17 00:00:00 2001 From: Sebastian Nallar Date: Thu, 2 Oct 2025 18:51:45 -0300 Subject: [PATCH 01/59] [feature]: gateway_type --- .../networking/dns/az-records/manage_route | 21 ++++++++++++++++--- k8s/scope/networking/dns/build_dns_context | 5 +++++ 2 files changed, 23 insertions(+), 3 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index db5d44ab..2ba49ce6 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -52,9 +52,24 @@ for arg in "$@"; do esac done -# Get IP from Gateway resource -GATEWAY_IP=$(kubectl get gateway "$GATEWAY_NAME" -n gateways \ - -o jsonpath='{.status.addresses[?(@.type=="IPAddress")].value}' 2>/dev/null) +# Get IP based on gateway type +if [ "${GATEWAY_TYPE:-istio}" = "aro_cluster" ]; then + # Get IP from OpenShift router service + GATEWAY_IP=$(kubectl get svc router-default -n openshift-ingress \ + -o jsonpath='{.status.loadBalancer.ingress[0].ip}' 2>/dev/null) + + if [ -z "$GATEWAY_IP" ]; then + echo "Error: Could not get IP address from ARO router service" >&2 + echo "Falling back to istio gateway..." >&2 + # Fall back to istio gateway + GATEWAY_IP=$(kubectl get gateway "$GATEWAY_NAME" -n gateways \ + -o jsonpath='{.status.addresses[?(@.type=="IPAddress")].value}' 2>/dev/null) + fi +else + # Default: Get IP from Gateway resource (istio) + GATEWAY_IP=$(kubectl get gateway "$GATEWAY_NAME" -n gateways \ + -o jsonpath='{.status.addresses[?(@.type=="IPAddress")].value}' 2>/dev/null) +fi if [ -z "$GATEWAY_IP" ]; then echo "Error: Could not get IP address for gateway $GATEWAY_NAME" >&2 diff --git a/k8s/scope/networking/dns/build_dns_context b/k8s/scope/networking/dns/build_dns_context index 9df57eb5..5cd476e0 100755 --- a/k8s/scope/networking/dns/build_dns_context +++ b/k8s/scope/networking/dns/build_dns_context @@ -9,8 +9,13 @@ case "$DNS_TYPE" in source "$SERVICE_PATH/scope/networking/dns/get_hosted_zones" ;; azure) + # Set default gateway type to istio if not specified + GATEWAY_TYPE="${GATEWAY_TYPE:-istio}" + export GATEWAY_TYPE + # from values.yaml: HOSTED_ZONE_NAME, HOSTED_ZONE_RG, etc. echo "Azure DNS context ready" + echo "GATEWAY_TYPE: $GATEWAY_TYPE" echo "HOSTED_ZONE_NAME: $HOSTED_ZONE_NAME" echo "HOSTED_ZONE_RG: $HOSTED_ZONE_RG" echo "AZURE_SUBSCRIPTION_ID: $AZURE_SUBSCRIPTION_ID" From c5f44ea32ec5765cf89ef7d966163cc9f8ca7ca0 Mon Sep 17 00:00:00 2001 From: Sebastian Nallar Date: Thu, 2 Oct 2025 18:58:47 -0300 Subject: [PATCH 02/59] aro --- azure-aro/specs/actions/create-scope.json.tpl | 29 + .../specs/actions/delete-deployment.json.tpl | 33 + azure-aro/specs/actions/delete-scope.json.tpl | 29 + .../actions/finalize-blue-green.json.tpl | 33 + .../specs/actions/kill-instances.json.tpl | 18 + .../specs/actions/pause-autoscaling.json.tpl | 19 + azure-aro/specs/actions/restart-pods.json.tpl | 30 + .../specs/actions/resume-autoscaling.json.tpl | 19 + .../actions/rollback-deployment.json.tpl | 33 + .../set-desired-instance-count.json.tpl | 33 + .../specs/actions/start-blue-green.json.tpl | 33 + .../specs/actions/start-initial.json.tpl | 32 + .../specs/actions/switch-traffic.json.tpl | 37 ++ azure-aro/specs/notification-channel.json.tpl | 34 + .../specs/scope-type-definition.json.tpl | 9 + azure-aro/specs/service-spec.json.tpl | 595 ++++++++++++++++++ azure-aro/values.yaml | 9 + .../aro/blue-green-httproute.yaml.tpl | 58 ++ .../templates/aro/initial-httproute.yaml.tpl | 51 ++ 19 files changed, 1134 insertions(+) create mode 100644 azure-aro/specs/actions/create-scope.json.tpl create mode 100644 azure-aro/specs/actions/delete-deployment.json.tpl create mode 100644 azure-aro/specs/actions/delete-scope.json.tpl create mode 100644 azure-aro/specs/actions/finalize-blue-green.json.tpl create mode 100644 azure-aro/specs/actions/kill-instances.json.tpl create mode 100644 azure-aro/specs/actions/pause-autoscaling.json.tpl create mode 100644 azure-aro/specs/actions/restart-pods.json.tpl create mode 100644 azure-aro/specs/actions/resume-autoscaling.json.tpl create mode 100644 azure-aro/specs/actions/rollback-deployment.json.tpl create mode 100644 azure-aro/specs/actions/set-desired-instance-count.json.tpl create mode 100644 azure-aro/specs/actions/start-blue-green.json.tpl create mode 100644 azure-aro/specs/actions/start-initial.json.tpl create mode 100644 azure-aro/specs/actions/switch-traffic.json.tpl create mode 100644 azure-aro/specs/notification-channel.json.tpl create mode 100644 azure-aro/specs/scope-type-definition.json.tpl create mode 100644 azure-aro/specs/service-spec.json.tpl create mode 100644 azure-aro/values.yaml create mode 100644 k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl create mode 100644 k8s/deployment/templates/aro/initial-httproute.yaml.tpl diff --git a/azure-aro/specs/actions/create-scope.json.tpl b/azure-aro/specs/actions/create-scope.json.tpl new file mode 100644 index 00000000..4c0fb3a6 --- /dev/null +++ b/azure-aro/specs/actions/create-scope.json.tpl @@ -0,0 +1,29 @@ +{ + "name": "create-scope", + "slug": "create-scope", + "type": "create", + "retryable": false, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id" + ], + "properties": { + "scope_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/delete-deployment.json.tpl b/azure-aro/specs/actions/delete-deployment.json.tpl new file mode 100644 index 00000000..0334b10c --- /dev/null +++ b/azure-aro/specs/actions/delete-deployment.json.tpl @@ -0,0 +1,33 @@ +{ + "name": "delete-deployment", + "slug": "delete-deployment", + "type": "custom", + "retryable": false, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id", + "deployment_id" + ], + "properties": { + "scope_id": { + "type": "string" + }, + "deployment_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/delete-scope.json.tpl b/azure-aro/specs/actions/delete-scope.json.tpl new file mode 100644 index 00000000..16d9b992 --- /dev/null +++ b/azure-aro/specs/actions/delete-scope.json.tpl @@ -0,0 +1,29 @@ +{ + "name": "delete-scope", + "slug": "delete-scope", + "type": "custom", + "retryable": false, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id" + ], + "properties": { + "scope_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/finalize-blue-green.json.tpl b/azure-aro/specs/actions/finalize-blue-green.json.tpl new file mode 100644 index 00000000..4dc780cb --- /dev/null +++ b/azure-aro/specs/actions/finalize-blue-green.json.tpl @@ -0,0 +1,33 @@ +{ + "name": "finalize-blue-green", + "slug": "finalize-blue-green", + "type": "custom", + "retryable": false, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id", + "deployment_id" + ], + "properties": { + "scope_id": { + "type": "string" + }, + "deployment_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/kill-instances.json.tpl b/azure-aro/specs/actions/kill-instances.json.tpl new file mode 100644 index 00000000..c1351f94 --- /dev/null +++ b/azure-aro/specs/actions/kill-instances.json.tpl @@ -0,0 +1,18 @@ +{ + "name": "Kill instances", + "type": "custom", + "icon": "material-symbols:delete-outline", + "results": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "annotations": { + "show_on": ["performance"], + "runs_over": "scope" + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/pause-autoscaling.json.tpl b/azure-aro/specs/actions/pause-autoscaling.json.tpl new file mode 100644 index 00000000..7d3808fc --- /dev/null +++ b/azure-aro/specs/actions/pause-autoscaling.json.tpl @@ -0,0 +1,19 @@ +{ + "name": "Pause autoscaling", + "type": "custom", + "icon": "material-symbols:pause-circle-outline", + "results": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "annotations": { + "show_on": ["performance"], + "runs_over": "scope" + }, + "enabled_when": ".service.attributes.scaling_type == \"auto\"" +} \ No newline at end of file diff --git a/azure-aro/specs/actions/restart-pods.json.tpl b/azure-aro/specs/actions/restart-pods.json.tpl new file mode 100644 index 00000000..7e285f35 --- /dev/null +++ b/azure-aro/specs/actions/restart-pods.json.tpl @@ -0,0 +1,30 @@ +{ + "name": "Restart pods", + "type": "custom", + "icon": "material-symbols:refresh", + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + }, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + ], + "properties": { + } + }, + "values": {} + }, + "annotations": { + "show_on": [ + "performance" + ], + "runs_over": "scope" + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/resume-autoscaling.json.tpl b/azure-aro/specs/actions/resume-autoscaling.json.tpl new file mode 100644 index 00000000..091f34b0 --- /dev/null +++ b/azure-aro/specs/actions/resume-autoscaling.json.tpl @@ -0,0 +1,19 @@ +{ + "name": "Resume autoscaling", + "type": "custom", + "icon": "material-symbols:play-circle-outline", + "results": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "annotations": { + "show_on": ["performance"], + "runs_over": "scope" + }, + "enabled_when": ".service.attributes.scaling_type == \"auto\"" +} \ No newline at end of file diff --git a/azure-aro/specs/actions/rollback-deployment.json.tpl b/azure-aro/specs/actions/rollback-deployment.json.tpl new file mode 100644 index 00000000..dcbf4cd1 --- /dev/null +++ b/azure-aro/specs/actions/rollback-deployment.json.tpl @@ -0,0 +1,33 @@ +{ + "name": "rollback-deployment", + "slug": "rollback-deployment", + "type": "custom", + "retryable": false, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id", + "deployment_id" + ], + "properties": { + "scope_id": { + "type": "string" + }, + "deployment_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/set-desired-instance-count.json.tpl b/azure-aro/specs/actions/set-desired-instance-count.json.tpl new file mode 100644 index 00000000..a792699b --- /dev/null +++ b/azure-aro/specs/actions/set-desired-instance-count.json.tpl @@ -0,0 +1,33 @@ +{ + "name": "Set desired instance count", + "type": "custom", + "icon": "material-symbols:note-add-outline", + "results": { + "schema": { "type": "object", "required": [], "properties": {} }, + "values": {} + }, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": ["desired_instances"], + "properties": { + "desired_instances": { + "type": "integer", + "title": "Desired Instance Count", + "description": "Set the number of instances you want to run", + "additionalKeywords": { + "default": ".service.attributes.autoscaling.min_replicas // 1", + "maximum": ".service.attributes.autoscaling.max_replicas // 10", + "minimum": ".service.attributes.autoscaling.min_replicas // 1" + } + } + } + }, + "values": {} + }, + "annotations": { + "show_on": ["performance"], + "runs_over": "scope" + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/start-blue-green.json.tpl b/azure-aro/specs/actions/start-blue-green.json.tpl new file mode 100644 index 00000000..a5e387b5 --- /dev/null +++ b/azure-aro/specs/actions/start-blue-green.json.tpl @@ -0,0 +1,33 @@ +{ + "name": "start-blue-green", + "slug": "start-blue-green", + "type": "custom", + "retryable": false, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id", + "deployment_id" + ], + "properties": { + "scope_id": { + "type": "string" + }, + "deployment_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/start-initial.json.tpl b/azure-aro/specs/actions/start-initial.json.tpl new file mode 100644 index 00000000..b00708e0 --- /dev/null +++ b/azure-aro/specs/actions/start-initial.json.tpl @@ -0,0 +1,32 @@ +{ + "name": "start-initial", + "slug": "start-initial", + "type": "custom", + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id", + "deployment_id" + ], + "properties": { + "scope_id": { + "type": "string" + }, + "deployment_id": { + "type": "string" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/actions/switch-traffic.json.tpl b/azure-aro/specs/actions/switch-traffic.json.tpl new file mode 100644 index 00000000..9e853438 --- /dev/null +++ b/azure-aro/specs/actions/switch-traffic.json.tpl @@ -0,0 +1,37 @@ +{ + "name": "switch-traffic", + "slug": "switch-traffic", + "type": "custom", + "retryable": true, + "service_specification_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "parameters": { + "schema": { + "type": "object", + "required": [ + "scope_id", + "deployment_id", + "desired_traffic" + ], + "properties": { + "scope_id": { + "type": "string" + }, + "deployment_id": { + "type": "string" + }, + "desired_traffic": { + "type": "number" + } + } + }, + "values": {} + }, + "results": { + "schema": { + "type": "object", + "required": [], + "properties": {} + }, + "values": {} + } +} \ No newline at end of file diff --git a/azure-aro/specs/notification-channel.json.tpl b/azure-aro/specs/notification-channel.json.tpl new file mode 100644 index 00000000..f1db58e5 --- /dev/null +++ b/azure-aro/specs/notification-channel.json.tpl @@ -0,0 +1,34 @@ +{ + "nrn": "{{ env.Getenv "NRN" }}", + "status": "active", + "type": "agent", + "source": [ + "telemetry", + "service" + ], + "configuration": { + "api_key": "{{ env.Getenv "NP_API_KEY" }}", + "command": { + "data": { + "cmdline": "{{ env.Getenv "REPO_PATH" }}/entrypoint --service-path={{ env.Getenv "REPO_PATH" }}/k8s --overrides-path={{ env.Getenv "REPO_PATH" }}/{{ env.Getenv "SERVICE_PATH" }}", + "environment": { + "NP_ACTION_CONTEXT": "'${NOTIFICATION_CONTEXT}'" + } + }, + "type": "exec" + }, + "selector": { + "environment": "{{ env.Getenv "ENVIRONMENT" }}" + } + }, + "filters": { + "$or": [ + { + "service.specification.slug": "{{ env.Getenv "SERVICE_SLUG" }}" + }, + { + "arguments.scope_provider": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}" + } + ] + } +} \ No newline at end of file diff --git a/azure-aro/specs/scope-type-definition.json.tpl b/azure-aro/specs/scope-type-definition.json.tpl new file mode 100644 index 00000000..9da853fa --- /dev/null +++ b/azure-aro/specs/scope-type-definition.json.tpl @@ -0,0 +1,9 @@ +{ + "description": "Docker containers on pods", + "name": "Containers", + "nrn": "{{ env.Getenv "NRN" }}", + "provider_id": "{{ env.Getenv "SERVICE_SPECIFICATION_ID" }}", + "provider_type": "service", + "status": "active", + "type": "custom" +} \ No newline at end of file diff --git a/azure-aro/specs/service-spec.json.tpl b/azure-aro/specs/service-spec.json.tpl new file mode 100644 index 00000000..c838fd23 --- /dev/null +++ b/azure-aro/specs/service-spec.json.tpl @@ -0,0 +1,595 @@ +{ + "assignable_to": "any", + "attributes": { + "schema":{ + "type":"object", + "required":[ + "ram_memory", + "visibility", + "autoscaling", + "health_check", + "scaling_type", + "cpu_millicores", + "fixed_instances", + "scheduled_stop", + "additional_ports", + "continuous_delivery" + ], + "uiSchema":{ + "type":"VerticalLayout", + "elements":[ + { + "type":"Control", + "label":"RAM Memory", + "scope":"#/properties/ram_memory" + }, + { + "type":"Control", + "label":"Visibility", + "scope":"#/properties/visibility", + "options":{ + "format":"radio" + } + }, + { + "type":"Categorization", + "options":{ + "collapsable":{ + "label":"ADVANCED", + "collapsed":true + } + }, + "elements":[ + { + "type":"Category", + "label":"Processor", + "elements":[ + { + "type":"Control", + "label":"CPU Millicores", + "scope":"#/properties/cpu_millicores" + } + ] + }, + { + "type":"Category", + "label":"Size & Scaling", + "elements":[ + { + "type":"Control", + "scope":"#/properties/scaling_type" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/scaling_type", + "schema":{ + "enum":[ + "fixed" + ] + } + } + }, + "type":"Control", + "scope":"#/properties/fixed_instances" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/scaling_type", + "schema":{ + "enum":[ + "auto" + ] + } + } + }, + "type":"Group", + "label":"Autoscaling Settings", + "elements":[ + { + "type":"Control", + "scope":"#/properties/autoscaling/properties/min_replicas" + }, + { + "type":"Control", + "scope":"#/properties/autoscaling/properties/max_replicas" + }, + { + "type":"Control", + "scope":"#/properties/autoscaling/properties/target_cpu_utilization" + }, + { + "type": "Control", + "scope": "#/properties/autoscaling/properties/target_memory_enabled" + }, + { + "rule": { + "effect": "SHOW", + "condition": { + "scope": "#/properties/autoscaling/properties/target_memory_enabled", + "schema": { + "const": true + } + } + }, + "type": "Control", + "scope": "#/properties/autoscaling/properties/target_memory_utilization" + } + ] + } + ] + }, + { + "type":"Category", + "label":"Additional Ports", + "elements":[ + { + "type":"Control", + "scope":"#/properties/additional_ports", + "options":{ + "detail":{ + "type":"VerticalLayout", + "elements":[ + { + "type":"Control", + "scope":"#/properties/port" + }, + { + "type":"Control", + "scope":"#/properties/type" + } + ] + } + } + } + ] + }, + { + "type":"Category", + "label":"Scheduled Stop", + "elements":[ + { + "type":"Control", + "scope":"#/properties/scheduled_stop/properties/enabled" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/scheduled_stop/properties/enabled", + "schema":{ + "const":true + } + } + }, + "type":"Control", + "scope":"#/properties/scheduled_stop/properties/timer" + } + ] + }, + { + "type":"Category", + "label":"Continuous deployment", + "elements":[ + { + "type":"Control", + "scope":"#/properties/continuous_delivery/properties/enabled" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/continuous_delivery/properties/enabled", + "schema":{ + "const":true + } + } + }, + "type":"Control", + "scope":"#/properties/continuous_delivery/properties/branches" + } + ] + }, + { + "type":"Category", + "label":"Health Check", + "elements":[ + { + "type":"Control", + "scope":"#/properties/health_check/properties/enabled" + }, + { + "rule": { + "effect": "SHOW", + "condition": { + "scope": "#/properties/health_check/properties/enabled", + "schema": { + "const": true + } + } + }, + "type": "Control", + "scope": "#/properties/health_check/properties/type", + "options":{ + "format":"radio" + } + }, + { + "rule": { + "effect": "SHOW", + "condition": { + "type": "AND", + "conditions": [ + { + "scope": "#/properties/health_check/properties/type", + "schema": { + "const": "HTTP" + } + }, + { + "scope": "#/properties/health_check/properties/enabled", + "schema": { + "const": true + } + } + ] + } + }, + "type": "Control", + "scope": "#/properties/health_check/properties/path" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/health_check/properties/enabled", + "schema":{ + "const":true + } + } + }, + "type":"Control", + "scope":"#/properties/health_check/properties/initial_delay_seconds" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/health_check/properties/enabled", + "schema":{ + "const":true + } + } + }, + "type":"Control", + "scope":"#/properties/health_check/properties/period_seconds" + }, + { + "rule":{ + "effect":"SHOW", + "condition":{ + "scope":"#/properties/health_check/properties/enabled", + "schema":{ + "const":true + } + } + }, + "type":"Control", + "scope":"#/properties/health_check/properties/timeout_seconds" + } + ] + } + ] + } + ] + }, + "properties":{ + "asset_type":{ + "type":"string", + "export":false, + "default":"docker-image" + }, + "ram_memory":{ + "type":"integer", + "oneOf":[ + { + "const":64, + "title":"64 MB" + }, + { + "const":128, + "title":"128 MB" + }, + { + "const":256, + "title":"256 MB" + }, + { + "const":512, + "title":"512 MB" + }, + { + "const":1024, + "title":"1 GB" + }, + { + "const":2048, + "title":"2 GB" + }, + { + "const":4096, + "title":"4 GB" + }, + { + "const":8192, + "title":"8 GB" + }, + { + "const":16384, + "title":"16 GB" + } + ], + "title":"RAM Memory", + "default":128, + "description":"Amount of RAM memory to allocate to the container (in MB)" + }, + "visibility":{ + "type":"string", + "oneOf":[ + { + "const":"public", + "title":"Internet", + "description":"Public, reachable by anyone" + }, + { + "const":"internal", + "title":"Main Account", + "description":"Only visible inside your organization" + } + ], + "title":"Visibility", + "default":"public", + "description":"Define whether the scope is publicly accessible or private to your account" + }, + "autoscaling":{ + "type":"object", + "properties":{ + "max_replicas":{ + "type":"integer", + "title":"Maximum Replicas", + "default":5, + "maximum":20, + "minimum":1, + "description":"Maximum number of instances to scale to" + }, + "min_replicas":{ + "type":"integer", + "title":"Minimum Replicas", + "default":1, + "maximum":10, + "minimum":1, + "description":"Minimum number of instances to maintain" + }, + "target_cpu_utilization":{ + "type":"integer", + "title":"Target CPU Utilization (%)", + "default":70, + "maximum":90, + "minimum":50, + "description":"CPU utilization threshold that triggers scaling" + }, + "target_memory_enabled": { + "type": "boolean", + "title": "Scale by memory", + "default": false + }, + "target_memory_utilization": { + "type": "integer", + "title": "Target memory utilization (%)", + "default": 70, + "maximum": 90, + "minimum": 30, + "description": "Memory utilization threshold that triggers scaling" + } + } + }, + "health_check":{ + "type":"object", + "properties":{ + "path":{ + "type":"string", + "title":"Health Check Path", + "default":"/health", + "description":"HTTP path for health check requests" + }, + "enabled":{ + "type":"boolean", + "title":"Enable Health Check", + "default":true + }, + "period_seconds":{ + "type":"integer", + "title":"Check Interval", + "default":10, + "maximum":300, + "minimum":1, + "description":"Seconds between health checks" + }, + "timeout_seconds":{ + "type":"integer", + "title":"Timeout", + "default":5, + "maximum":60, + "minimum":1, + "description":"Seconds to wait for a health check response" + }, + "initial_delay_seconds":{ + "type":"integer", + "title":"Initial Delay", + "default":30, + "maximum":300, + "minimum":0, + "description":"Seconds to wait before starting health checks" + }, + "type": { + "type": "string", + "title": "Health check type", + "default": "HTTP", + "enum": [ + "HTTP", + "TCP" + ], + "description": "To be applied in startup, readiness and liveness probes" + } + } + }, + "scaling_type":{ + "enum":[ + "fixed", + "auto" + ], + "type":"string", + "title":"Scaling Type", + "default":"fixed", + "description":"Choose between fixed number of instances or automatic scaling" + }, + "cpu_millicores":{ + "type":"integer", + "title":"CPU Millicores", + "default":500, + "maximum":4000, + "minimum":100, + "description":"Amount of CPU to allocate (in millicores, 1000m = 1 CPU core)" + }, + "scheduled_stop":{ + "type":"object", + "title":"Scheduled Stop", + "required":[ + "enabled", + "timer" + ], + "properties":{ + "timer":{ + "type":"string", + "oneOf":[ + { + "const":"3600", + "title":"1 hour" + }, + { + "const":"10800", + "title":"3 hours" + }, + { + "const":"21600", + "title":"6 hours" + }, + { + "const":"43200", + "title":"12 hours" + }, + { + "const":"tonight", + "title":"Tonight" + } + ], + "title":"Stop After", + "default":"3600", + "description":"When to automatically stop the service" + }, + "enabled":{ + "type":"boolean", + "title":"Enable Scheduled Stop", + "default":false, + "description":"Automatically stop the service after a specified time" + } + }, + "description":"Configure automatic stopping of the service" + }, + "fixed_instances":{ + "type":"integer", + "title":"Number of Instances", + "default":1, + "maximum":10, + "minimum":1, + "description":"Fixed number of instances to run" + }, + "additional_ports":{ + "type":"array", + "items":{ + "type":"object", + "required":[ + "port", + "type" + ], + "properties":{ + "port":{ + "type":"integer", + "title":"Port Number", + "maximum":65535, + "minimum":1024, + "description":"The port number to expose (1024-65535)" + }, + "type":{ + "enum":[ + "GRPC" + ], + "type":"string", + "title":"Port Type", + "description":"The protocol type for this port" + } + } + }, + "title":"Additional Ports", + "default":[ + + ], + "description":"Configure additional ports for your application" + }, + "continuous_delivery":{ + "type":"object", + "title":"Continuous Delivery", + "required":[ + "enabled", + "branches" + ], + "properties":{ + "enabled":{ + "type":"boolean", + "title":"Enable Continuous Delivery", + "default":false, + "description":"Automatically deploy new versions from specified branches" + }, + "branches":{ + "type":"array", + "items":{ + "type":"string" + }, + "title":"Branches", + "default":[ + "main" + ], + "description":"Git branches to monitor for automatic deployment" + } + }, + "description":"Configure automatic deployment from Git branches" + } + } + } + }, + "name": "Containers", + "selectors": { + "category": "any", + "imported": false, + "provider": "any", + "sub_category": "any" + }, + "type": "scope", + "use_default_actions": false, + "visible_to": [ + "{{ env.Getenv "NRN" }}" + ] +} diff --git a/azure-aro/values.yaml b/azure-aro/values.yaml new file mode 100644 index 00000000..c55ffe7c --- /dev/null +++ b/azure-aro/values.yaml @@ -0,0 +1,9 @@ +configuration: + DNS_TYPE: azure + USE_ACCOUNT_SLUG: false + IMAGE_PULL_SECRETS: + ENABLED: false + DOMAIN: $OVERRIDE_DOMAIN + SERVICE_TEMPLATE: "$SERVICE_PATH/deployment/templates/istio/service.yaml.tpl" + INITIAL_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/initial-httproute.yaml.tpl" + BLUE_GREEN_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/blue-green-httproute.yaml.tpl" diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl new file mode 100644 index 00000000..9c44ead9 --- /dev/null +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -0,0 +1,58 @@ +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: aro-payments-route-bg-{{ .scope.slug }}-{{ .scope.id }} + namespace: {{ .k8s_namespace }} + labels: + nullplatform: "true" + account: {{ .account.slug }} + account_id: "{{ .account.id }}" + namespace: {{ .namespace.slug }} + namespace_id: "{{ .namespace.id }}" + application: {{ .application.slug }} + application_id: "{{ .application.id }}" + scope: {{ .scope.slug }} + scope_id: "{{ .scope.id }}" + deployment-strategy: "blue-green" +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} + {{- $labels := index $global "labels" }} + {{- if $labels }} +{{ data.ToYAML $labels | indent 4 }} + {{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} + {{- $labels := index $ingress "labels" }} + {{- if $labels }} +{{ data.ToYAML $labels | indent 4 }} + {{- end }} +{{- end }} + annotations: + route.openshift.io/deployment-strategy: "blue-green" +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} + {{- $annotations := index $global "annotations" }} + {{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} + {{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} + {{- $annotations := index $ingress "annotations" }} + {{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} + {{- end }} +{{- end }} +spec: + host: {{ .scope.domain }} + to: + kind: Service + name: d-{{ .scope.id }}-{{ .blue_deployment_id }} + weight: {{ sub 100 .deployment.strategy_data.desired_switched_traffic }} + port: + targetPort: 8080 + alternateBackends: + - kind: Service + name: d-{{ .scope.id }}-{{ .deployment.id }} + weight: {{ .deployment.strategy_data.desired_switched_traffic }} \ No newline at end of file diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl new file mode 100644 index 00000000..834b7c4b --- /dev/null +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -0,0 +1,51 @@ +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: aro-payments-route-{{ .scope.slug }}-{{ .scope.id }} + namespace: {{ .k8s_namespace }} + labels: + nullplatform: "true" + account: {{ .account.slug }} + account_id: "{{ .account.id }}" + namespace: {{ .namespace.slug }} + namespace_id: "{{ .namespace.id }}" + application: {{ .application.slug }} + application_id: "{{ .application.id }}" + scope: {{ .scope.slug }} + scope_id: "{{ .scope.id }}" +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} + {{- $labels := index $global "labels" }} + {{- if $labels }} +{{ data.ToYAML $labels | indent 4 }} + {{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} + {{- $labels := index $ingress "labels" }} + {{- if $labels }} +{{ data.ToYAML $labels | indent 4 }} + {{- end }} +{{- end }} + annotations: +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} + {{- $annotations := index $global "annotations" }} + {{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} + {{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} + {{- $annotations := index $ingress "annotations" }} + {{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} + {{- end }} +{{- end }} +spec: + host: {{ .scope.domain }} + to: + kind: Service + name: d-{{ .scope.id }}-{{ .deployment.id }} + port: + targetPort: 8080 \ No newline at end of file From 9b7dde832216a2e89d3230cc2983eb7c24bb74c1 Mon Sep 17 00:00:00 2001 From: Sebastian Nallar Date: Thu, 2 Oct 2025 19:02:35 -0300 Subject: [PATCH 03/59] aro --- azure-aro/values.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/azure-aro/values.yaml b/azure-aro/values.yaml index c55ffe7c..7ff585b6 100644 --- a/azure-aro/values.yaml +++ b/azure-aro/values.yaml @@ -7,3 +7,4 @@ configuration: SERVICE_TEMPLATE: "$SERVICE_PATH/deployment/templates/istio/service.yaml.tpl" INITIAL_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/initial-httproute.yaml.tpl" BLUE_GREEN_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/blue-green-httproute.yaml.tpl" + GATEWAY_TYPE: aro_cluster \ No newline at end of file From 78ea065d9ec6054b696acb72fa7c91dc765c563b Mon Sep 17 00:00:00 2001 From: Sebastian Nallar Date: Thu, 2 Oct 2025 19:07:46 -0300 Subject: [PATCH 04/59] aro --- k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl | 4 ++-- k8s/deployment/templates/aro/initial-httproute.yaml.tpl | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index 9c44ead9..cc1c9aa3 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -1,7 +1,7 @@ apiVersion: route.openshift.io/v1 kind: Route metadata: - name: aro-payments-route-bg-{{ .scope.slug }}-{{ .scope.id }} + name: k-8-s-{{ .scope.slug }}-{{ .scope.id }}-{{ .ingress_visibility }} namespace: {{ .k8s_namespace }} labels: nullplatform: "true" @@ -51,7 +51,7 @@ spec: name: d-{{ .scope.id }}-{{ .blue_deployment_id }} weight: {{ sub 100 .deployment.strategy_data.desired_switched_traffic }} port: - targetPort: 8080 + targetPort: 80 alternateBackends: - kind: Service name: d-{{ .scope.id }}-{{ .deployment.id }} diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index 834b7c4b..5f13b77e 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -1,7 +1,7 @@ apiVersion: route.openshift.io/v1 kind: Route metadata: - name: aro-payments-route-{{ .scope.slug }}-{{ .scope.id }} + name: k-8-s-{{ .scope.slug }}-{{ .scope.id }}-{{ .ingress_visibility }} namespace: {{ .k8s_namespace }} labels: nullplatform: "true" @@ -48,4 +48,4 @@ spec: kind: Service name: d-{{ .scope.id }}-{{ .deployment.id }} port: - targetPort: 8080 \ No newline at end of file + targetPort: 80 \ No newline at end of file From eb2d540cf2de823ea45e1ac0f2b24379ab1a7d21 Mon Sep 17 00:00:00 2001 From: Javi Date: Thu, 30 Oct 2025 16:17:45 -0300 Subject: [PATCH 05/59] feat: update httroutes to do tls termination --- azure-aro/values.yaml | 3 ++- .../templates/aro/blue-green-httproute.yaml.tpl | 8 ++++++-- .../templates/aro/initial-httproute.yaml.tpl | 10 +++++++--- k8s/scope/networking/dns/az-records/manage_route | 2 +- 4 files changed, 16 insertions(+), 7 deletions(-) diff --git a/azure-aro/values.yaml b/azure-aro/values.yaml index 7ff585b6..943edcbe 100644 --- a/azure-aro/values.yaml +++ b/azure-aro/values.yaml @@ -7,4 +7,5 @@ configuration: SERVICE_TEMPLATE: "$SERVICE_PATH/deployment/templates/istio/service.yaml.tpl" INITIAL_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/initial-httproute.yaml.tpl" BLUE_GREEN_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/blue-green-httproute.yaml.tpl" - GATEWAY_TYPE: aro_cluster \ No newline at end of file + GATEWAY_TYPE: aro_cluster + CUSTOM_INGRESS_CONTROLLER: router-custom-domain \ No newline at end of file diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index cc1c9aa3..7d4b6292 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -46,12 +46,16 @@ metadata: {{- end }} spec: host: {{ .scope.domain }} + port: + targetPort: 80 + tls: + insecureEdgeTerminationPolicy: Redirect + termination: edge + wildcardPolicy: None to: kind: Service name: d-{{ .scope.id }}-{{ .blue_deployment_id }} weight: {{ sub 100 .deployment.strategy_data.desired_switched_traffic }} - port: - targetPort: 80 alternateBackends: - kind: Service name: d-{{ .scope.id }}-{{ .deployment.id }} diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index 5f13b77e..7ba14085 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -44,8 +44,12 @@ metadata: {{- end }} spec: host: {{ .scope.domain }} + port: + targetPort: 80 + tls: + insecureEdgeTerminationPolicy: Redirect + termination: edge + wildcardPolicy: None to: kind: Service - name: d-{{ .scope.id }}-{{ .deployment.id }} - port: - targetPort: 80 \ No newline at end of file + name: d-{{ .scope.id }}-{{ .deployment.id }} \ No newline at end of file diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 2ba49ce6..bce9a899 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -55,7 +55,7 @@ done # Get IP based on gateway type if [ "${GATEWAY_TYPE:-istio}" = "aro_cluster" ]; then # Get IP from OpenShift router service - GATEWAY_IP=$(kubectl get svc router-default -n openshift-ingress \ + GATEWAY_IP=$(kubectl get svc "${CUSTOM_INGRESS_CONTROLLER:-router-default}" -n openshift-ingress \ -o jsonpath='{.status.loadBalancer.ingress[0].ip}' 2>/dev/null) if [ -z "$GATEWAY_IP" ]; then From 2134de1971144c0db18597c0f500d731d3787b01 Mon Sep 17 00:00:00 2001 From: Javi Date: Thu, 30 Oct 2025 17:24:10 -0300 Subject: [PATCH 06/59] feat: update httroutes to do tls termination --- k8s/scope/networking/dns/manage_dns | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index f5fd1202..caadca46 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -26,6 +26,11 @@ case "$DNS_TYPE" in else GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" fi + + echo "Using Azure DNS" + echo "> gateway name: $GATEWAY_NAME" + echo "> hosted zone name: $HOSTED_ZONE_NAME" + echo "> hosted zone resource group: $HOSTED_ZONE_RG" source "$SERVICE_PATH/scope/networking/dns/az-records/manage_route" \ --action="$ACTION" \ From b9788de33ad0f9708d69723e6141df1f9521a87b Mon Sep 17 00:00:00 2001 From: Javi Date: Thu, 30 Oct 2025 17:53:22 -0300 Subject: [PATCH 07/59] feat: update httroutes to do tls termination --- k8s/scope/networking/dns/build_dns_context | 4 ++-- k8s/scope/networking/dns/manage_dns | 3 --- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/k8s/scope/networking/dns/build_dns_context b/k8s/scope/networking/dns/build_dns_context index 5cd476e0..3bf341af 100755 --- a/k8s/scope/networking/dns/build_dns_context +++ b/k8s/scope/networking/dns/build_dns_context @@ -20,8 +20,8 @@ case "$DNS_TYPE" in echo "HOSTED_ZONE_RG: $HOSTED_ZONE_RG" echo "AZURE_SUBSCRIPTION_ID: $AZURE_SUBSCRIPTION_ID" echo "RESOURCE_GROUP: $RESOURCE_GROUP" - echo "PUBLIC_GATEWAY_NAME: $PUBLIC_GATEWAY_NAME" - echo "PRIVATE_GATEWAY_NAME: $PRIVATE_GATEWAY_NAME" + # echo "PUBLIC_GATEWAY_NAME: $PUBLIC_GATEWAY_NAME" + # echo "PRIVATE_GATEWAY_NAME: $PRIVATE_GATEWAY_NAME" ;; external_dns) echo "external_dns context ready" diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index caadca46..7e55a3b5 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -28,9 +28,6 @@ case "$DNS_TYPE" in fi echo "Using Azure DNS" - echo "> gateway name: $GATEWAY_NAME" - echo "> hosted zone name: $HOSTED_ZONE_NAME" - echo "> hosted zone resource group: $HOSTED_ZONE_RG" source "$SERVICE_PATH/scope/networking/dns/az-records/manage_route" \ --action="$ACTION" \ From 167ed88d8fb5950efbafe7a8ba8b353504f066a0 Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 09:42:56 -0300 Subject: [PATCH 08/59] feat: add custom-domain label --- k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl | 1 + k8s/deployment/templates/aro/initial-httproute.yaml.tpl | 1 + 2 files changed, 2 insertions(+) diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index 7d4b6292..d209bcaf 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -14,6 +14,7 @@ metadata: scope: {{ .scope.slug }} scope_id: "{{ .scope.id }}" deployment-strategy: "blue-green" + type: custom-domain {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $labels := index $global "labels" }} diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index 7ba14085..7885142e 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -13,6 +13,7 @@ metadata: application_id: "{{ .application.id }}" scope: {{ .scope.slug }} scope_id: "{{ .scope.id }}" + type: custom-domain {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $labels := index $global "labels" }} From fd14b3c42520076dd891de5540a83ee80dcca0ea Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 14:46:14 -0300 Subject: [PATCH 09/59] feat: add private hosted zones support --- k8s/scope/networking/dns/manage_dns | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index 7e55a3b5..70740637 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -23,8 +23,12 @@ case "$DNS_TYPE" in azure) if [ "$SCOPE_VISIBILITY" = "public" ]; then GATEWAY_NAME="$PUBLIC_GATEWAY_NAME" + HOSTED_ZONE_NAME="$PUBLIC_HOSTED_ZONE_NAME" + HOSTED_ZONE_RG="$PUBLIC_HOSTED_ZONE_RG" else GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" + HOSTED_ZONE_NAME="$PRIVATE_HOSTED_ZONE_NAME" + HOSTED_ZONE_RG="$PRIVATE_HOSTED_ZONE_RG" fi echo "Using Azure DNS" From 3a4ef9327608d7ea608d94249ce2a6b38b879043 Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 14:59:15 -0300 Subject: [PATCH 10/59] feat: add private hosted zones support --- k8s/scope/networking/dns/build_dns_context | 10 ---------- 1 file changed, 10 deletions(-) diff --git a/k8s/scope/networking/dns/build_dns_context b/k8s/scope/networking/dns/build_dns_context index 3bf341af..fc189b75 100755 --- a/k8s/scope/networking/dns/build_dns_context +++ b/k8s/scope/networking/dns/build_dns_context @@ -12,16 +12,6 @@ case "$DNS_TYPE" in # Set default gateway type to istio if not specified GATEWAY_TYPE="${GATEWAY_TYPE:-istio}" export GATEWAY_TYPE - - # from values.yaml: HOSTED_ZONE_NAME, HOSTED_ZONE_RG, etc. - echo "Azure DNS context ready" - echo "GATEWAY_TYPE: $GATEWAY_TYPE" - echo "HOSTED_ZONE_NAME: $HOSTED_ZONE_NAME" - echo "HOSTED_ZONE_RG: $HOSTED_ZONE_RG" - echo "AZURE_SUBSCRIPTION_ID: $AZURE_SUBSCRIPTION_ID" - echo "RESOURCE_GROUP: $RESOURCE_GROUP" - # echo "PUBLIC_GATEWAY_NAME: $PUBLIC_GATEWAY_NAME" - # echo "PRIVATE_GATEWAY_NAME: $PRIVATE_GATEWAY_NAME" ;; external_dns) echo "external_dns context ready" From 8fe821b65603a7c423733af74dae8aa414fa7dc8 Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 15:06:29 -0300 Subject: [PATCH 11/59] feat: add private hosted zones support --- k8s/scope/networking/dns/domain/generate_domain | 1 + 1 file changed, 1 insertion(+) diff --git a/k8s/scope/networking/dns/domain/generate_domain b/k8s/scope/networking/dns/domain/generate_domain index ccb2a3b5..32745462 100755 --- a/k8s/scope/networking/dns/domain/generate_domain +++ b/k8s/scope/networking/dns/domain/generate_domain @@ -15,6 +15,7 @@ SCOPE_DOMAIN=$("$SERVICE_PATH/scope/networking/dns/domain/domain-generate" \ --domain="$DOMAIN" \ --useAccountSlug="$USE_ACCOUNT_SLUG") +echo "Domain: $DOMAIN" echo "Generated domain: $SCOPE_DOMAIN" np scope patch --id "$SCOPE_ID" --body "{\"domain\":\"$SCOPE_DOMAIN\"}" From 674fab77e8fd94529bbfb447220ce734f04a0c0b Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 15:12:06 -0300 Subject: [PATCH 12/59] feat: add private hosted zones support --- k8s/scope/networking/dns/az-records/manage_route | 2 ++ k8s/scope/networking/dns/manage_dns | 2 ++ 2 files changed, 4 insertions(+) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 5807dba3..0a52e819 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -81,6 +81,8 @@ if [ -z "$SCOPE_SUBDOMAIN" ]; then SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" fi +echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP" + if [ "$ACTION" = "CREATE" ]; then # Get access token ACCESS_TOKEN=$(get_azure_token) || exit 1 diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index 70740637..a0a29a25 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -32,6 +32,8 @@ case "$DNS_TYPE" in fi echo "Using Azure DNS" + echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" + echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" source "$SERVICE_PATH/scope/networking/dns/az-records/manage_route" \ --action="$ACTION" \ From 733c545561e6b22b546c81cc61d57ef68d0aef17 Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 15:20:02 -0300 Subject: [PATCH 13/59] feat: add private hosted zones support --- k8s/scope/networking/dns/domain/generate_domain | 1 + 1 file changed, 1 insertion(+) diff --git a/k8s/scope/networking/dns/domain/generate_domain b/k8s/scope/networking/dns/domain/generate_domain index 32745462..5a0aedc4 100755 --- a/k8s/scope/networking/dns/domain/generate_domain +++ b/k8s/scope/networking/dns/domain/generate_domain @@ -15,6 +15,7 @@ SCOPE_DOMAIN=$("$SERVICE_PATH/scope/networking/dns/domain/domain-generate" \ --domain="$DOMAIN" \ --useAccountSlug="$USE_ACCOUNT_SLUG") +echo "Context: $CONTEXT" echo "Domain: $DOMAIN" echo "Generated domain: $SCOPE_DOMAIN" From 8fe47282301f9bc8acfbe20dae36d8a79760f616 Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 16:02:43 -0300 Subject: [PATCH 14/59] feat: use azure dns providers keys --- k8s/scope/build_context | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/scope/build_context b/k8s/scope/build_context index 08018b9b..278e1a5d 100755 --- a/k8s/scope/build_context +++ b/k8s/scope/build_context @@ -14,11 +14,11 @@ SCOPE_VISIBILITY=$(echo "$CONTEXT" | jq -r '.scope.capabilities.visibility') if [ "$SCOPE_VISIBILITY" = "public" ]; then DOMAIN=$(echo "$CONTEXT" | jq -r --arg default "$DOMAIN" ' - .providers["cloud-providers"].networking.domain_name // $default + .providers["cloud-providers"].public_dns_zone_name // .providers["cloud-providers"].networking.domain_name // $default ') else DOMAIN=$(echo "$CONTEXT" | jq -r --arg private_default "$PRIVATE_DOMAIN" --arg default "$DOMAIN" ' - (.providers["cloud-providers"].networking.private_domain_name // $private_default | if . == "" then empty else . end) // .providers["cloud-providers"].networking.domain_name // $default + (.providers["cloud-providers"].networking.private_domain_name // .providers["cloud-providers"].networking.private_dns_zone_name // $private_default | if . == "" then empty else . end) // .providers["cloud-providers"].networking.domain_name // $default ') fi SCOPE_DOMAIN=$(echo "$CONTEXT" | jq .scope.domain -r) From 50134bb7787675da5047b880ee3ea4b57e7980ef Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 16:11:21 -0300 Subject: [PATCH 15/59] feat: use azure dns providers keys --- k8s/scope/networking/dns/az-records/manage_route | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 0a52e819..320d6a56 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -76,10 +76,7 @@ if [ -z "$GATEWAY_IP" ]; then exit 1 fi -SCOPE_SUBDOMAIN="${SCOPE_SUBDOMAIN:-}" -if [ -z "$SCOPE_SUBDOMAIN" ]; then - SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" -fi +SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP" From ebe49fb79174a680024bcb80583b4fd7c667fe6c Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 16:43:38 -0300 Subject: [PATCH 16/59] feat: use azure dns providers keys --- .../networking/dns/az-records/manage_route | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 320d6a56..c2e31186 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -76,16 +76,22 @@ if [ -z "$GATEWAY_IP" ]; then exit 1 fi -SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" +SCOPE_SUBDOMAIN="${SCOPE_SUBDOMAIN:-}" +if [ -z "$SCOPE_SUBDOMAIN" ]; then + SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" -echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP" +echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, SCOPE_VISIBILITY = $SCOPE_VISIBILITY" if [ "$ACTION" = "CREATE" ]; then # Get access token ACCESS_TOKEN=$(get_azure_token) || exit 1 - # Create or update A record - RECORD_SET_URL="https://management.azure.com/subscriptions/${AZURE_SUBSCRIPTION_ID}/resourceGroups/${HOSTED_ZONE_RG}/providers/Microsoft.Network/dnsZones/${HOSTED_ZONE_NAME}/A/${SCOPE_SUBDOMAIN}?api-version=2018-05-01" + if [ "$SCOPE_VISIBILITY" = "public" ]; then + zone_path="dnsZones" + else + zone_path="privateDnsZones" + fi + RECORD_SET_URL="https://management.azure.com/subscriptions/${AZURE_SUBSCRIPTION_ID}/resourceGroups/${HOSTED_ZONE_RG}/providers/Microsoft.Network/${zone_path}/${HOSTED_ZONE_NAME}/A/${SCOPE_SUBDOMAIN}?api-version=2018-09-01" RECORD_BODY=$(cat < Date: Fri, 31 Oct 2025 16:48:21 -0300 Subject: [PATCH 17/59] feat: use azure dns providers keys --- k8s/scope/networking/dns/az-records/manage_route | 1 + 1 file changed, 1 insertion(+) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index c2e31186..d51f8fdc 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -79,6 +79,7 @@ fi SCOPE_SUBDOMAIN="${SCOPE_SUBDOMAIN:-}" if [ -z "$SCOPE_SUBDOMAIN" ]; then SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" +fi echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, SCOPE_VISIBILITY = $SCOPE_VISIBILITY" From 0683bc3a0b9f671930693591b1d9db75f5e74ecc Mon Sep 17 00:00:00 2001 From: Javi Date: Fri, 31 Oct 2025 16:54:06 -0300 Subject: [PATCH 18/59] feat: use azure dns providers keys --- k8s/scope/networking/dns/az-records/manage_route | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index d51f8fdc..f45a862c 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -89,10 +89,12 @@ if [ "$ACTION" = "CREATE" ]; then if [ "$SCOPE_VISIBILITY" = "public" ]; then zone_path="dnsZones" + api_version="2018-05-01" else zone_path="privateDnsZones" + api_version="2018-09-01" fi - RECORD_SET_URL="https://management.azure.com/subscriptions/${AZURE_SUBSCRIPTION_ID}/resourceGroups/${HOSTED_ZONE_RG}/providers/Microsoft.Network/${zone_path}/${HOSTED_ZONE_NAME}/A/${SCOPE_SUBDOMAIN}?api-version=2018-09-01" + RECORD_SET_URL="https://management.azure.com/subscriptions/${AZURE_SUBSCRIPTION_ID}/resourceGroups/${HOSTED_ZONE_RG}/providers/Microsoft.Network/${zone_path}/${HOSTED_ZONE_NAME}/A/${SCOPE_SUBDOMAIN}?api-version=${api_version}" RECORD_BODY=$(cat < Date: Fri, 31 Oct 2025 17:00:54 -0300 Subject: [PATCH 19/59] feat: use azure dns providers keys --- k8s/scope/build_context | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/k8s/scope/build_context b/k8s/scope/build_context index 278e1a5d..ffed13fb 100755 --- a/k8s/scope/build_context +++ b/k8s/scope/build_context @@ -14,7 +14,7 @@ SCOPE_VISIBILITY=$(echo "$CONTEXT" | jq -r '.scope.capabilities.visibility') if [ "$SCOPE_VISIBILITY" = "public" ]; then DOMAIN=$(echo "$CONTEXT" | jq -r --arg default "$DOMAIN" ' - .providers["cloud-providers"].public_dns_zone_name // .providers["cloud-providers"].networking.domain_name // $default + .providers["cloud-providers"].networking.public_dns_zone_name // .providers["cloud-providers"].networking.domain_name // $default ') else DOMAIN=$(echo "$CONTEXT" | jq -r --arg private_default "$PRIVATE_DOMAIN" --arg default "$DOMAIN" ' From f1b284e20e8b92deaaa195e1678dfe39fac84f1a Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 3 Nov 2025 10:57:07 -0300 Subject: [PATCH 20/59] fix: private dns recordset --- .../networking/dns/az-records/manage_route | 26 ++++++++++++++----- 1 file changed, 20 insertions(+), 6 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index f45a862c..7ae7dc00 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -90,17 +90,29 @@ if [ "$ACTION" = "CREATE" ]; then if [ "$SCOPE_VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" + # Public DNS zone uses uppercase TTL and ARecords + RECORD_BODY=$(cat < Date: Mon, 3 Nov 2025 11:36:59 -0300 Subject: [PATCH 21/59] fix: use gateway name --- k8s/scope/networking/dns/az-records/manage_route | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 7ae7dc00..a9a6f5be 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -55,7 +55,7 @@ done # Get IP based on gateway type if [ "${GATEWAY_TYPE:-istio}" = "aro_cluster" ]; then # Get IP from OpenShift router service - GATEWAY_IP=$(kubectl get svc "${CUSTOM_INGRESS_CONTROLLER:-router-default}" -n openshift-ingress \ + GATEWAY_IP=$(kubectl get svc "$GATEWAY_NAME" -n openshift-ingress-operator \ -o jsonpath='{.status.loadBalancer.ingress[0].ip}' 2>/dev/null) if [ -z "$GATEWAY_IP" ]; then From 976c687f6c8186255577fd4bf86c64d950271c73 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 3 Nov 2025 11:46:24 -0300 Subject: [PATCH 22/59] fix: polish code --- azure-aro/values.yaml | 3 +-- k8s/scope/networking/dns/build_dns_context | 3 +++ k8s/scope/networking/dns/domain/generate_domain | 2 -- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/azure-aro/values.yaml b/azure-aro/values.yaml index 943edcbe..7ff585b6 100644 --- a/azure-aro/values.yaml +++ b/azure-aro/values.yaml @@ -7,5 +7,4 @@ configuration: SERVICE_TEMPLATE: "$SERVICE_PATH/deployment/templates/istio/service.yaml.tpl" INITIAL_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/initial-httproute.yaml.tpl" BLUE_GREEN_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/blue-green-httproute.yaml.tpl" - GATEWAY_TYPE: aro_cluster - CUSTOM_INGRESS_CONTROLLER: router-custom-domain \ No newline at end of file + GATEWAY_TYPE: aro_cluster \ No newline at end of file diff --git a/k8s/scope/networking/dns/build_dns_context b/k8s/scope/networking/dns/build_dns_context index fc189b75..88a06b68 100755 --- a/k8s/scope/networking/dns/build_dns_context +++ b/k8s/scope/networking/dns/build_dns_context @@ -12,6 +12,9 @@ case "$DNS_TYPE" in # Set default gateway type to istio if not specified GATEWAY_TYPE="${GATEWAY_TYPE:-istio}" export GATEWAY_TYPE + + echo "Azure DNS context ready" + echo "GATEWAY_TYPE: $GATEWAY_TYPE" ;; external_dns) echo "external_dns context ready" diff --git a/k8s/scope/networking/dns/domain/generate_domain b/k8s/scope/networking/dns/domain/generate_domain index 5a0aedc4..ccb2a3b5 100755 --- a/k8s/scope/networking/dns/domain/generate_domain +++ b/k8s/scope/networking/dns/domain/generate_domain @@ -15,8 +15,6 @@ SCOPE_DOMAIN=$("$SERVICE_PATH/scope/networking/dns/domain/domain-generate" \ --domain="$DOMAIN" \ --useAccountSlug="$USE_ACCOUNT_SLUG") -echo "Context: $CONTEXT" -echo "Domain: $DOMAIN" echo "Generated domain: $SCOPE_DOMAIN" np scope patch --id "$SCOPE_ID" --body "{\"domain\":\"$SCOPE_DOMAIN\"}" From 8769b4297a1f5d5f344e4e60b15f000f3c1f52ff Mon Sep 17 00:00:00 2001 From: Javi Date: Tue, 4 Nov 2025 15:16:46 -0300 Subject: [PATCH 23/59] fix: add route labels --- k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl | 2 +- k8s/deployment/templates/aro/initial-httproute.yaml.tpl | 2 +- k8s/scope/networking/dns/az-records/manage_route | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index d209bcaf..650b5221 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -14,7 +14,7 @@ metadata: scope: {{ .scope.slug }} scope_id: "{{ .scope.id }}" deployment-strategy: "blue-green" - type: custom-domain + type: {{ .ingress_visibility }} {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $labels := index $global "labels" }} diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index 7885142e..67e20ba0 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -13,7 +13,7 @@ metadata: application_id: "{{ .application.id }}" scope: {{ .scope.slug }} scope_id: "{{ .scope.id }}" - type: custom-domain + type: {{ .ingress_visibility }} {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $labels := index $global "labels" }} diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index a9a6f5be..7a697bf8 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -55,7 +55,7 @@ done # Get IP based on gateway type if [ "${GATEWAY_TYPE:-istio}" = "aro_cluster" ]; then # Get IP from OpenShift router service - GATEWAY_IP=$(kubectl get svc "$GATEWAY_NAME" -n openshift-ingress-operator \ + GATEWAY_IP=$(kubectl get svc "$GATEWAY_NAME" -n openshift-ingress \ -o jsonpath='{.status.loadBalancer.ingress[0].ip}' 2>/dev/null) if [ -z "$GATEWAY_IP" ]; then From 9a58f9af9d65152ac79b3f424d3a9b04cd01eb3a Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Tue, 4 Nov 2025 18:59:13 -0300 Subject: [PATCH 24/59] correctly extract hosted zones from azure configuration --- k8s/scope/networking/dns/get_hosted_zones | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/scope/networking/dns/get_hosted_zones b/k8s/scope/networking/dns/get_hosted_zones index 019707a9..3884efea 100755 --- a/k8s/scope/networking/dns/get_hosted_zones +++ b/k8s/scope/networking/dns/get_hosted_zones @@ -1,8 +1,8 @@ #!/bin/bash echo "Getting hosted zones" -HOSTED_PUBLIC_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_public_zone_id') -HOSTED_PRIVATE_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_zone_id') +HOSTED_PUBLIC_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_public_zone_id // .providers["cloud-providers"].networking.public_dns_zone_name') +HOSTED_PRIVATE_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_zone_id // .providers["cloud-providers"].networking.private_dns_zone_name') echo "Public Hosted Zone ID: $HOSTED_PUBLIC_ZONE_ID" echo "Private Hosted Zone ID: $HOSTED_PRIVATE_ZONE_ID" From 0d0a4874d5ffcd5f8088de3235349c3743aa52c4 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Tue, 4 Nov 2025 19:34:29 -0300 Subject: [PATCH 25/59] read azure dns configuration from providers --- k8s/scope/networking/dns/get_hosted_zones | 4 ++-- k8s/scope/networking/dns/manage_dns | 28 +++++++++++++++++------ 2 files changed, 23 insertions(+), 9 deletions(-) diff --git a/k8s/scope/networking/dns/get_hosted_zones b/k8s/scope/networking/dns/get_hosted_zones index 3884efea..5e9a7c02 100755 --- a/k8s/scope/networking/dns/get_hosted_zones +++ b/k8s/scope/networking/dns/get_hosted_zones @@ -1,8 +1,8 @@ #!/bin/bash echo "Getting hosted zones" -HOSTED_PUBLIC_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_public_zone_id // .providers["cloud-providers"].networking.public_dns_zone_name') -HOSTED_PRIVATE_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_zone_id // .providers["cloud-providers"].networking.private_dns_zone_name') +HOSTED_PUBLIC_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_public_zone_id // .providers["cloud-providers"].networking.hosted_public_zone_name') +HOSTED_PRIVATE_ZONE_ID=$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.hosted_zone_id // .providers["cloud-providers"].networking.hosted_public_zone_name') echo "Public Hosted Zone ID: $HOSTED_PUBLIC_ZONE_ID" echo "Private Hosted Zone ID: $HOSTED_PRIVATE_ZONE_ID" diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index a0a29a25..9fad4f64 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -7,6 +7,7 @@ echo "DNS Type: $DNS_TYPE" echo "Action: $ACTION" echo "Scope Domain: $SCOPE_DOMAIN" + if [[ "$ACTION" == "DELETE" ]] && [[ -z "${SCOPE_DOMAIN:-}" || "${SCOPE_DOMAIN:-}" == "To be defined" ]]; then echo "Skipping route53 action as the scope has no domain" return 0 @@ -21,17 +22,30 @@ case "$DNS_TYPE" in } ;; azure) + # TODO(federico.maleh) azure creates just one record (public or private), aro always creates private and optionally public. Make this work for both scenarios if [ "$SCOPE_VISIBILITY" = "public" ]; then GATEWAY_NAME="$PUBLIC_GATEWAY_NAME" - HOSTED_ZONE_NAME="$PUBLIC_HOSTED_ZONE_NAME" - HOSTED_ZONE_RG="$PUBLIC_HOSTED_ZONE_RG" - else - GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" - HOSTED_ZONE_NAME="$PRIVATE_HOSTED_ZONE_NAME" - HOSTED_ZONE_RG="$PRIVATE_HOSTED_ZONE_RG" + HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r 'providers["cloud-providers"].networking.public_dns_zone_name')" + HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_resource_group_name')" + + echo "Using Azure DNS; Creating public dns record" + echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" + echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" + + source "$SERVICE_PATH/scope/networking/dns/az-records/manage_route" \ + --action="$ACTION" \ + --resource-group="$RESOURCE_GROUP" \ + --subscription-id="$AZURE_SUBSCRIPTION_ID" \ + --gateway-name="$GATEWAY_NAME" \ + --hosted-zone-name="$HOSTED_ZONE_NAME" \ + --hosted-zone-rg="$HOSTED_ZONE_RG" fi - echo "Using Azure DNS" + GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" + HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r 'providers["cloud-providers"].networking.private_dns_zone_name')" + HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_resource_group_name')" + + echo "Using Azure DNS; Creating private dns record" echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" From 65c826b7087e4553573e475d57dd00a5b8711a41 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Tue, 4 Nov 2025 20:01:48 -0300 Subject: [PATCH 26/59] fix read data from providers --- k8s/scope/networking/dns/manage_dns | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index 9fad4f64..99b9ad8f 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -25,7 +25,7 @@ case "$DNS_TYPE" in # TODO(federico.maleh) azure creates just one record (public or private), aro always creates private and optionally public. Make this work for both scenarios if [ "$SCOPE_VISIBILITY" = "public" ]; then GATEWAY_NAME="$PUBLIC_GATEWAY_NAME" - HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r 'providers["cloud-providers"].networking.public_dns_zone_name')" + HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_name')" HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_resource_group_name')" echo "Using Azure DNS; Creating public dns record" @@ -42,7 +42,7 @@ case "$DNS_TYPE" in fi GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" - HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r 'providers["cloud-providers"].networking.private_dns_zone_name')" + HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_name')" HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_resource_group_name')" echo "Using Azure DNS; Creating private dns record" From 6bf44888efbed86ca4a9dda54f256e8fac49b727 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Tue, 4 Nov 2025 20:24:33 -0300 Subject: [PATCH 27/59] use correct api version for private dns zone --- k8s/scope/networking/dns/az-records/manage_route | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 7a697bf8..0209ae80 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -106,7 +106,7 @@ EOF ) else zone_path="privateDnsZones" - api_version="2018-09-01" + api_version="2020-06-01" # Private DNS zone uses lowercase ttl and aRecords RECORD_BODY=$(cat < Date: Tue, 4 Nov 2025 20:35:43 -0300 Subject: [PATCH 28/59] use private visibility for private domain --- k8s/scope/networking/dns/az-records/manage_route | 8 +++++--- k8s/scope/networking/dns/manage_dns | 6 ++++-- 2 files changed, 9 insertions(+), 5 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 0209ae80..5eb98b34 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -40,6 +40,7 @@ RESOURCE_GROUP="" AZURE_SUBSCRIPTION_ID="" HOSTED_ZONE_NAME="" HOSTED_ZONE_RG="" +VISIBILITY="" for arg in "$@"; do case $arg in @@ -49,6 +50,7 @@ for arg in "$@"; do --gateway-name=*) GATEWAY_NAME="${arg#*=}" ;; --hosted-zone-name=*) HOSTED_ZONE_NAME="${arg#*=}" ;; --hosted-zone-rg=*) HOSTED_ZONE_RG="${arg#*=}" ;; + --visibility=*) VISIBILITY="${arg#*=}" ;; esac done @@ -81,13 +83,13 @@ if [ -z "$SCOPE_SUBDOMAIN" ]; then SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" fi -echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, SCOPE_VISIBILITY = $SCOPE_VISIBILITY" +echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, VISIBILITY = $VISIBILITY" if [ "$ACTION" = "CREATE" ]; then # Get access token ACCESS_TOKEN=$(get_azure_token) || exit 1 - if [ "$SCOPE_VISIBILITY" = "public" ]; then + if [ "$VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" # Public DNS zone uses uppercase TTL and ARecords @@ -157,7 +159,7 @@ elif [ "$ACTION" = "DELETE" ]; then ACCESS_TOKEN=$(get_azure_token) || exit 1 - if [ "$SCOPE_VISIBILITY" = "public" ]; then + if [ "$VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" else diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index 99b9ad8f..7aac9ff4 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -38,7 +38,8 @@ case "$DNS_TYPE" in --subscription-id="$AZURE_SUBSCRIPTION_ID" \ --gateway-name="$GATEWAY_NAME" \ --hosted-zone-name="$HOSTED_ZONE_NAME" \ - --hosted-zone-rg="$HOSTED_ZONE_RG" + --hosted-zone-rg="$HOSTED_ZONE_RG" \ + --visibility="public" fi GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" @@ -55,7 +56,8 @@ case "$DNS_TYPE" in --subscription-id="$AZURE_SUBSCRIPTION_ID" \ --gateway-name="$GATEWAY_NAME" \ --hosted-zone-name="$HOSTED_ZONE_NAME" \ - --hosted-zone-rg="$HOSTED_ZONE_RG" + --hosted-zone-rg="$HOSTED_ZONE_RG" \ + --visibility="internal" ;; external_dns) echo "Using external_dns provider" From 9fdd498d5dc4973fab413368a0b1b37554f14bd6 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Tue, 4 Nov 2025 21:06:39 -0300 Subject: [PATCH 29/59] do not internal dns for public scopes --- .../networking/dns/az-records/manage_route | 8 ++---- k8s/scope/networking/dns/manage_dns | 28 +++++-------------- 2 files changed, 10 insertions(+), 26 deletions(-) diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 5eb98b34..0209ae80 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -40,7 +40,6 @@ RESOURCE_GROUP="" AZURE_SUBSCRIPTION_ID="" HOSTED_ZONE_NAME="" HOSTED_ZONE_RG="" -VISIBILITY="" for arg in "$@"; do case $arg in @@ -50,7 +49,6 @@ for arg in "$@"; do --gateway-name=*) GATEWAY_NAME="${arg#*=}" ;; --hosted-zone-name=*) HOSTED_ZONE_NAME="${arg#*=}" ;; --hosted-zone-rg=*) HOSTED_ZONE_RG="${arg#*=}" ;; - --visibility=*) VISIBILITY="${arg#*=}" ;; esac done @@ -83,13 +81,13 @@ if [ -z "$SCOPE_SUBDOMAIN" ]; then SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" fi -echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, VISIBILITY = $VISIBILITY" +echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, SCOPE_VISIBILITY = $SCOPE_VISIBILITY" if [ "$ACTION" = "CREATE" ]; then # Get access token ACCESS_TOKEN=$(get_azure_token) || exit 1 - if [ "$VISIBILITY" = "public" ]; then + if [ "$SCOPE_VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" # Public DNS zone uses uppercase TTL and ARecords @@ -159,7 +157,7 @@ elif [ "$ACTION" = "DELETE" ]; then ACCESS_TOKEN=$(get_azure_token) || exit 1 - if [ "$VISIBILITY" = "public" ]; then + if [ "$SCOPE_VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" else diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index 7aac9ff4..24575ad6 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -22,31 +22,18 @@ case "$DNS_TYPE" in } ;; azure) - # TODO(federico.maleh) azure creates just one record (public or private), aro always creates private and optionally public. Make this work for both scenarios if [ "$SCOPE_VISIBILITY" = "public" ]; then GATEWAY_NAME="$PUBLIC_GATEWAY_NAME" HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_name')" HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_resource_group_name')" - - echo "Using Azure DNS; Creating public dns record" - echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" - echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" - - source "$SERVICE_PATH/scope/networking/dns/az-records/manage_route" \ - --action="$ACTION" \ - --resource-group="$RESOURCE_GROUP" \ - --subscription-id="$AZURE_SUBSCRIPTION_ID" \ - --gateway-name="$GATEWAY_NAME" \ - --hosted-zone-name="$HOSTED_ZONE_NAME" \ - --hosted-zone-rg="$HOSTED_ZONE_RG" \ - --visibility="public" + else + GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" + HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_name')" + HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_resource_group_name')" fi - GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" - HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_name')" - HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_resource_group_name')" - - echo "Using Azure DNS; Creating private dns record" + echo "Using Azure DNS" + echo "GATEWAY_NAME = $GATEWAY_NAME" echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" @@ -56,8 +43,7 @@ case "$DNS_TYPE" in --subscription-id="$AZURE_SUBSCRIPTION_ID" \ --gateway-name="$GATEWAY_NAME" \ --hosted-zone-name="$HOSTED_ZONE_NAME" \ - --hosted-zone-rg="$HOSTED_ZONE_RG" \ - --visibility="internal" + --hosted-zone-rg="$HOSTED_ZONE_RG" ;; external_dns) echo "Using external_dns provider" From f9caac7b62c1431852e918195634ab1378b7d125 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Wed, 5 Nov 2025 02:25:40 -0300 Subject: [PATCH 30/59] create internal record for public scopes --- azure-aro/scripts/build_internal_domain | 15 +++ azure-aro/values.yaml | 7 +- .../aro/blue-green-httproute.yaml.tpl | 104 ++++++++++++++---- .../templates/aro/initial-httproute.yaml.tpl | 95 +++++++++++++--- .../networking/dns/az-records/manage_route | 8 +- k8s/scope/networking/dns/manage_dns | 28 +++-- 6 files changed, 209 insertions(+), 48 deletions(-) create mode 100644 azure-aro/scripts/build_internal_domain diff --git a/azure-aro/scripts/build_internal_domain b/azure-aro/scripts/build_internal_domain new file mode 100644 index 00000000..e250e20c --- /dev/null +++ b/azure-aro/scripts/build_internal_domain @@ -0,0 +1,15 @@ +#!/bin/bash + +SCOPE_DOMAIN=$(echo "$CONTEXT" | jq .scope.domain -r) + +PUBLIC_HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_name')" +PRIVATE_HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_name')" + +INTERNAL_DOMAIN="${SCOPE_DOMAIN%.$PUBLIC_HOSTED_ZONE_NAME}.$PRIVATE_HOSTED_ZONE_NAME" + +CONTEXT=$(echo "$CONTEXT" | jq \ + --arg internal_domain "$INTERNAL_DOMAIN" \ + '. + {internal_domain: $internal_domain}') + +export INTERNAL_DOMAIN +export CONTEXT \ No newline at end of file diff --git a/azure-aro/values.yaml b/azure-aro/values.yaml index 7ff585b6..6f906911 100644 --- a/azure-aro/values.yaml +++ b/azure-aro/values.yaml @@ -7,4 +7,9 @@ configuration: SERVICE_TEMPLATE: "$SERVICE_PATH/deployment/templates/istio/service.yaml.tpl" INITIAL_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/initial-httproute.yaml.tpl" BLUE_GREEN_INGRESS_PATH: "$SERVICE_PATH/deployment/templates/aro/blue-green-httproute.yaml.tpl" - GATEWAY_TYPE: aro_cluster \ No newline at end of file + GATEWAY_TYPE: aro_cluster +steps: + - name: build_private_domain + type: script + file: "$OVERRIDES_PATH/scripts/build_internal_domain" + after: build context \ No newline at end of file diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index 650b5221..6468fa7d 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -15,36 +15,36 @@ metadata: scope_id: "{{ .scope.id }}" deployment-strategy: "blue-green" type: {{ .ingress_visibility }} -{{- $global := index .k8s_modifiers "global" }} -{{- if $global }} + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} {{- $labels := index $global "labels" }} {{- if $labels }} -{{ data.ToYAML $labels | indent 4 }} + {{ data.ToYAML $labels | indent 4 }} {{- end }} -{{- end }} -{{- $ingress := index .k8s_modifiers "ingress" }} -{{- if $ingress }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} {{- $labels := index $ingress "labels" }} {{- if $labels }} -{{ data.ToYAML $labels | indent 4 }} + {{ data.ToYAML $labels | indent 4 }} + {{- end }} {{- end }} -{{- end }} - annotations: - route.openshift.io/deployment-strategy: "blue-green" -{{- $global := index .k8s_modifiers "global" }} -{{- if $global }} +annotations: + route.openshift.io/deployment-strategy: "blue-green" + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} {{- $annotations := index $global "annotations" }} {{- if $annotations }} -{{ data.ToYAML $annotations | indent 4 }} + {{ data.ToYAML $annotations | indent 4 }} {{- end }} -{{- end }} -{{- $ingress := index .k8s_modifiers "ingress" }} -{{- if $ingress }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} {{- $annotations := index $ingress "annotations" }} {{- if $annotations }} -{{ data.ToYAML $annotations | indent 4 }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} {{- end }} -{{- end }} spec: host: {{ .scope.domain }} port: @@ -60,4 +60,70 @@ spec: alternateBackends: - kind: Service name: d-{{ .scope.id }}-{{ .deployment.id }} - weight: {{ .deployment.strategy_data.desired_switched_traffic }} \ No newline at end of file + weight: {{ .deployment.strategy_data.desired_switched_traffic }} + {{- if eq .ingress_visibility "internet-facing" }} +--- +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: k-8-s-{{ .scope.slug }}-{{ .scope.id }}-internal + namespace: {{ .k8s_namespace }} + labels: + nullplatform: "true" + account: {{ .account.slug }} + account_id: "{{ .account.id }}" + namespace: {{ .namespace.slug }} + namespace_id: "{{ .namespace.id }}" + application: {{ .application.slug }} + application_id: "{{ .application.id }}" + scope: {{ .scope.slug }} + scope_id: "{{ .scope.id }}" + deployment-strategy: "blue-green" + type: internal + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} + {{- $labels := index $global "labels" }} + {{- if $labels }} + {{ data.ToYAML $labels | indent 4 }} + {{- end }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} + {{- $labels := index $ingress "labels" }} + {{- if $labels }} + {{ data.ToYAML $labels | indent 4 }} + {{- end }} + {{- end }} +annotations: + route.openshift.io/deployment-strategy: "blue-green" + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} + {{- $annotations := index $global "annotations" }} + {{- if $annotations }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} + {{- $annotations := index $ingress "annotations" }} + {{- if $annotations }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} + {{- end }} +spec: + host: {{ .internal_domain }} + port: + targetPort: 80 + tls: + insecureEdgeTerminationPolicy: Redirect + termination: edge + wildcardPolicy: None + to: + kind: Service + name: d-{{ .scope.id }}-{{ .blue_deployment_id }} + weight: {{ sub 100 .deployment.strategy_data.desired_switched_traffic }} + alternateBackends: + - kind: Service + name: d-{{ .scope.id }}-{{ .deployment.id }} + weight: {{ .deployment.strategy_data.desired_switched_traffic }} + {{- end }} \ No newline at end of file diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index 67e20ba0..a5c290bc 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -14,35 +14,35 @@ metadata: scope: {{ .scope.slug }} scope_id: "{{ .scope.id }}" type: {{ .ingress_visibility }} -{{- $global := index .k8s_modifiers "global" }} -{{- if $global }} + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} {{- $labels := index $global "labels" }} {{- if $labels }} -{{ data.ToYAML $labels | indent 4 }} + {{ data.ToYAML $labels | indent 4 }} {{- end }} -{{- end }} -{{- $ingress := index .k8s_modifiers "ingress" }} -{{- if $ingress }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} {{- $labels := index $ingress "labels" }} {{- if $labels }} -{{ data.ToYAML $labels | indent 4 }} + {{ data.ToYAML $labels | indent 4 }} + {{- end }} {{- end }} -{{- end }} - annotations: -{{- $global := index .k8s_modifiers "global" }} -{{- if $global }} +annotations: + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} {{- $annotations := index $global "annotations" }} {{- if $annotations }} -{{ data.ToYAML $annotations | indent 4 }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} {{- end }} -{{- end }} -{{- $ingress := index .k8s_modifiers "ingress" }} -{{- if $ingress }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} {{- $annotations := index $ingress "annotations" }} {{- if $annotations }} -{{ data.ToYAML $annotations | indent 4 }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} {{- end }} -{{- end }} spec: host: {{ .scope.domain }} port: @@ -53,4 +53,63 @@ spec: wildcardPolicy: None to: kind: Service - name: d-{{ .scope.id }}-{{ .deployment.id }} \ No newline at end of file + name: d-{{ .scope.id }}-{{ .deployment.id }} + {{- if eq .ingress_visibility "internet-facing" }} +--- +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: k-8-s-{{ .scope.slug }}-{{ .scope.id }}-internal + namespace: {{ .k8s_namespace }} + labels: + nullplatform: "true" + account: {{ .account.slug }} + account_id: "{{ .account.id }}" + namespace: {{ .namespace.slug }} + namespace_id: "{{ .namespace.id }}" + application: {{ .application.slug }} + application_id: "{{ .application.id }}" + scope: {{ .scope.slug }} + scope_id: "{{ .scope.id }}" + type: internal + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} + {{- $labels := index $global "labels" }} + {{- if $labels }} + {{ data.ToYAML $labels | indent 4 }} + {{- end }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} + {{- $labels := index $ingress "labels" }} + {{- if $labels }} + {{ data.ToYAML $labels | indent 4 }} + {{- end }} + {{- end }} +annotations: + {{- $global := index .k8s_modifiers "global" }} + {{- if $global }} + {{- $annotations := index $global "annotations" }} + {{- if $annotations }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} + {{- end }} + {{- $ingress := index .k8s_modifiers "ingress" }} + {{- if $ingress }} + {{- $annotations := index $ingress "annotations" }} + {{- if $annotations }} + {{ data.ToYAML $annotations | indent 4 }} + {{- end }} + {{- end }} +spec: + host: {{ .internal_domain }} + port: + targetPort: 80 + tls: + insecureEdgeTerminationPolicy: Redirect + termination: edge + wildcardPolicy: None + to: + kind: Service + name: d-{{ .scope.id }}-{{ .deployment.id }} + {{- end }} \ No newline at end of file diff --git a/k8s/scope/networking/dns/az-records/manage_route b/k8s/scope/networking/dns/az-records/manage_route index 0209ae80..5eb98b34 100755 --- a/k8s/scope/networking/dns/az-records/manage_route +++ b/k8s/scope/networking/dns/az-records/manage_route @@ -40,6 +40,7 @@ RESOURCE_GROUP="" AZURE_SUBSCRIPTION_ID="" HOSTED_ZONE_NAME="" HOSTED_ZONE_RG="" +VISIBILITY="" for arg in "$@"; do case $arg in @@ -49,6 +50,7 @@ for arg in "$@"; do --gateway-name=*) GATEWAY_NAME="${arg#*=}" ;; --hosted-zone-name=*) HOSTED_ZONE_NAME="${arg#*=}" ;; --hosted-zone-rg=*) HOSTED_ZONE_RG="${arg#*=}" ;; + --visibility=*) VISIBILITY="${arg#*=}" ;; esac done @@ -81,13 +83,13 @@ if [ -z "$SCOPE_SUBDOMAIN" ]; then SCOPE_SUBDOMAIN="${SCOPE_DOMAIN%.$HOSTED_ZONE_NAME}" fi -echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, SCOPE_VISIBILITY = $SCOPE_VISIBILITY" +echo "manage_route SCOPE_SUBDOMAIN = $SCOPE_SUBDOMAIN HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME GATEWAY_IP = $GATEWAY_IP, VISIBILITY = $VISIBILITY" if [ "$ACTION" = "CREATE" ]; then # Get access token ACCESS_TOKEN=$(get_azure_token) || exit 1 - if [ "$SCOPE_VISIBILITY" = "public" ]; then + if [ "$VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" # Public DNS zone uses uppercase TTL and ARecords @@ -157,7 +159,7 @@ elif [ "$ACTION" = "DELETE" ]; then ACCESS_TOKEN=$(get_azure_token) || exit 1 - if [ "$SCOPE_VISIBILITY" = "public" ]; then + if [ "$VISIBILITY" = "public" ]; then zone_path="dnsZones" api_version="2018-05-01" else diff --git a/k8s/scope/networking/dns/manage_dns b/k8s/scope/networking/dns/manage_dns index 24575ad6..7aac9ff4 100755 --- a/k8s/scope/networking/dns/manage_dns +++ b/k8s/scope/networking/dns/manage_dns @@ -22,18 +22,31 @@ case "$DNS_TYPE" in } ;; azure) + # TODO(federico.maleh) azure creates just one record (public or private), aro always creates private and optionally public. Make this work for both scenarios if [ "$SCOPE_VISIBILITY" = "public" ]; then GATEWAY_NAME="$PUBLIC_GATEWAY_NAME" HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_name')" HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.public_dns_zone_resource_group_name')" - else - GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" - HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_name')" - HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_resource_group_name')" + + echo "Using Azure DNS; Creating public dns record" + echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" + echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" + + source "$SERVICE_PATH/scope/networking/dns/az-records/manage_route" \ + --action="$ACTION" \ + --resource-group="$RESOURCE_GROUP" \ + --subscription-id="$AZURE_SUBSCRIPTION_ID" \ + --gateway-name="$GATEWAY_NAME" \ + --hosted-zone-name="$HOSTED_ZONE_NAME" \ + --hosted-zone-rg="$HOSTED_ZONE_RG" \ + --visibility="public" fi - echo "Using Azure DNS" - echo "GATEWAY_NAME = $GATEWAY_NAME" + GATEWAY_NAME="$PRIVATE_GATEWAY_NAME" + HOSTED_ZONE_NAME="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_name')" + HOSTED_ZONE_RG="$(echo "$CONTEXT" | jq -r '.providers["cloud-providers"].networking.private_dns_zone_resource_group_name')" + + echo "Using Azure DNS; Creating private dns record" echo "HOSTED_ZONE_NAME = $HOSTED_ZONE_NAME" echo "HOSTED_ZONE_RG = $HOSTED_ZONE_RG" @@ -43,7 +56,8 @@ case "$DNS_TYPE" in --subscription-id="$AZURE_SUBSCRIPTION_ID" \ --gateway-name="$GATEWAY_NAME" \ --hosted-zone-name="$HOSTED_ZONE_NAME" \ - --hosted-zone-rg="$HOSTED_ZONE_RG" + --hosted-zone-rg="$HOSTED_ZONE_RG" \ + --visibility="internal" ;; external_dns) echo "Using external_dns provider" From 2f116aa3092b6679bd4dfb004c8982051c41a810 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Wed, 5 Nov 2025 02:30:35 -0300 Subject: [PATCH 31/59] fix aro route annotations --- .../aro/blue-green-httproute.yaml.tpl | 64 +++++++++---------- .../templates/aro/initial-httproute.yaml.tpl | 60 ++++++++--------- 2 files changed, 62 insertions(+), 62 deletions(-) diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index 6468fa7d..3569c1dc 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -29,22 +29,22 @@ metadata: {{ data.ToYAML $labels | indent 4 }} {{- end }} {{- end }} -annotations: - route.openshift.io/deployment-strategy: "blue-green" - {{- $global := index .k8s_modifiers "global" }} - {{- if $global }} - {{- $annotations := index $global "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} - {{- $ingress := index .k8s_modifiers "ingress" }} - {{- if $ingress }} - {{- $annotations := index $ingress "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} + annotations: + route.openshift.io/deployment-strategy: "blue-green" +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} +{{- $annotations := index $global "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} +{{- $annotations := index $ingress "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} spec: host: {{ .scope.domain }} port: @@ -94,22 +94,22 @@ metadata: {{ data.ToYAML $labels | indent 4 }} {{- end }} {{- end }} -annotations: - route.openshift.io/deployment-strategy: "blue-green" - {{- $global := index .k8s_modifiers "global" }} - {{- if $global }} - {{- $annotations := index $global "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} - {{- $ingress := index .k8s_modifiers "ingress" }} - {{- if $ingress }} - {{- $annotations := index $ingress "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} + annotations: + route.openshift.io/deployment-strategy: "blue-green" +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} +{{- $annotations := index $global "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} +{{- $annotations := index $ingress "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} spec: host: {{ .internal_domain }} port: diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index a5c290bc..5a026245 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -28,21 +28,21 @@ metadata: {{ data.ToYAML $labels | indent 4 }} {{- end }} {{- end }} -annotations: - {{- $global := index .k8s_modifiers "global" }} - {{- if $global }} - {{- $annotations := index $global "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} - {{- $ingress := index .k8s_modifiers "ingress" }} - {{- if $ingress }} - {{- $annotations := index $ingress "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} + annotations: +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} +{{- $annotations := index $global "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} +{{- $annotations := index $ingress "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} spec: host: {{ .scope.domain }} port: @@ -86,21 +86,21 @@ metadata: {{ data.ToYAML $labels | indent 4 }} {{- end }} {{- end }} -annotations: - {{- $global := index .k8s_modifiers "global" }} - {{- if $global }} - {{- $annotations := index $global "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} - {{- $ingress := index .k8s_modifiers "ingress" }} - {{- if $ingress }} - {{- $annotations := index $ingress "annotations" }} - {{- if $annotations }} - {{ data.ToYAML $annotations | indent 4 }} - {{- end }} - {{- end }} + annotations: +{{- $global := index .k8s_modifiers "global" }} +{{- if $global }} +{{- $annotations := index $global "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} +{{- $ingress := index .k8s_modifiers "ingress" }} +{{- if $ingress }} +{{- $annotations := index $ingress "annotations" }} +{{- if $annotations }} +{{ data.ToYAML $annotations | indent 4 }} +{{- end }} +{{- end }} spec: host: {{ .internal_domain }} port: From 770572f1a1a5ac9cf043c4dba1c6752814ae8c17 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Wed, 5 Nov 2025 02:48:50 -0300 Subject: [PATCH 32/59] Disable sticky sessions --- k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl | 2 ++ k8s/deployment/templates/aro/initial-httproute.yaml.tpl | 2 ++ 2 files changed, 4 insertions(+) diff --git a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl index 3569c1dc..872d3968 100644 --- a/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/blue-green-httproute.yaml.tpl @@ -31,6 +31,7 @@ metadata: {{- end }} annotations: route.openshift.io/deployment-strategy: "blue-green" + haproxy.router.openshift.io/disable_cookies: "true" {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $annotations := index $global "annotations" }} @@ -96,6 +97,7 @@ metadata: {{- end }} annotations: route.openshift.io/deployment-strategy: "blue-green" + haproxy.router.openshift.io/disable_cookies: "true" {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $annotations := index $global "annotations" }} diff --git a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl index 5a026245..f3167a7c 100644 --- a/k8s/deployment/templates/aro/initial-httproute.yaml.tpl +++ b/k8s/deployment/templates/aro/initial-httproute.yaml.tpl @@ -29,6 +29,7 @@ metadata: {{- end }} {{- end }} annotations: + haproxy.router.openshift.io/disable_cookies: "true" {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $annotations := index $global "annotations" }} @@ -87,6 +88,7 @@ metadata: {{- end }} {{- end }} annotations: + haproxy.router.openshift.io/disable_cookies: "true" {{- $global := index .k8s_modifiers "global" }} {{- if $global }} {{- $annotations := index $global "annotations" }} From 8cde55f5a21d9cbbc7a93f30a824b94d395d9d73 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Fri, 7 Nov 2025 14:52:05 -0300 Subject: [PATCH 33/59] Add logic to create applications --- application/entrypoint | 37 +++++++++++++++++ .../asset-repo/create_asset_repository | 15 +++++++ .../asset-repo/docker-server/build_context | 9 ++++ .../docker-server/create_repository | 3 ++ .../docker-server/generate_repository_uri | 16 ++++++++ application/scripts/base_context | 25 +++++++++++ .../scripts/code-repo/create_code_repository | 39 ++++++++++++++++++ .../scripts/code-repo/generate_secrets | 28 +++++++++++++ .../scripts/code-repo/gitlab/build_context | 26 ++++++++++++ .../code-repo/gitlab/create_repository | 41 +++++++++++++++++++ .../scripts/code-repo/gitlab/create_secrets | 29 +++++++++++++ .../scripts/code-repo/gitlab/run_first_build | 27 ++++++++++++ .../gitlab/validate_repository_does_not_exist | 28 +++++++++++++ application/workflows/create_app.yaml | 10 +++++ .../workflows/create_asset_repository.yaml | 10 +++++ .../workflows/create_code_repository.yaml | 19 +++++++++ 16 files changed, 362 insertions(+) create mode 100755 application/entrypoint create mode 100644 application/scripts/asset-repo/create_asset_repository create mode 100644 application/scripts/asset-repo/docker-server/build_context create mode 100644 application/scripts/asset-repo/docker-server/create_repository create mode 100644 application/scripts/asset-repo/docker-server/generate_repository_uri create mode 100644 application/scripts/base_context create mode 100644 application/scripts/code-repo/create_code_repository create mode 100644 application/scripts/code-repo/generate_secrets create mode 100755 application/scripts/code-repo/gitlab/build_context create mode 100644 application/scripts/code-repo/gitlab/create_repository create mode 100644 application/scripts/code-repo/gitlab/create_secrets create mode 100644 application/scripts/code-repo/gitlab/run_first_build create mode 100644 application/scripts/code-repo/gitlab/validate_repository_does_not_exist create mode 100644 application/workflows/create_app.yaml create mode 100644 application/workflows/create_asset_repository.yaml create mode 100644 application/workflows/create_code_repository.yaml diff --git a/application/entrypoint b/application/entrypoint new file mode 100755 index 00000000..f1bcb7bf --- /dev/null +++ b/application/entrypoint @@ -0,0 +1,37 @@ +#!/bin/bash + +CLEAN_CONTEXT=$(echo "$NP_ACTION_CONTEXT" | sed "s/^'//;s/'$//") + +export NP_ACTION_CONTEXT="$CLEAN_CONTEXT" + +CURRENT_DIR=$(dirname "${BASH_SOURCE[0]}") + +cd "$CURRENT_DIR" && cd .. + +TOKEN=$(np token create --body "{\"api_key\": \"$NP_API_KEY\"}" --format json | jq -r .access_token) + +CALLBACK_URL=$(echo "$NP_ACTION_CONTEXT" | jq -r .notification.callback_url) + +np service workflow exec --workflow application/workflows/create_app.yaml +EXIT_CODE=$? + +# Determine status based on exit code +if [ $EXIT_CODE -eq 0 ]; then + STATUS="success" +else + STATUS="failed" +fi + +echo "Updating hook with status: $STATUS. URL: $CALLBACK_URL" + +# Call the callback URL with the status +HTTP_CODE=$(curl -s -o /dev/null -w "%{http_code}" -X PATCH "$CALLBACK_URL" \ + -H "Authorization: Bearer $TOKEN" \ + -H "Content-Type: application/json" \ + -d "{\"status\": \"$STATUS\"}") + +if [ "$HTTP_CODE" -ge 200 ] && [ "$HTTP_CODE" -lt 300 ]; then + echo "✓ Successfully updated hook (HTTP $HTTP_CODE)" +else + echo "✗ Failed to update hook (HTTP $HTTP_CODE)" +fi \ No newline at end of file diff --git a/application/scripts/asset-repo/create_asset_repository b/application/scripts/asset-repo/create_asset_repository new file mode 100644 index 00000000..9fe5d6c7 --- /dev/null +++ b/application/scripts/asset-repo/create_asset_repository @@ -0,0 +1,15 @@ +#!/bin/bash + +ASSET_REPOSITORY=$(np provider list --categories assets-repository --nrn "$NRN" --format json | jq ".results[0]") +ASSET_REPOSITORY_SPEC=$(echo "$ASSET_REPOSITORY" | jq -r .specification_id) + +REPOSITORY_PROVIDER=$(np provider specification read --id "$ASSET_REPOSITORY_SPEC" --format json | jq -r .slug) + +ASSET_REPOSITORY_SCRIPT_PATH="application/scripts/asset-repo/$REPOSITORY_PROVIDER" + +export ASSET_REPOSITORY_TYPE +export ASSET_REPOSITORY + +export ASSET_REPOSITORY_SCRIPT_PATH + +np service workflow exec --workflow application/workflows/create_asset_repository.yaml \ No newline at end of file diff --git a/application/scripts/asset-repo/docker-server/build_context b/application/scripts/asset-repo/docker-server/build_context new file mode 100644 index 00000000..7321cdc7 --- /dev/null +++ b/application/scripts/asset-repo/docker-server/build_context @@ -0,0 +1,9 @@ +#!/bin/bash + +DOCKER_SERVER_URL=$(echo "$ASSET_REPOSITORY" | jq -r .attributes.setup.server) +DOCKER_SERVER_PATH=$(echo "$ASSET_REPOSITORY" | jq -r .attributes.setup.path) +DOCKER_SERVER_USE_NAMESPACE=$(echo "$ASSET_REPOSITORY" | jq -r .attributes.setup.use_namespace) + +export DOCKER_SERVER_URL +export DOCKER_SERVER_PATH +export DOCKER_SERVER_USE_NAMESPACE \ No newline at end of file diff --git a/application/scripts/asset-repo/docker-server/create_repository b/application/scripts/asset-repo/docker-server/create_repository new file mode 100644 index 00000000..e3b7564c --- /dev/null +++ b/application/scripts/asset-repo/docker-server/create_repository @@ -0,0 +1,3 @@ +#!/bin/bash + +np nrn patch --nrn "$NRN" --body "{\"docker.repository_uri\":\"$DOCKER_SERVER_URI\"}" \ No newline at end of file diff --git a/application/scripts/asset-repo/docker-server/generate_repository_uri b/application/scripts/asset-repo/docker-server/generate_repository_uri new file mode 100644 index 00000000..e81d7db6 --- /dev/null +++ b/application/scripts/asset-repo/docker-server/generate_repository_uri @@ -0,0 +1,16 @@ +#!/bin/bash + +DOCKER_SERVER_URI=$DOCKER_SERVER_URL + +if [[ ! -z "$DOCKER_SERVER_PATH" ]]; then + DOCKER_SERVER_URI="$DOCKER_SERVER_URI/$DOCKER_SERVER_PATH" +fi + +SEPARATOR="-" +if [[ "$DOCKER_SERVER_USE_NAMESPACE" == "true" ]]; then + SEPARATOR="/" +fi + +DOCKER_SERVER_URI="$DOCKER_SERVER_URI/$NAMESPACE_SLUG$SEPARATOR$APPLICATION_SLUG" + +export DOCKER_SERVER_URI \ No newline at end of file diff --git a/application/scripts/base_context b/application/scripts/base_context new file mode 100644 index 00000000..d8f60bec --- /dev/null +++ b/application/scripts/base_context @@ -0,0 +1,25 @@ +#!/bin/bash + +NRN=$(echo "$NP_ACTION_CONTEXT" | jq -r .notification.nrn) + +ACCOUNT_ID=$(echo "$NRN" | sed -n 's/.*account=\([0-9]*\).*/\1/p') +NAMESPACE_ID=$(echo "$NRN" | sed -n 's/.*namespace=\([0-9]*\).*/\1/p') +APPLICATION_ID=$(echo "$NRN" | sed -n 's/.*application=\([0-9]*\).*/\1/p') + +NAMESPACE=$(np namespace read --format json --id "$NAMESPACE_ID") + +APPLICATION=$(np application read --format json --id "$APPLICATION_ID") + +APPLICATION_SLUG=$(echo "$APPLICATION" | jq -r .slug) +NAMESPACE_SLUG=$(echo "$NAMESPACE" | jq -r .slug) + +export ACCOUNT_ID + +export NAMESPACE +export NAMESPACE_ID +export NAMESPACE_SLUG + +export APPLICATION +export APPLICATION_ID +export APPLICATION_SLUG +export NRN diff --git a/application/scripts/code-repo/create_code_repository b/application/scripts/code-repo/create_code_repository new file mode 100644 index 00000000..43c2a677 --- /dev/null +++ b/application/scripts/code-repo/create_code_repository @@ -0,0 +1,39 @@ +#!/bin/bash + +CURRENT_DIR=$(dirname "${BASH_SOURCE[0]}") + +REPOSITORY_URL=$(echo "$APPLICATION" | jq -r .repository_url) + +if [[ -z $REPOSITORY_URL ]]; then + CODE_REPOSITORY_STRATEGY=create + + TEMPLATE_ID=$(echo "$APPLICATION" | jq -r .template_id) + + TEMPLATE_URL=$(np template read --id "$TEMPLATE_ID" --format json | jq -r .url) + + export TEMPLATE_URL + + REPOSITORY_NAME=$NAMESPACE_SLUG-$APPLICATION_SLUG +else + REPOSITORY_NAME=$(basename "$REPOSITORY_URL") + CODE_REPOSITORY_STRATEGY=import +fi + +ACCOUNT=$(np account read --id "$ACCOUNT_ID" --format json) + +REPOSITORY_PROVIDER=$(echo "$ACCOUNT" | jq -r .repository_provider) + +CODE_REPOSITORY=$(np provider list --categories code-repository --nrn "$NRN" --format json | jq ".results[0]") + +CODE_REPOSITORY_SCRIPT_PATH="application/scripts/code-repo/$REPOSITORY_PROVIDER" + +export CODE_REPOSITORY_STRATEGY + +export REPOSITORY_URL +export REPOSITORY_NAME + +export CODE_REPOSITORY +export REPOSITORY_PROVIDER +export CODE_REPOSITORY_SCRIPT_PATH + +np service workflow exec --workflow application/workflows/create_code_repository.yaml \ No newline at end of file diff --git a/application/scripts/code-repo/generate_secrets b/application/scripts/code-repo/generate_secrets new file mode 100644 index 00000000..3edb322f --- /dev/null +++ b/application/scripts/code-repo/generate_secrets @@ -0,0 +1,28 @@ +#!/bin/bash +CI_ROLE_ID=1855672260 +# TODO(federico.maleh) missing support for mono repo +# TODO(federico.maleh) missing support for extra secrets +# TODO(federico.maleh) missing support for extra roles in api key +# TODO(federico.maleh) missing add collaborators +# TODO(federico.maleh) missing support for no template use case + +API_KEY_NAME="ci-$NAMESPACE_SLUG-$NAMESPACE_ID-$APPLICATION_SLUG-$APPLICATION_ID" + +echo "Creating api key for ci: $API_KEY_NAME" + +API_KEY_RESPONSE=$(np api-key create --format json --body "{ + \"name\": \"$API_KEY_NAME\", + \"grants\": [ + {\"nrn\": \"$NRN\", \"role_id\": $CI_ROLE_ID} + ], + \"tags\": [{ \"key\": \"ci\", \"value\": true }], + \"internal\": true +}") + + +API_KEY=$(echo "$API_KEY_RESPONSE" | jq -r .api_key) +echo "Created api key for ci" + +CODE_REPOSITORY_SECRETS="{\"NP_API_KEY\": \"$API_KEY\"}" + +export CODE_REPOSITORY_SECRETS \ No newline at end of file diff --git a/application/scripts/code-repo/gitlab/build_context b/application/scripts/code-repo/gitlab/build_context new file mode 100755 index 00000000..41ef45fb --- /dev/null +++ b/application/scripts/code-repo/gitlab/build_context @@ -0,0 +1,26 @@ +#!/bin/bash + +GITLAB_ACCESS_TOKEN=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.access_token') +GITLAB_GROUP_PATH=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.group_path') +GITLAB_INSTALLATION_URL=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.installation_url') + +echo "Getting group ID for path: $GITLAB_GROUP_PATH" +GROUP_RESPONSE=$(curl -s --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + "${GITLAB_INSTALLATION_URL}/api/v4/groups?search=${GITLAB_GROUP_PATH}") + +GITLAB_GROUP_ID=$(echo "$GROUP_RESPONSE" | jq -r ".[] | select(.full_path == \"${GITLAB_GROUP_PATH}\") | .id") + +if [ -z "$GITLAB_GROUP_ID" ] || [ "$GITLAB_GROUP_ID" == "null" ]; then + echo "Error: Group not found for path: $GITLAB_GROUP_PATH" + exit 1 +fi + +echo "Found gitlab Group ID: $GITLAB_GROUP_ID" + +GITLAB_ENCODED_GROUP_PATH=$(echo "$GITLAB_GROUP_PATH" | sed 's/\//%2F/g') + +export GITLAB_ACCESS_TOKEN +export GITLAB_GROUP_PATH +export GITLAB_INSTALLATION_URL +export GITLAB_GROUP_ID +export GITLAB_ENCODED_GROUP_PATH \ No newline at end of file diff --git a/application/scripts/code-repo/gitlab/create_repository b/application/scripts/code-repo/gitlab/create_repository new file mode 100644 index 00000000..e6d8c8e9 --- /dev/null +++ b/application/scripts/code-repo/gitlab/create_repository @@ -0,0 +1,41 @@ +#!/bin/bash + +if [[ $CODE_REPOSITORY_STRATEGY == "import" ]]; then + echo "Strategy is set to 'import'. Skipping repo creation." + return +fi + +IMPORT_URL=$TEMPLATE_URL + +if [[ "$TEMPLATE_URL" == "$GITLAB_INSTALLATION_URL"* ]]; then + PARSED_HOST=$(echo "$TEMPLATE_URL" | sed -E 's|https?://||' | cut -d'/' -f1) + PARSED_PATH=$(echo "$TEMPLATE_URL" | sed -E 's|https?://[^/]+||') + + IMPORT_URL="https://oauth2:${GITLAB_ACCESS_TOKEN}@${PARSED_HOST}${PARSED_PATH}.git" +fi + +CREATE_REPO_BODY="{ + \"name\": \"$REPOSITORY_NAME\", + \"namespace_id\": $GITLAB_GROUP_ID, + \"visibility\": \"private\", + \"import_url\": \"$IMPORT_URL\"}" + +echo "Creating repository with body: " +echo "$CREATE_REPO_BODY" | jq . + +CREATE_RESPONSE=$(curl --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + --header "Content-Type: application/json" \ + --data "$CREATE_REPO_BODY" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects") + +GITLAB_PROJECT_ID=$(echo "$CREATE_RESPONSE" | jq -r '.id') + +if [ -z "$GITLAB_PROJECT_ID" ] || [ "$GITLAB_PROJECT_ID" == "null" ]; then + echo "Error creating repository:" + echo "$CREATE_RESPONSE" | jq + exit 1 +fi + +echo "Repository created with ID: $GITLAB_PROJECT_ID" + +export GITLAB_PROJECT_ID \ No newline at end of file diff --git a/application/scripts/code-repo/gitlab/create_secrets b/application/scripts/code-repo/gitlab/create_secrets new file mode 100644 index 00000000..fb72b31e --- /dev/null +++ b/application/scripts/code-repo/gitlab/create_secrets @@ -0,0 +1,29 @@ +#!/bin/bash + +echo "$CODE_REPOSITORY_SECRETS" \ +| jq -r 'to_entries[] | [.key, (.value|tostring)] | @tsv' \ +| while IFS=$'\t' read -r key value; do + echo "Creating secret: $key" + + curl -s -o /dev/null -w "" --request DELETE \ + --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${GITLAB_PROJECT_ID}/variables/$key" \ + >/dev/null 2>&1 || true + + SECRET_RESPONSE=$(curl -s --request POST \ + --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + --header "Content-Type: application/json" \ + --data "$(jq -n \ + --arg key "$key" \ + --arg value "$value" \ + '{ key: $key, value: $value, protected: false, masked: true }')" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${GITLAB_PROJECT_ID}/variables" + ) + + if echo "$SECRET_RESPONSE" | jq -e '.key' > /dev/null 2>&1; then + echo "Secret $key created successfully" + else + echo "Error creating $key secret:" + echo "$SECRET_RESPONSE" | jq + fi +done \ No newline at end of file diff --git a/application/scripts/code-repo/gitlab/run_first_build b/application/scripts/code-repo/gitlab/run_first_build new file mode 100644 index 00000000..7842b062 --- /dev/null +++ b/application/scripts/code-repo/gitlab/run_first_build @@ -0,0 +1,27 @@ +#!/bin/bash + +PIPELINE_RESPONSE=$(curl -s --request POST --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${GITLAB_PROJECT_ID}/pipeline?ref=main" 2>&1 || echo "") + +if echo "$PIPELINE_RESPONSE" | jq -e '.id' > /dev/null 2>&1; then + echo "Pipeline triggered successfully" +else + echo "Could not trigger pipeline directly, trying to create a commit..." + + # Create an empty commit to trigger CI + COMMIT_RESPONSE=$(curl -s --request POST --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + --header "Content-Type: application/json" \ + --data "{ + \"branch\": \"main\", + \"commit_message\": \"Trigger CI\", + \"actions\": [] + }" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${GITLAB_PROJECT_ID}/repository/commits") + + if echo "$COMMIT_RESPONSE" | jq -e '.id' > /dev/null 2>&1; then + echo "Commit created to trigger CI" + else + echo "Warning: Could not trigger CI automatically" + echo "$COMMIT_RESPONSE" | jq + fi +fi diff --git a/application/scripts/code-repo/gitlab/validate_repository_does_not_exist b/application/scripts/code-repo/gitlab/validate_repository_does_not_exist new file mode 100644 index 00000000..06ecff8e --- /dev/null +++ b/application/scripts/code-repo/gitlab/validate_repository_does_not_exist @@ -0,0 +1,28 @@ +#!/bin/bash + +echo "Checking if repository exists: $GITLAB_INSTALLATION_URL/$GITLAB_GROUP_PATH/$REPOSITORY_NAME" + +REPO_CHECK=$(curl -s --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${GITLAB_ENCODED_GROUP_PATH}%2F${REPOSITORY_NAME}" || echo "") + +if echo "$REPO_CHECK" | jq -e '.id' > /dev/null 2>&1; then + # Repository exists + if [ "$CODE_REPOSITORY_STRATEGY" = "create" ]; then + echo "Error: Repository already exists but strategy is set to 'create'. Please use a different repository name or change strategy to 'import'." + exit 1 + fi + + GITLAB_PROJECT_ID=$(echo "$REPO_CHECK" | jq -r '.id') + + export GITLAB_PROJECT_ID + + echo "Repository found and strategy is set to 'import'. Proceeding with import configuration..." +elif [ "$CODE_REPOSITORY_STRATEGY" = "import" ]; then + echo "Error: Repository does not exist but strategy is set to 'import'. Please create the repository first or change strategy to 'create'." + exit 1 +else + echo "Repository does not exist and trategy is set to 'create'. Proceeding with repository creation..." +fi + + + diff --git a/application/workflows/create_app.yaml b/application/workflows/create_app.yaml new file mode 100644 index 00000000..4f6e79ea --- /dev/null +++ b/application/workflows/create_app.yaml @@ -0,0 +1,10 @@ +steps: + - name: base_context + type: script + file: application/scripts/base_context + - name: create_code_repository + type: script + file: application/scripts/code-repo/create_code_repository + - name: create_asset_repository + type: script + file: application/scripts/asset-repo/create_asset_repository \ No newline at end of file diff --git a/application/workflows/create_asset_repository.yaml b/application/workflows/create_asset_repository.yaml new file mode 100644 index 00000000..6acd3ee1 --- /dev/null +++ b/application/workflows/create_asset_repository.yaml @@ -0,0 +1,10 @@ +steps: + - name: build_context + type: script + file: "$ASSET_REPOSITORY_SCRIPT_PATH/build_context" + - name: generate_repository_uri + type: script + file: "$ASSET_REPOSITORY_SCRIPT_PATH/generate_repository_uri" + - name: create_repository + type: script + file: "$ASSET_REPOSITORY_SCRIPT_PATH/create_repository" \ No newline at end of file diff --git a/application/workflows/create_code_repository.yaml b/application/workflows/create_code_repository.yaml new file mode 100644 index 00000000..8bedd022 --- /dev/null +++ b/application/workflows/create_code_repository.yaml @@ -0,0 +1,19 @@ +steps: + - name: build_context + type: script + file: "$CODE_REPOSITORY_SCRIPT_PATH/build_context" + - name: validate_repository_does_not_exist + type: script + file: "$CODE_REPOSITORY_SCRIPT_PATH/validate_repository_does_not_exist" + - name: create_repository + type: script + file: "$CODE_REPOSITORY_SCRIPT_PATH/create_repository" + - name: generate_secrets + type: script + file: "application/scripts/code-repo/generate_secrets" + - name: create_secrets + type: script + file: "$CODE_REPOSITORY_SCRIPT_PATH/create_secrets" + - name: run_first_build + type: script + file: "$CODE_REPOSITORY_SCRIPT_PATH/run_first_build" \ No newline at end of file From b65cd985986f924acfdc55f3528142006bf20247 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 15:27:06 -0300 Subject: [PATCH 34/59] feat: add debug logs --- k8s/metric/build_context | 9 +++++++++ service/metric/entrypoint | 15 ++++++++++++++- 2 files changed, 23 insertions(+), 1 deletion(-) diff --git a/k8s/metric/build_context b/k8s/metric/build_context index 8328aad8..9af74c68 100755 --- a/k8s/metric/build_context +++ b/k8s/metric/build_context @@ -3,6 +3,15 @@ SCOPE_ID=$(echo "$CONTEXT" | jq -r '.arguments.scope_id // empty') K8S_NAMESPACE=${K8S_NAMESPACE:-"nullplatform"} +LOGFILE="$HOME/metric_debug.log" +{ + date + printf 'SCOPE_ID=%s\n' "$SCOPE_ID" + printf 'K8S_NAMESPACE=%s\n' "$K8S_NAMESPACE" + printf 'PROMETHEUS_URL=%s\n' "$PROMETHEUS_URL" + echo '---' +} >> "$LOGFILE" + if [[ -z "$PROMETHEUS_URL" ]]; then NRN=$(np scope read --id "$SCOPE_ID" --format json | jq -r .nrn) diff --git a/service/metric/entrypoint b/service/metric/entrypoint index 43d191fb..69d45569 100755 --- a/service/metric/entrypoint +++ b/service/metric/entrypoint @@ -8,7 +8,20 @@ if [[ "$NOTIFICATION_ACTION" == "metric:list" ]]; then OVERRIDES_WORKFLOW_PATH="$OVERRIDES_PATH/metric/workflows/list.yaml" fi -CMD="np service workflow exec --no-output --workflow $WORKFLOW_PATH" +# append debug info to a file in $HOME +LOGFILE="$HOME/metric_debug.log" +{ + date + printf 'SERVICE_PATH=%s\n' "$SERVICE_PATH" + printf 'OVERRIDES_PATH=%s\n' "$OVERRIDES_PATH" + printf 'NOTIFICATION_ACTION=%s\n' "$NOTIFICATION_ACTION" + printf 'WORKFLOW_PATH=%s\n' "$WORKFLOW_PATH" + printf 'OVERRIDES_WORKFLOW_PATH=%s\n' "$OVERRIDES_WORKFLOW_PATH" + printf 'CMD=%s\n' "$CMD" + echo '---' +} >> "$LOGFILE" + +CMD="np service workflow exec --workflow $WORKFLOW_PATH" if [[ -f "$OVERRIDES_WORKFLOW_PATH" ]]; then CMD="$CMD --overrides $OVERRIDES_WORKFLOW_PATH" From 44acc879e59257ecc34b22636b3c8b3ea692ae5c Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 15:35:43 -0300 Subject: [PATCH 35/59] feat: add debug logs --- k8s/metric/build_context | 7 +++++++ k8s/metric/metric | 20 ++++++++++++++++++++ 2 files changed, 27 insertions(+) diff --git a/k8s/metric/build_context b/k8s/metric/build_context index 9af74c68..bd2e1109 100755 --- a/k8s/metric/build_context +++ b/k8s/metric/build_context @@ -39,6 +39,13 @@ if [[ -n "$METRIC" ]]; then export METRIC_NAME="$METRIC" fi +LOGFILE="$HOME/metric_debug.log" +{ + date + printf 'METRIC_NAME =%s\n' "$METRIC_NAME" + echo '---' +} >> "$LOGFILE" + export PROM_URL export K8S_NAMESPACE export SCOPE_ID \ No newline at end of file diff --git a/k8s/metric/metric b/k8s/metric/metric index 49fb97b9..ea836251 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -2,6 +2,14 @@ GROUP_BY=${GROUP_BY:-""} +LOGFILE="$HOME/metric_debug.log" +{ + date + printf 'METRIC FILE: METRIC_NAME =%s\n' "$METRIC_NAME" + echo '---' +} >> "$LOGFILE" + + # Validate required parameters if [[ -z "$METRIC_NAME" ]]; then echo '{"metric":"","type":"","period_in_seconds":0,"unit":"","results":[]}' @@ -204,6 +212,18 @@ query_prometheus() { local url="${PROM_URL}/api/v1/query_range" local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" + LOGFILE="$HOME/metric_debug.log" + { + date + printf 'PROMETHEUS QUERY URL=%s\n' "$url" + printf 'PROMETHEUS QUERY PARAMS=%s\n' "$params" + printf 'PROMETHEUS QUERY=%s\n' "$query" + printf 'START TIME=%s\n' "$start_time" + printf 'END TIME=%s\n' "$end_time" + printf 'STEP=%s\n' "$step" + echo '---' + } >> "$LOGFILE" + curl -s -G "$url" --data-urlencode "query=$query" --data-urlencode "start=$start_time" --data-urlencode "end=$end_time" --data-urlencode "step=${step}s" } From 4f6cc35d93e44a2b61cad6c068d6c74b3ec29b89 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 15:55:46 -0300 Subject: [PATCH 36/59] feat: add debug logs --- k8s/metric/metric | 1 + 1 file changed, 1 insertion(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index ea836251..470b6a5a 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -215,6 +215,7 @@ query_prometheus() { LOGFILE="$HOME/metric_debug.log" { date + printf 'NP_ACTION_CONTEXT=%s\n' "$NP_ACTION_CONTEXT" printf 'PROMETHEUS QUERY URL=%s\n' "$url" printf 'PROMETHEUS QUERY PARAMS=%s\n' "$params" printf 'PROMETHEUS QUERY=%s\n' "$query" From 0f55051df04153535ab1f09fc5344a014f25e72e Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 16:00:15 -0300 Subject: [PATCH 37/59] feat: add debug logs --- k8s/metric/metric | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 470b6a5a..0beb515f 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -225,7 +225,9 @@ query_prometheus() { echo '---' } >> "$LOGFILE" - curl -s -G "$url" --data-urlencode "query=$query" --data-urlencode "start=$start_time" --data-urlencode "end=$end_time" --data-urlencode "step=${step}s" + local token=$(cat /var/run/secrets/kubernetes.io/serviceaccount/token) + + curl -k -H "Authorization: Bearer $token" -G "$url" --data-urlencode "query=$query" --data-urlencode "start=$start_time" --data-urlencode "end=$end_time" --data-urlencode "step=${step}s" } urlencode() { From 18d137399957490be41246d82d60049dce693712 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 16:04:51 -0300 Subject: [PATCH 38/59] feat: add debug logs --- k8s/metric/metric | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index 0beb515f..fe508176 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -318,6 +318,14 @@ filters=$(build_filters) query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") response=$(query_prometheus "$query" "$start_time" "$now" "$step") +# print response to logfile +LOGFILE="$HOME/metric_debug.log" +{ + date + printf 'PROMETHEUS RESPONSE=%s\n' "$response" + echo '---' +} >> "$LOGFILE" + transform_response() { local response="$1" From d64a3da1a994c7ef193171cc70b8a2c697fc840a Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 16:09:56 -0300 Subject: [PATCH 39/59] feat: add debug logs --- k8s/metric/metric | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index fe508176..1e6ada89 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -353,5 +353,14 @@ transform_response() { } transformed_results=$(transform_response "$response") +# Output results to log file +{ + date + printf 'TRANSFORMED RESULTS=%s\n' "$transformed_results" + printf 'METRIC TYPE=%s\n' "$metric_type" + printf 'UNIT=%s\n' "$unit" + echo '---' +} >> "$LOGFILE" + echo "{\"metric\":\"$METRIC_NAME\",\"type\":\"$metric_type\",\"period_in_seconds\":$step,\"unit\":\"$unit\",\"results\":$transformed_results}" From d72fb91933e5eddec52d7494059338bbe8cc2e11 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 17:17:15 -0300 Subject: [PATCH 40/59] feat: restablish no output --- service/metric/entrypoint | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/service/metric/entrypoint b/service/metric/entrypoint index 69d45569..a88c4162 100755 --- a/service/metric/entrypoint +++ b/service/metric/entrypoint @@ -21,7 +21,7 @@ LOGFILE="$HOME/metric_debug.log" echo '---' } >> "$LOGFILE" -CMD="np service workflow exec --workflow $WORKFLOW_PATH" +CMD="np service workflow exec --no-output --workflow $WORKFLOW_PATH" if [[ -f "$OVERRIDES_WORKFLOW_PATH" ]]; then CMD="$CMD --overrides $OVERRIDES_WORKFLOW_PATH" From ea676694db8aee5dc93584f131314ced1ced85e2 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 17:27:31 -0300 Subject: [PATCH 41/59] feat: override workflow for openshift token --- azure-aro/metric/get_prom_token | 4 ++++ azure-aro/metric/workflows/metric.yaml | 5 +++++ k8s/metric/metric | 15 +++++++++++++-- 3 files changed, 22 insertions(+), 2 deletions(-) create mode 100644 azure-aro/metric/get_prom_token create mode 100644 azure-aro/metric/workflows/metric.yaml diff --git a/azure-aro/metric/get_prom_token b/azure-aro/metric/get_prom_token new file mode 100644 index 00000000..6381ee79 --- /dev/null +++ b/azure-aro/metric/get_prom_token @@ -0,0 +1,4 @@ +#!/bin/bash + +PROMETHEUS_TOKEN=$(cat /var/run/secrets/kubernetes.io/serviceaccount/token) +export PROMETHEUS_TOKEN \ No newline at end of file diff --git a/azure-aro/metric/workflows/metric.yaml b/azure-aro/metric/workflows/metric.yaml new file mode 100644 index 00000000..0702337c --- /dev/null +++ b/azure-aro/metric/workflows/metric.yaml @@ -0,0 +1,5 @@ +steps: + - name: get prometheus token + type: script + file: "$OVERRIDES_PATH/metric/get_prom_token" + after: build context \ No newline at end of file diff --git a/k8s/metric/metric b/k8s/metric/metric index 1e6ada89..5383fe11 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -225,9 +225,20 @@ query_prometheus() { echo '---' } >> "$LOGFILE" - local token=$(cat /var/run/secrets/kubernetes.io/serviceaccount/token) - curl -k -H "Authorization: Bearer $token" -G "$url" --data-urlencode "query=$query" --data-urlencode "start=$start_time" --data-urlencode "end=$end_time" --data-urlencode "step=${step}s" + if [[ -n "$PROMETHEUS_TOKEN" ]]; then + curl -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ + --data-urlencode "query=$query" \ + --data-urlencode "start=$start_time" \ + --data-urlencode "end=$end_time" \ + --data-urlencode "step=${step}s" + else + curl -k -G "$url" \ + --data-urlencode "query=$query" \ + --data-urlencode "start=$start_time" \ + --data-urlencode "end=$end_time" \ + --data-urlencode "step=${step}s" + fi } urlencode() { From 4143def8791a39e1f197a219f0a7b4c27ccd05f3 Mon Sep 17 00:00:00 2001 From: Javi Date: Mon, 10 Nov 2025 17:33:54 -0300 Subject: [PATCH 42/59] feat: remove file logging --- k8s/metric/build_context | 16 ---------------- k8s/metric/metric | 39 --------------------------------------- service/metric/entrypoint | 13 ------------- 3 files changed, 68 deletions(-) diff --git a/k8s/metric/build_context b/k8s/metric/build_context index bd2e1109..8328aad8 100755 --- a/k8s/metric/build_context +++ b/k8s/metric/build_context @@ -3,15 +3,6 @@ SCOPE_ID=$(echo "$CONTEXT" | jq -r '.arguments.scope_id // empty') K8S_NAMESPACE=${K8S_NAMESPACE:-"nullplatform"} -LOGFILE="$HOME/metric_debug.log" -{ - date - printf 'SCOPE_ID=%s\n' "$SCOPE_ID" - printf 'K8S_NAMESPACE=%s\n' "$K8S_NAMESPACE" - printf 'PROMETHEUS_URL=%s\n' "$PROMETHEUS_URL" - echo '---' -} >> "$LOGFILE" - if [[ -z "$PROMETHEUS_URL" ]]; then NRN=$(np scope read --id "$SCOPE_ID" --format json | jq -r .nrn) @@ -39,13 +30,6 @@ if [[ -n "$METRIC" ]]; then export METRIC_NAME="$METRIC" fi -LOGFILE="$HOME/metric_debug.log" -{ - date - printf 'METRIC_NAME =%s\n' "$METRIC_NAME" - echo '---' -} >> "$LOGFILE" - export PROM_URL export K8S_NAMESPACE export SCOPE_ID \ No newline at end of file diff --git a/k8s/metric/metric b/k8s/metric/metric index 5383fe11..968326b4 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -2,14 +2,6 @@ GROUP_BY=${GROUP_BY:-""} -LOGFILE="$HOME/metric_debug.log" -{ - date - printf 'METRIC FILE: METRIC_NAME =%s\n' "$METRIC_NAME" - echo '---' -} >> "$LOGFILE" - - # Validate required parameters if [[ -z "$METRIC_NAME" ]]; then echo '{"metric":"","type":"","period_in_seconds":0,"unit":"","results":[]}' @@ -212,20 +204,6 @@ query_prometheus() { local url="${PROM_URL}/api/v1/query_range" local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" - LOGFILE="$HOME/metric_debug.log" - { - date - printf 'NP_ACTION_CONTEXT=%s\n' "$NP_ACTION_CONTEXT" - printf 'PROMETHEUS QUERY URL=%s\n' "$url" - printf 'PROMETHEUS QUERY PARAMS=%s\n' "$params" - printf 'PROMETHEUS QUERY=%s\n' "$query" - printf 'START TIME=%s\n' "$start_time" - printf 'END TIME=%s\n' "$end_time" - printf 'STEP=%s\n' "$step" - echo '---' - } >> "$LOGFILE" - - if [[ -n "$PROMETHEUS_TOKEN" ]]; then curl -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ --data-urlencode "query=$query" \ @@ -329,14 +307,6 @@ filters=$(build_filters) query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") response=$(query_prometheus "$query" "$start_time" "$now" "$step") -# print response to logfile -LOGFILE="$HOME/metric_debug.log" -{ - date - printf 'PROMETHEUS RESPONSE=%s\n' "$response" - echo '---' -} >> "$LOGFILE" - transform_response() { local response="$1" @@ -364,14 +334,5 @@ transform_response() { } transformed_results=$(transform_response "$response") -# Output results to log file -{ - date - printf 'TRANSFORMED RESULTS=%s\n' "$transformed_results" - printf 'METRIC TYPE=%s\n' "$metric_type" - printf 'UNIT=%s\n' "$unit" - echo '---' -} >> "$LOGFILE" - echo "{\"metric\":\"$METRIC_NAME\",\"type\":\"$metric_type\",\"period_in_seconds\":$step,\"unit\":\"$unit\",\"results\":$transformed_results}" diff --git a/service/metric/entrypoint b/service/metric/entrypoint index a88c4162..43d191fb 100755 --- a/service/metric/entrypoint +++ b/service/metric/entrypoint @@ -8,19 +8,6 @@ if [[ "$NOTIFICATION_ACTION" == "metric:list" ]]; then OVERRIDES_WORKFLOW_PATH="$OVERRIDES_PATH/metric/workflows/list.yaml" fi -# append debug info to a file in $HOME -LOGFILE="$HOME/metric_debug.log" -{ - date - printf 'SERVICE_PATH=%s\n' "$SERVICE_PATH" - printf 'OVERRIDES_PATH=%s\n' "$OVERRIDES_PATH" - printf 'NOTIFICATION_ACTION=%s\n' "$NOTIFICATION_ACTION" - printf 'WORKFLOW_PATH=%s\n' "$WORKFLOW_PATH" - printf 'OVERRIDES_WORKFLOW_PATH=%s\n' "$OVERRIDES_WORKFLOW_PATH" - printf 'CMD=%s\n' "$CMD" - echo '---' -} >> "$LOGFILE" - CMD="np service workflow exec --no-output --workflow $WORKFLOW_PATH" if [[ -f "$OVERRIDES_WORKFLOW_PATH" ]]; then From 9c855053f223f2125413cd60882ff345a524b2e0 Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Wed, 12 Nov 2025 12:21:24 -0300 Subject: [PATCH 43/59] Merge feature/create-applications --- application/entrypoint | 32 +++++++++++++++++-- .../scripts/code-repo/create_code_repository | 10 +++--- .../scripts/code-repo/generate_secrets | 16 ++++------ .../scripts/code-repo/gitlab/run_first_build | 4 ++- .../gitlab/validate_repository_does_not_exist | 7 ++-- datadog/metric/metric | 8 ++++- 6 files changed, 52 insertions(+), 25 deletions(-) diff --git a/application/entrypoint b/application/entrypoint index f1bcb7bf..02b756e8 100755 --- a/application/entrypoint +++ b/application/entrypoint @@ -12,9 +12,8 @@ TOKEN=$(np token create --body "{\"api_key\": \"$NP_API_KEY\"}" --format json | CALLBACK_URL=$(echo "$NP_ACTION_CONTEXT" | jq -r .notification.callback_url) -np service workflow exec --workflow application/workflows/create_app.yaml +logs=$(np service workflow exec --workflow application/workflows/create_app.yaml) EXIT_CODE=$? - # Determine status based on exit code if [ $EXIT_CODE -eq 0 ]; then STATUS="success" @@ -22,13 +21,40 @@ else STATUS="failed" fi +timestamp=$(($(date +%s) * 1000)) + +messages=$(echo "$logs" | while IFS= read -r line; do + [[ -z "$line" ]] && continue + + if [[ "$line" =~ "failed" ]] || [[ "$line" =~ "ERROR" ]] || [[ "$line" =~ "error" ]]; then + level="ERROR" + elif [[ "$line" =~ "warning" ]] || [[ "$line" =~ "WARNING" ]] || [[ "$line" =~ "warn" ]]; then + level="WARNING" + else + level="INFO" + fi + + jq -n \ + --arg level "$level" \ + --arg message "$line" \ + --arg ts "$timestamp" \ + '{level: $level, message: $message, timestamp: ($ts | tonumber)}' +done | jq -s '.') + +payload=$(jq -n \ + --arg status "$STATUS" \ + --argjson messages "$messages" \ + '{status: $status, messages: $messages}') + +echo "$payload" | jq . + echo "Updating hook with status: $STATUS. URL: $CALLBACK_URL" # Call the callback URL with the status HTTP_CODE=$(curl -s -o /dev/null -w "%{http_code}" -X PATCH "$CALLBACK_URL" \ -H "Authorization: Bearer $TOKEN" \ -H "Content-Type: application/json" \ - -d "{\"status\": \"$STATUS\"}") + -d "$payload") if [ "$HTTP_CODE" -ge 200 ] && [ "$HTTP_CODE" -lt 300 ]; then echo "✓ Successfully updated hook (HTTP $HTTP_CODE)" diff --git a/application/scripts/code-repo/create_code_repository b/application/scripts/code-repo/create_code_repository index 43c2a677..ca71d070 100644 --- a/application/scripts/code-repo/create_code_repository +++ b/application/scripts/code-repo/create_code_repository @@ -3,22 +3,20 @@ CURRENT_DIR=$(dirname "${BASH_SOURCE[0]}") REPOSITORY_URL=$(echo "$APPLICATION" | jq -r .repository_url) +TEMPLATE_ID=$(echo "$APPLICATION" | jq -r '.template_id // empty' ) -if [[ -z $REPOSITORY_URL ]]; then +if [[ -n "$TEMPLATE_ID" ]]; then CODE_REPOSITORY_STRATEGY=create - TEMPLATE_ID=$(echo "$APPLICATION" | jq -r .template_id) - TEMPLATE_URL=$(np template read --id "$TEMPLATE_ID" --format json | jq -r .url) export TEMPLATE_URL - - REPOSITORY_NAME=$NAMESPACE_SLUG-$APPLICATION_SLUG else - REPOSITORY_NAME=$(basename "$REPOSITORY_URL") CODE_REPOSITORY_STRATEGY=import fi +REPOSITORY_NAME=$(basename "$REPOSITORY_URL") + ACCOUNT=$(np account read --id "$ACCOUNT_ID" --format json) REPOSITORY_PROVIDER=$(echo "$ACCOUNT" | jq -r .repository_provider) diff --git a/application/scripts/code-repo/generate_secrets b/application/scripts/code-repo/generate_secrets index 3edb322f..a3af865e 100644 --- a/application/scripts/code-repo/generate_secrets +++ b/application/scripts/code-repo/generate_secrets @@ -4,23 +4,21 @@ CI_ROLE_ID=1855672260 # TODO(federico.maleh) missing support for extra secrets # TODO(federico.maleh) missing support for extra roles in api key # TODO(federico.maleh) missing add collaborators -# TODO(federico.maleh) missing support for no template use case API_KEY_NAME="ci-$NAMESPACE_SLUG-$NAMESPACE_ID-$APPLICATION_SLUG-$APPLICATION_ID" echo "Creating api key for ci: $API_KEY_NAME" -API_KEY_RESPONSE=$(np api-key create --format json --body "{ - \"name\": \"$API_KEY_NAME\", - \"grants\": [ - {\"nrn\": \"$NRN\", \"role_id\": $CI_ROLE_ID} - ], - \"tags\": [{ \"key\": \"ci\", \"value\": true }], - \"internal\": true -}") +API_KEY_BODY=$(jq -nc \ + --arg name "$API_KEY_NAME" \ + --arg nrn "$NRN" \ + --argjson role_id "$CI_ROLE_ID" \ + '{name: $name, grants: [{nrn: $nrn, role_id: $role_id}], tags: [{key: "ci", value: true}], internal: true}') +API_KEY_RESPONSE=$(np api-key create --format json --body "$API_KEY_BODY") API_KEY=$(echo "$API_KEY_RESPONSE" | jq -r .api_key) + echo "Created api key for ci" CODE_REPOSITORY_SECRETS="{\"NP_API_KEY\": \"$API_KEY\"}" diff --git a/application/scripts/code-repo/gitlab/run_first_build b/application/scripts/code-repo/gitlab/run_first_build index 7842b062..74bf1fd0 100644 --- a/application/scripts/code-repo/gitlab/run_first_build +++ b/application/scripts/code-repo/gitlab/run_first_build @@ -23,5 +23,7 @@ else else echo "Warning: Could not trigger CI automatically" echo "$COMMIT_RESPONSE" | jq + + exit 1 fi -fi +fi \ No newline at end of file diff --git a/application/scripts/code-repo/gitlab/validate_repository_does_not_exist b/application/scripts/code-repo/gitlab/validate_repository_does_not_exist index 06ecff8e..215a2ed3 100644 --- a/application/scripts/code-repo/gitlab/validate_repository_does_not_exist +++ b/application/scripts/code-repo/gitlab/validate_repository_does_not_exist @@ -21,8 +21,5 @@ elif [ "$CODE_REPOSITORY_STRATEGY" = "import" ]; then echo "Error: Repository does not exist but strategy is set to 'import'. Please create the repository first or change strategy to 'create'." exit 1 else - echo "Repository does not exist and trategy is set to 'create'. Proceeding with repository creation..." -fi - - - + echo "Repository does not exist and strategy is set to 'create'. Proceeding with repository creation..." +fi \ No newline at end of file diff --git a/datadog/metric/metric b/datadog/metric/metric index 244c7bcb..656a7cd0 100755 --- a/datadog/metric/metric +++ b/datadog/metric/metric @@ -135,7 +135,13 @@ build_datadog_query() { local p99_interval=$((end_time - start_time)) echo "p99:trace.http.request{service:$service_name,env:$env_name}.rollup(avg, $p99_interval) * 1000" ;; - + p??:*) + local env_name=$(echo "$CONTEXT" | jq -r '.service.dimensions.environment') + local service_name=$(basename $(echo "$CONTEXT" | jq -r '.tags.repository_url'))-kubernetes + + local percentile_interval=$((end_time - start_time)) + echo "$metric{service:$service_name,env:$env_name}.rollup(avg, $percentile_interval) * 1000" + ;; # Generic handler for any other Datadog metric *) echo "avg:$metric{$filters}$group_clause" From 341efd8e60161c50a5d180e90f25d523d6bb128c Mon Sep 17 00:00:00 2001 From: Federico Maleh Date: Mon, 17 Nov 2025 11:06:30 -0300 Subject: [PATCH 44/59] Add latest applications code --- .../asset-repo/create_asset_repository | 12 ++- .../asset-repo/docker-server/build_context | 24 +++++- .../scripts/code-repo/create_code_repository | 16 +++- .../scripts/code-repo/generate_secrets | 13 +++- .../code-repo/gitlab/add_collaborators | 74 +++++++++++++++++++ .../scripts/code-repo/gitlab/build_context | 24 +++++- .../scripts/code-repo/gitlab/run_first_build | 1 - .../workflows/create_code_repository.yaml | 3 + 8 files changed, 150 insertions(+), 17 deletions(-) create mode 100644 application/scripts/code-repo/gitlab/add_collaborators diff --git a/application/scripts/asset-repo/create_asset_repository b/application/scripts/asset-repo/create_asset_repository index 9fe5d6c7..308cc150 100644 --- a/application/scripts/asset-repo/create_asset_repository +++ b/application/scripts/asset-repo/create_asset_repository @@ -1,11 +1,17 @@ #!/bin/bash ASSET_REPOSITORY=$(np provider list --categories assets-repository --nrn "$NRN" --format json | jq ".results[0]") -ASSET_REPOSITORY_SPEC=$(echo "$ASSET_REPOSITORY" | jq -r .specification_id) -REPOSITORY_PROVIDER=$(np provider specification read --id "$ASSET_REPOSITORY_SPEC" --format json | jq -r .slug) +if [[ -n "$ASSET_REPOSITORY_PROVIDER" ]]; then + echo "Using ASSET_REPOSITORY_PROVIDER from environment: $ASSET_REPOSITORY_PROVIDER" +else + ASSET_REPOSITORY_SPEC=$(echo "$ASSET_REPOSITORY" | jq -r .specification_id) + ASSET_REPOSITORY_PROVIDER=$(np provider specification read --id "$ASSET_REPOSITORY_SPEC" --format json | jq -r .slug) -ASSET_REPOSITORY_SCRIPT_PATH="application/scripts/asset-repo/$REPOSITORY_PROVIDER" + echo "No ASSET_REPOSITORY_PROVIDER configured from environment, will use the provider configured in platform settings: $ASSET_REPOSITORY_PROVIDER" +fi + +ASSET_REPOSITORY_SCRIPT_PATH="application/scripts/asset-repo/$ASSET_REPOSITORY_PROVIDER" export ASSET_REPOSITORY_TYPE export ASSET_REPOSITORY diff --git a/application/scripts/asset-repo/docker-server/build_context b/application/scripts/asset-repo/docker-server/build_context index 7321cdc7..0d4836a5 100644 --- a/application/scripts/asset-repo/docker-server/build_context +++ b/application/scripts/asset-repo/docker-server/build_context @@ -1,8 +1,26 @@ #!/bin/bash -DOCKER_SERVER_URL=$(echo "$ASSET_REPOSITORY" | jq -r .attributes.setup.server) -DOCKER_SERVER_PATH=$(echo "$ASSET_REPOSITORY" | jq -r .attributes.setup.path) -DOCKER_SERVER_USE_NAMESPACE=$(echo "$ASSET_REPOSITORY" | jq -r .attributes.setup.use_namespace) +if [[ -n "$DOCKER_SERVER_URL" ]]; then + echo "Using DOCKER_SERVER_URL from environment: $DOCKER_SERVER_URL" +else + DOCKER_SERVER_URL=$(echo "$ASSET_REPOSITORY" | jq -r '.attributes.setup.server') + echo "No DOCKER_SERVER_URL in environment, using value from platform: $DOCKER_SERVER_URL" +fi + +if [[ -n "$DOCKER_SERVER_PATH" ]]; then + echo "Using DOCKER_SERVER_PATH from environment: $DOCKER_SERVER_PATH" +else + DOCKER_SERVER_PATH=$(echo "$ASSET_REPOSITORY" | jq -r '.attributes.setup.path') + echo "No DOCKER_SERVER_PATH in environment, using value from platform: $DOCKER_SERVER_PATH" +fi + +if [[ -n "$DOCKER_SERVER_USE_NAMESPACE" ]]; then + echo "Using DOCKER_SERVER_USE_NAMESPACE from environment: $DOCKER_SERVER_USE_NAMESPACE" +else + DOCKER_SERVER_USE_NAMESPACE=$(echo "$ASSET_REPOSITORY" | jq -r '.attributes.setup.use_namespace') + echo "No DOCKER_SERVER_USE_NAMESPACE in environment, using value from platform: $DOCKER_SERVER_USE_NAMESPACE" +fi + export DOCKER_SERVER_URL export DOCKER_SERVER_PATH diff --git a/application/scripts/code-repo/create_code_repository b/application/scripts/code-repo/create_code_repository index ca71d070..99cdd32c 100644 --- a/application/scripts/code-repo/create_code_repository +++ b/application/scripts/code-repo/create_code_repository @@ -17,13 +17,21 @@ fi REPOSITORY_NAME=$(basename "$REPOSITORY_URL") -ACCOUNT=$(np account read --id "$ACCOUNT_ID" --format json) +if [[ -n "$CODE_REPOSITORY_PROVIDER" ]]; then + echo "Using CODE_REPOSITORY_PROVIDER from environment: $CODE_REPOSITORY_PROVIDER" +else + ACCOUNT=$(np account read --id "$ACCOUNT_ID" --format json) + + CODE_REPOSITORY_PROVIDER=$(echo "$ACCOUNT" | jq -r .repository_provider) -REPOSITORY_PROVIDER=$(echo "$ACCOUNT" | jq -r .repository_provider) + echo "No CODE_REPOSITORY_PROVIDER configured from environment, will use the provider configured in the nullplatform account: $CODE_REPOSITORY_PROVIDER" +fi CODE_REPOSITORY=$(np provider list --categories code-repository --nrn "$NRN" --format json | jq ".results[0]") -CODE_REPOSITORY_SCRIPT_PATH="application/scripts/code-repo/$REPOSITORY_PROVIDER" +CODE_REPOSITORY_SCRIPT_PATH="application/scripts/code-repo/$CODE_REPOSITORY_PROVIDER" + +CODE_REPOSITORY_COLLABORATORS=$(echo "$CODE_REPOSITORY" | jq .attributes.access.default_collaborators) export CODE_REPOSITORY_STRATEGY @@ -31,7 +39,7 @@ export REPOSITORY_URL export REPOSITORY_NAME export CODE_REPOSITORY -export REPOSITORY_PROVIDER export CODE_REPOSITORY_SCRIPT_PATH +export CODE_REPOSITORY_COLLABORATORS np service workflow exec --workflow application/workflows/create_code_repository.yaml \ No newline at end of file diff --git a/application/scripts/code-repo/generate_secrets b/application/scripts/code-repo/generate_secrets index a3af865e..98c855a6 100644 --- a/application/scripts/code-repo/generate_secrets +++ b/application/scripts/code-repo/generate_secrets @@ -3,8 +3,7 @@ CI_ROLE_ID=1855672260 # TODO(federico.maleh) missing support for mono repo # TODO(federico.maleh) missing support for extra secrets # TODO(federico.maleh) missing support for extra roles in api key -# TODO(federico.maleh) missing add collaborators - + API_KEY_NAME="ci-$NAMESPACE_SLUG-$NAMESPACE_ID-$APPLICATION_SLUG-$APPLICATION_ID" echo "Creating api key for ci: $API_KEY_NAME" @@ -18,8 +17,16 @@ API_KEY_BODY=$(jq -nc \ API_KEY_RESPONSE=$(np api-key create --format json --body "$API_KEY_BODY") API_KEY=$(echo "$API_KEY_RESPONSE" | jq -r .api_key) +API_KEY_ID=$(echo "$API_KEY_RESPONSE" | jq -r .id) + +if [[ -n "$API_KEY_ID" ]]; then + echo "Created ci api key: $API_KEY_ID" +else + echo "Error creating ci api key" + echo "$API_API_KEY_RESPONSE" | jq -echo "Created api key for ci" + exit 1 +fi CODE_REPOSITORY_SECRETS="{\"NP_API_KEY\": \"$API_KEY\"}" diff --git a/application/scripts/code-repo/gitlab/add_collaborators b/application/scripts/code-repo/gitlab/add_collaborators new file mode 100644 index 00000000..bfd0f1be --- /dev/null +++ b/application/scripts/code-repo/gitlab/add_collaborators @@ -0,0 +1,74 @@ +#!/bin/bash + +PROJECT_PATH="${GITLAB_ENCODED_GROUP_PATH}%2F${REPOSITORY_NAME}" + +get_access_level() { + local role="$1" # Don't convert to uppercase + case $role in + guest) echo "10" ;; + reporter) echo "20" ;; + developer) echo "30" ;; + maintainer) echo "40" ;; + owner) echo "50" ;; + *) echo "30" ;; # default to DEVELOPER + esac +} + +# Function to get user ID from username +get_user_id() { + local username="$1" + curl --silent --header "PRIVATE-TOKEN: ${GITLAB_ACCESS_TOKEN}" \ + "${GITLAB_INSTALLATION_URL}/api/v4/users?username=${username}" | jq -r '.[0].id' +} + +# Function to get group ID from group path +get_group_id() { + local group_path="$1" + + curl --silent --header "PRIVATE-TOKEN: ${GITLAB_ACCESS_TOKEN}" \ + "${GITLAB_INSTALLATION_URL}/api/v4/groups/${group_path}" | jq -r '.id' +} + +echo "$CODE_REPOSITORY_COLLABORATORS" | jq -c '.[]' | while read -r collaborator; do + id=$(echo "$collaborator" | jq -r '.id') + role=$(echo "$collaborator" | jq -r '.role') + type=$(echo "$collaborator" | jq -r '.type') + access_level=$(get_access_level "$role") + + if [ "$type" = "user" ]; then + # Look up user ID from username + user_id=$(get_user_id "$id") + + if [ "$user_id" = "null" ] || [ -z "$user_id" ]; then + echo "Error: User '$id' not found" + continue + fi + + echo "Adding user '$id' (ID: $user_id) with role '$role' (access_level=$access_level)" + + curl --request POST \ + --header "PRIVATE-TOKEN: ${GITLAB_ACCESS_TOKEN}" \ + --data "user_id=${user_id}&access_level=${access_level}" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${PROJECT_PATH}/members" + echo "" + + elif [ "$type" = "group" ]; then + # Look up group ID from group path + group_id=$(get_group_id "$id") + + if [ "$group_id" = "null" ] || [ -z "$group_id" ]; then + echo "Error: Group '$id' not found" + continue + fi + + echo "Adding group '$id' (ID: $group_id) with role '$role' (access_level=$access_level)" + + curl --request POST \ + --header "PRIVATE-TOKEN: ${GITLAB_ACCESS_TOKEN}" \ + --data "group_id=${group_id}&group_access=${access_level}" \ + "${GITLAB_INSTALLATION_URL}/api/v4/projects/${PROJECT_PATH}/share" + echo "" + fi +done + +echo "Finished adding collaborators" \ No newline at end of file diff --git a/application/scripts/code-repo/gitlab/build_context b/application/scripts/code-repo/gitlab/build_context index 41ef45fb..e95b153b 100755 --- a/application/scripts/code-repo/gitlab/build_context +++ b/application/scripts/code-repo/gitlab/build_context @@ -1,8 +1,26 @@ #!/bin/bash -GITLAB_ACCESS_TOKEN=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.access_token') -GITLAB_GROUP_PATH=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.group_path') -GITLAB_INSTALLATION_URL=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.installation_url') +if [[ -n "$GITLAB_ACCESS_TOKEN" ]]; then + echo "Using GITLAB_ACCESS_TOKEN from environment (hidden)" +else + GITLAB_ACCESS_TOKEN=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.access_token') + echo "No GITLAB_ACCESS_TOKEN in environment, using value from platform (hidden)" +fi + +if [[ -n "$GITLAB_GROUP_PATH" ]]; then + echo "Using GITLAB_GROUP_PATH from environment: $GITLAB_GROUP_PATH" +else + GITLAB_GROUP_PATH=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.group_path') + echo "No GITLAB_GROUP_PATH in environment, using value from platform: $GITLAB_GROUP_PATH" +fi + +if [[ -n "$GITLAB_INSTALLATION_URL" ]]; then + echo "Using GITLAB_INSTALLATION_URL from environment: $GITLAB_INSTALLATION_URL" +else + GITLAB_INSTALLATION_URL=$(echo "$CODE_REPOSITORY" | jq -r '.attributes.setup.installation_url') + echo "No GITLAB_INSTALLATION_URL in environment, using value from platform: $GITLAB_INSTALLATION_URL" +fi + echo "Getting group ID for path: $GITLAB_GROUP_PATH" GROUP_RESPONSE=$(curl -s --header "PRIVATE-TOKEN: $GITLAB_ACCESS_TOKEN" \ diff --git a/application/scripts/code-repo/gitlab/run_first_build b/application/scripts/code-repo/gitlab/run_first_build index 74bf1fd0..e4e15c5b 100644 --- a/application/scripts/code-repo/gitlab/run_first_build +++ b/application/scripts/code-repo/gitlab/run_first_build @@ -24,6 +24,5 @@ else echo "Warning: Could not trigger CI automatically" echo "$COMMIT_RESPONSE" | jq - exit 1 fi fi \ No newline at end of file diff --git a/application/workflows/create_code_repository.yaml b/application/workflows/create_code_repository.yaml index 8bedd022..7a500284 100644 --- a/application/workflows/create_code_repository.yaml +++ b/application/workflows/create_code_repository.yaml @@ -8,6 +8,9 @@ steps: - name: create_repository type: script file: "$CODE_REPOSITORY_SCRIPT_PATH/create_repository" + - name: add_collaborators + type: script + file: "$CODE_REPOSITORY_SCRIPT_PATH/add_collaborators" - name: generate_secrets type: script file: "application/scripts/code-repo/generate_secrets" From 0744f966bc6e6e04f056bab1774d148f3a563ea5 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:07:48 -0300 Subject: [PATCH 45/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index 968326b4..f51832d4 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -203,6 +203,11 @@ query_prometheus() { local url="${PROM_URL}/api/v1/query_range" local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" + #add debuggin + echo "" + echo "$url" + echo "" + echo "$params" if [[ -n "$PROMETHEUS_TOKEN" ]]; then curl -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ @@ -307,6 +312,11 @@ filters=$(build_filters) query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") response=$(query_prometheus "$query" "$start_time" "$now" "$step") +## add debug +echo "$filters" +echo "$query" +echo "$response" + transform_response() { local response="$1" @@ -335,4 +345,7 @@ transform_response() { transformed_results=$(transform_response "$response") +#add debug +echo "$transformed_results" + echo "{\"metric\":\"$METRIC_NAME\",\"type\":\"$metric_type\",\"period_in_seconds\":$step,\"unit\":\"$unit\",\"results\":$transformed_results}" From 9fe575fa3fe75e92c1351456f45ab1f494a2ed71 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:13:18 -0300 Subject: [PATCH 46/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 1 + 1 file changed, 1 insertion(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index f51832d4..42b3f760 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -305,6 +305,7 @@ else fi config=$(get_metric_config) +echo "$config" metric_type=$(echo $config | cut -d' ' -f1) unit=$(echo $config | cut -d' ' -f2) From e5a9065238c654bce299b51d59a9e9746f4b0a9c Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:18:18 -0300 Subject: [PATCH 47/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 3 +++ 1 file changed, 3 insertions(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index 42b3f760..e1ef6123 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -322,6 +322,9 @@ echo "$response" transform_response() { local response="$1" local status=$(echo "$response" | jq -r '.status') + ##debug + echo "DEBUG: status = $status" + echo "DEBUG: response = $response" if [[ "$status" != "success" ]]; then echo "[]" From 82fce9564cfedf7f320d5432f34b9ce76151c141 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:24:10 -0300 Subject: [PATCH 48/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index e1ef6123..9dba0168 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -203,20 +203,25 @@ query_prometheus() { local url="${PROM_URL}/api/v1/query_range" local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" - #add debuggin - echo "" - echo "$url" - echo "" - echo "$params" + #########debug + local encoded_query=$(urlencode "$query") + local full_url="${url}?query=${encoded_query}&start=${start_time}&end=${end_time}&step=${step}s" + + echo "===============================================" + echo "FULL URL :" + echo "$full_url" + echo "===============================================" + + ########## if [[ -n "$PROMETHEUS_TOKEN" ]]; then - curl -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ + curl -v -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ --data-urlencode "end=$end_time" \ --data-urlencode "step=${step}s" else - curl -k -G "$url" \ + curl -v -k -G "$url" \ --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ --data-urlencode "end=$end_time" \ From b08a8b88020846ae645c8b1be37d04687f5b102e Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:42:43 -0300 Subject: [PATCH 49/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/k8s/metric/metric b/k8s/metric/metric index 9dba0168..6287ae2c 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -252,7 +252,14 @@ if [[ -n "$START_TIME" && -n "$END_TIME" ]]; then start_time=$(echo "$START_TIME" | sed 's/T/ /' | sed 's/\.[0-9]*Z$//' | xargs -I {} date -u -d "{}" +%s 2>/dev/null || echo "0") now=$(echo "$END_TIME" | sed 's/T/ /' | sed 's/\.[0-9]*Z$//' | xargs -I {} date -u -d "{}" +%s 2>/dev/null || echo "0") step=${PERIOD:-60} + current_time=$(date +%s) + if [[ $end_time -gt $current_time ]]; then + now=$current_time + else + now=$end_time + fi # Calculate interval like JavaScript service: period/60 + "m" + if [[ -n "$PERIOD" && "$PERIOD" -gt 0 ]]; then interval_minutes=$((PERIOD / 60)) if [[ $interval_minutes -lt 1 ]]; then From 94180163c63b7e4b50ed69c68fade4806f4a9b54 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:50:24 -0300 Subject: [PATCH 50/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 6287ae2c..e3655d3d 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -202,10 +202,11 @@ query_prometheus() { local step="$4" local url="${PROM_URL}/api/v1/query_range" - local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" + #remove s + local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}" #########debug local encoded_query=$(urlencode "$query") - local full_url="${url}?query=${encoded_query}&start=${start_time}&end=${end_time}&step=${step}s" + local full_url="${url}?query=${encoded_query}&start=${start_time}&end=${end_time}&step=${step}" echo "===============================================" echo "FULL URL :" @@ -219,13 +220,13 @@ query_prometheus() { --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ --data-urlencode "end=$end_time" \ - --data-urlencode "step=${step}s" + --data-urlencode "step=${step}" else curl -v -k -G "$url" \ --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ --data-urlencode "end=$end_time" \ - --data-urlencode "step=${step}s" + --data-urlencode "step=${step}" fi } From f3e76459e67d90e8c1529ae7f9a0716f69300e10 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 14:59:24 -0300 Subject: [PATCH 51/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index e3655d3d..b59288b3 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -198,7 +198,8 @@ build_query() { query_prometheus() { local query="$1" local start_time="$2" - local end_time="$3" + #local end_time="$3" + local end_time=$(date +%s) local step="$4" local url="${PROM_URL}/api/v1/query_range" @@ -253,12 +254,14 @@ if [[ -n "$START_TIME" && -n "$END_TIME" ]]; then start_time=$(echo "$START_TIME" | sed 's/T/ /' | sed 's/\.[0-9]*Z$//' | xargs -I {} date -u -d "{}" +%s 2>/dev/null || echo "0") now=$(echo "$END_TIME" | sed 's/T/ /' | sed 's/\.[0-9]*Z$//' | xargs -I {} date -u -d "{}" +%s 2>/dev/null || echo "0") step=${PERIOD:-60} + ##add current_time=$(date +%s) if [[ $end_time -gt $current_time ]]; then now=$current_time else now=$end_time fi + ###end # Calculate interval like JavaScript service: period/60 + "m" if [[ -n "$PERIOD" && "$PERIOD" -gt 0 ]]; then @@ -325,7 +328,7 @@ unit=$(echo $config | cut -d' ' -f2) filters=$(build_filters) query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") -response=$(query_prometheus "$query" "$start_time" "$now" "$step") +response=$(query_prometheus "$query" "$start_time" "$now" "$step"s) ## add debug echo "$filters" echo "$query" From ccd2bccbffbcda502a245bc3b6bb7f6882306767 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 15:01:56 -0300 Subject: [PATCH 52/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index b59288b3..855d44fc 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -339,8 +339,8 @@ transform_response() { local response="$1" local status=$(echo "$response" | jq -r '.status') ##debug - echo "DEBUG: status = $status" - echo "DEBUG: response = $response" + echo "DEBUG: status =" "$status" + echo "DEBUG: response =" "$response" if [[ "$status" != "success" ]]; then echo "[]" From c37a76396fda545a979510330c4c79843c5ccbdb Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 15:05:59 -0300 Subject: [PATCH 53/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 855d44fc..0f60cd16 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -339,8 +339,8 @@ transform_response() { local response="$1" local status=$(echo "$response" | jq -r '.status') ##debug - echo "DEBUG: status =" "$status" - echo "DEBUG: response =" "$response" + echo "$status" + echo "$response" if [[ "$status" != "success" ]]; then echo "[]" From 9ce2039f8de9efe83fb8e00e0d9fb03b78d58de2 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 15:10:08 -0300 Subject: [PATCH 54/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 18 +++++------------- 1 file changed, 5 insertions(+), 13 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 0f60cd16..f8bf4909 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -203,18 +203,9 @@ query_prometheus() { local step="$4" local url="${PROM_URL}/api/v1/query_range" - #remove s - local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}" - #########debug - local encoded_query=$(urlencode "$query") - local full_url="${url}?query=${encoded_query}&start=${start_time}&end=${end_time}&step=${step}" - - echo "===============================================" - echo "FULL URL :" - echo "$full_url" - echo "===============================================" - - ########## + + local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" + if [[ -n "$PROMETHEUS_TOKEN" ]]; then curl -v -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ @@ -328,7 +319,8 @@ unit=$(echo $config | cut -d' ' -f2) filters=$(build_filters) query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") -response=$(query_prometheus "$query" "$start_time" "$now" "$step"s) +#response=$(query_prometheus "$query" "$start_time" "$now" "$step") +response=$(query_prometheus "$query" "$start_time" "$(date +%s)" "$step") ## add debug echo "$filters" echo "$query" From 3d27fdcc2f27b8b39063349d7d9dc99a8a3054d7 Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 15:13:07 -0300 Subject: [PATCH 55/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index f8bf4909..3cc839ec 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -211,7 +211,7 @@ query_prometheus() { curl -v -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ - --data-urlencode "end=$end_time" \ + --data-urlencode "end=$(date +%s)" \ --data-urlencode "step=${step}" else curl -v -k -G "$url" \ From 05f2df9bb746586fd9c175389d8a95f41ca026ba Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 15:20:03 -0300 Subject: [PATCH 56/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 22 +++++++++++++++++++--- 1 file changed, 19 insertions(+), 3 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 3cc839ec..3205663b 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -205,13 +205,29 @@ query_prometheus() { local url="${PROM_URL}/api/v1/query_range" local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" + + # ===== DEBUG START ===== + echo "=============================================" >&2 + echo "DEBUG - Query Prometheus" >&2 + echo "=============================================" >&2 + echo "URL: $url" >&2 + echo "Query: $query" >&2 + echo "Start: $start_time" >&2 + echo "End: $end_time" >&2 + echo "Step: ${step}s" >&2 + echo "Token: ${PROMETHEUS_TOKEN:0:50}..." >&2 # Solo primeros 50 chars + echo "" >&2 + echo "URL completa:" >&2 + echo "${url}?query=$(urlencode "$query")&start=${start_time}&end=${end_time}&step=${step}s" >&2 + echo "=============================================" >&2 + if [[ -n "$PROMETHEUS_TOKEN" ]]; then curl -v -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ - --data-urlencode "end=$(date +%s)" \ + --data-urlencode "end=$end_time" \ --data-urlencode "step=${step}" else curl -v -k -G "$url" \ @@ -319,8 +335,8 @@ unit=$(echo $config | cut -d' ' -f2) filters=$(build_filters) query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") -#response=$(query_prometheus "$query" "$start_time" "$now" "$step") -response=$(query_prometheus "$query" "$start_time" "$(date +%s)" "$step") +response=$(query_prometheus "$query" "$start_time" "$now" "$step") + ## add debug echo "$filters" echo "$query" From 6f9d5c4941211252b421c3cd331fef700bd6054d Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Tue, 25 Nov 2025 15:27:40 -0300 Subject: [PATCH 57/59] feat(metrics): add debug for prometheus operator --- k8s/metric/metric | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 3205663b..837bd398 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -228,13 +228,13 @@ query_prometheus() { --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ --data-urlencode "end=$end_time" \ - --data-urlencode "step=${step}" + --data-urlencode "step=${step}s" else curl -v -k -G "$url" \ --data-urlencode "query=$query" \ --data-urlencode "start=$start_time" \ --data-urlencode "end=$end_time" \ - --data-urlencode "step=${step}" + --data-urlencode "step=${step}s" fi } From 3ed08cb87465b7053bd850a6db877c24f9e8e94a Mon Sep 17 00:00:00 2001 From: David Fernandez Date: Thu, 27 Nov 2025 16:23:12 -0300 Subject: [PATCH 58/59] feat: remove debug --- k8s/metric/metric | 30 ++++-------------------------- 1 file changed, 4 insertions(+), 26 deletions(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 837bd398..94d4de39 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -206,23 +206,7 @@ query_prometheus() { local params="query=$(urlencode "$query")&start=$start_time&end=$end_time&step=${step}s" - # ===== DEBUG START ===== - echo "=============================================" >&2 - echo "DEBUG - Query Prometheus" >&2 - echo "=============================================" >&2 - echo "URL: $url" >&2 - echo "Query: $query" >&2 - echo "Start: $start_time" >&2 - echo "End: $end_time" >&2 - echo "Step: ${step}s" >&2 - echo "Token: ${PROMETHEUS_TOKEN:0:50}..." >&2 # Solo primeros 50 chars - echo "" >&2 - echo "URL completa:" >&2 - echo "${url}?query=$(urlencode "$query")&start=${start_time}&end=${end_time}&step=${step}s" >&2 - echo "=============================================" >&2 - - - + if [[ -n "$PROMETHEUS_TOKEN" ]]; then curl -v -k -H "Authorization: Bearer $PROMETHEUS_TOKEN" -G "$url" \ --data-urlencode "query=$query" \ @@ -337,18 +321,13 @@ query=$(build_query "$METRIC_NAME" "$filters" "$INTERVAL") response=$(query_prometheus "$query" "$start_time" "$now" "$step") -## add debug -echo "$filters" -echo "$query" -echo "$response" + transform_response() { local response="$1" local status=$(echo "$response" | jq -r '.status') - ##debug - echo "$status" - echo "$response" + if [[ "$status" != "success" ]]; then echo "[]" @@ -373,7 +352,6 @@ transform_response() { transformed_results=$(transform_response "$response") -#add debug -echo "$transformed_results" + echo "{\"metric\":\"$METRIC_NAME\",\"type\":\"$metric_type\",\"period_in_seconds\":$step,\"unit\":\"$unit\",\"results\":$transformed_results}" From b88ecc4bace57a34572816d829a610eb091ad894 Mon Sep 17 00:00:00 2001 From: Javi Date: Thu, 27 Nov 2025 16:30:03 -0300 Subject: [PATCH 59/59] fix: remove echo --- k8s/metric/metric | 1 - 1 file changed, 1 deletion(-) diff --git a/k8s/metric/metric b/k8s/metric/metric index 94d4de39..678e81f8 100755 --- a/k8s/metric/metric +++ b/k8s/metric/metric @@ -312,7 +312,6 @@ else fi config=$(get_metric_config) -echo "$config" metric_type=$(echo $config | cut -d' ' -f1) unit=$(echo $config | cut -d' ' -f2)