diff --git a/library/common-test/tests/pod/deployment_volumeMounts_test.yaml b/library/common-test/tests/pod/deployment_container_volumeMounts_test.yaml similarity index 100% rename from library/common-test/tests/pod/deployment_volumeMounts_test.yaml rename to library/common-test/tests/pod/deployment_container_volumeMounts_test.yaml diff --git a/library/common-test/tests/pod/deployment_contaner_port_test.yaml b/library/common-test/tests/pod/deployment_contaner_port_test.yaml index 129a570cb0..06bff840a4 100644 --- a/library/common-test/tests/pod/deployment_contaner_port_test.yaml +++ b/library/common-test/tests/pod/deployment_contaner_port_test.yaml @@ -35,6 +35,18 @@ tests: documentIndex: *deploymentDoc errorMessage: Port is required on enabled services. Service (main) + - it: should fail with disabled port on enabled service + set: + service: + main: + ports: + main: + enabled: false + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: No ports are enabled for the service (main) + - it: should fail with invalid protocol set: service: @@ -108,6 +120,13 @@ tests: port: 443 protocol: UDP targetPort: 8000 + probes: + liveness: + enabled: false + readiness: + enabled: false + startup: + enabled: false asserts: - equal: documentIndex: *deploymentDoc diff --git a/library/common-test/tests/pod/deployment_contaner_probe_test.yaml b/library/common-test/tests/pod/deployment_contaner_probe_test.yaml new file mode 100644 index 0000000000..039fb179f2 --- /dev/null +++ b/library/common-test/tests/pod/deployment_contaner_probe_test.yaml @@ -0,0 +1,706 @@ +suite: deployment container probe test +templates: + - common.yaml +tests: + - it: should pass with default values + asserts: + - hasDocuments: + count: 1 + - documentIndex: &deploymentDoc 0 + isKind: + of: Deployment + - equal: + path: spec.template.spec.containers[0].probes + value: + livenessProbe: + httpGet: + path: / + scheme: HTTP + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + readinessProbe: + httpGet: + path: / + scheme: HTTP + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + startupProbe: + httpGet: + path: / + scheme: HTTP + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 60 + timeoutSeconds: 2 + periodSeconds: 5 + + - it: should fail with wrong probe name + set: + probes: + invalid_probe_name: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: Invalid probe name (invalid_probe_name). Valid options are (liveness, readiness, startup) + + - it: should fail without commands on exec probe + set: + probes: + liveness: + type: exec + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: No commands were defined for exec type on probe (liveness) + + - it: should fail without path on http(s) liveness probe + set: + probes: + liveness: + path: "" + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: must be defined for HTTP/HTTPS probe types in probe (liveness) + + - it: should fail without path on http(s) readiness probe + set: + probes: + readiness: + path: "" + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: must be defined for HTTP/HTTPS probe types in probe (readiness) + + - it: should fail without path on http(s) startup probe + set: + probes: + startup: + path: "" + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: must be defined for HTTP/HTTPS probe types in probe (startup) + + - it: should fail without initialDelaySeconds on non-custom probes + set: + probes: + liveness: + spec: + initialDelaySeconds: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: cannot be empty in probe (liveness) + + - it: should fail without failureThreshold on non-custom probes + set: + probes: + liveness: + spec: + failureThreshold: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: cannot be empty in probe (liveness) + + - it: should fail without timeoutSeconds on non-custom probes + set: + probes: + liveness: + spec: + timeoutSeconds: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: cannot be empty in probe (liveness) + + - it: should fail without periodSeconds on non-custom probes + set: + probes: + liveness: + spec: + periodSeconds: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: cannot be empty in probe (liveness) + + - it: should fail when non-custom probe is defined in a disabled service + set: + service: + main: + enabled: false + probes: + liveness: + spec: + periodSeconds: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: Only custom probes are allowed when service is disabled (liveness) + + - it: should fail with invalid probe type + set: + probes: + liveness: + type: not_valid_type + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: Invalid probe type (not_valid_type) on probe (liveness) + + - it: should fail with httpHeader value is defined as list + set: + probes: + liveness: + type: HTTP + httpHeaders: + some_header: + - list_value + - list_value2 + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: Lists or Dicts are not allowed in httpHeaders on probe (liveness) + + - it: should fail with httpHeader value is defined as dict + set: + probes: + liveness: + type: HTTP + httpHeaders: + some_header: + some_key: + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: Lists or Dicts are not allowed in httpHeaders on probe (liveness) + + - it: should pass with with custom defined liveness probe + set: + probes: + liveness: + custom: true + spec: + httpGet: + path: /path + scheme: HTTPS + port: 1234 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: /path + scheme: HTTPS + port: 1234 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + + - it: should pass with with custom defined readiness probe + set: + probes: + readiness: + custom: true + spec: + httpGet: + path: /path + scheme: HTTPS + port: 1234 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.readinessProbe + value: + httpGet: + path: /path + scheme: HTTPS + port: 1234 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + + - it: should pass with with custom defined startup probe + set: + probes: + startup: + custom: true + spec: + httpGet: + path: /path + scheme: HTTPS + port: 1234 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.startupProbe + value: + httpGet: + path: /path + scheme: HTTPS + port: 1234 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + + - it: should pass with with probe type AUTO and service HTTP + set: + service: + main: + ports: + main: + protocol: HTTP + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTP + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type AUTO and service HTTPS + set: + service: + main: + ports: + main: + protocol: HTTPS + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTPS + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type AUTO and service TCP + set: + service: + main: + ports: + main: + protocol: TCP + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type TCP and service TCP + set: + probes: + liveness: + type: TCP + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type AUTO and service HTTP with custom path + set: + service: + main: + ports: + main: + protocol: HTTP + probes: + liveness: + type: AUTO + path: /some_path + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: /some_path + scheme: HTTP + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type AUTO and service HTTP with custom port + set: + service: + main: + ports: + main: + protocol: HTTP + probes: + liveness: + type: AUTO + port: 1234 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTP + port: 1234 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type AUTO and service HTTP with httpHeaders + set: + service: + main: + ports: + main: + protocol: HTTP + probes: + liveness: + type: AUTO + httpHeaders: + some_header: 1234 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTP + port: 999999 + httpHeaders: + - name: some_header + value: 1234 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type HTTP with httpHeaders set from tpl + set: + some_header_value: 1234 + probes: + liveness: + type: HTTP + httpHeaders: + some_header: "{{ .Values.some_header_value }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTP + port: 999999 + httpHeaders: + - name: some_header + value: 1234 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type HTTP with multiple httpHeaders set from tpl + set: + some_header_value: 1234 + some_header_value2: some_value + probes: + liveness: + type: HTTP + httpHeaders: + some_header: "{{ .Values.some_header_value }}" + some_header2: "{{ .Values.some_header_value2 }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTP + port: 999999 + httpHeaders: + - name: some_header + value: 1234 + - name: some_header2 + value: some_value + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type HTTP with path set from tpl + set: + some_path: /ping + probes: + liveness: + type: HTTP + path: "{{ .Values.some_path }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: /ping + scheme: HTTP + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type HTTP with port set from tpl + set: + some_port: 1234 + probes: + liveness: + type: HTTP + port: "{{ .Values.some_port }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + scheme: HTTP + port: 1234 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type TCP with port set from tpl + set: + some_port: 1234 + probes: + liveness: + type: TCP + port: "{{ .Values.some_port }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 1234 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with changed times + set: + probes: + liveness: + type: TCP + spec: + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 999999 + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + + - it: should pass with with probe type GRPC + set: + probes: + liveness: + type: GRPC + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + grpc: + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type exec with multiline command + set: + probes: + liveness: + type: exec + command: + - /bin/bash + - -c + - | + echo "probe!" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + exec: + command: + - /bin/bash + - -c + - | + echo "probe!" + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type exec with multiline command from tpl + set: + some_msg: probe! + probes: + liveness: + type: exec + command: + - /bin/bash + - -c + - | + echo "{{ .Values.some_msg }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + exec: + command: + - /bin/bash + - -c + - | + echo "probe!" + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type exec single command + set: + probes: + liveness: + type: exec + command: env + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + exec: + command: + - env + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with with probe type exec single command from tpl + set: + some_command: env + probes: + liveness: + type: exec + command: "{{ .Values.some_command }}" + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + exec: + command: + - env + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + + - it: should pass with with probe type exec single command and custom timings + set: + probes: + liveness: + type: exec + command: env + spec: + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + exec: + command: + - env + initialDelaySeconds: 15 + failureThreshold: 10 + timeoutSeconds: 10 + periodSeconds: 15 diff --git a/library/common-test/tests/pod/utils_primary_port_test.yaml b/library/common-test/tests/pod/utils_primary_port_test.yaml new file mode 100644 index 0000000000..cb3d81f5a4 --- /dev/null +++ b/library/common-test/tests/pod/utils_primary_port_test.yaml @@ -0,0 +1,90 @@ + +suite: primary port utils test +templates: + - common.yaml +tests: + - it: should pass with default values + asserts: + - hasDocuments: + count: 1 + - documentIndex: &deploymentDoc 0 + isKind: + of: Deployment + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + port: 999999 + scheme: HTTP + failureThreshold: 5 + initialDelaySeconds: 10 + periodSeconds: 10 + timeoutSeconds: 5 + + - it: should pass with no port set as primary + set: + service: + main: + ports: + main: + primary: false + protocol: TCP + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with different port set as primary + set: + service: + main: + ports: + main: + primary: false + other: + enabled: true + primary: true + protocol: TCP + port: 12345 + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 12345 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should fail with more than 1 primary ports + set: + service: + main: + ports: + main: + primary: true + other_port: + enabled: true + primary: true + port: 1234 + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: More than one ports are set as primary in the primary service. This is not supported. diff --git a/library/common-test/tests/pod/utils_primary_service_test.yaml b/library/common-test/tests/pod/utils_primary_service_test.yaml new file mode 100644 index 0000000000..073d2a1b89 --- /dev/null +++ b/library/common-test/tests/pod/utils_primary_service_test.yaml @@ -0,0 +1,89 @@ + +suite: primary service utils test +templates: + - common.yaml +tests: + - it: should pass with default values + asserts: + - hasDocuments: + count: 1 + - documentIndex: &deploymentDoc 0 + isKind: + of: Deployment + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + httpGet: + path: / + port: 999999 + scheme: HTTP + failureThreshold: 5 + initialDelaySeconds: 10 + periodSeconds: 10 + timeoutSeconds: 5 + + - it: should fail with more than 1 primary services + set: + service: + main: + primary: true + other: + enabled: true + primary: true + asserts: + - failedTemplate: + documentIndex: *deploymentDoc + errorMessage: More than one services are set as primary. This is not supported. + + + - it: should pass with no service set as primary + set: + service: + main: + primary: false + ports: + main: + protocol: TCP + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 999999 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 + + - it: should pass with different service set as primary + set: + service: + main: + primary: false + other: + enabled: true + primary: true + ports: + other: + enabled: true + protocol: TCP + port: 12345 + probes: + liveness: + type: AUTO + asserts: + - equal: + documentIndex: *deploymentDoc + path: spec.template.spec.containers[0].probes.livenessProbe + value: + tcpSocket: + port: 12345 + initialDelaySeconds: 10 + failureThreshold: 5 + timeoutSeconds: 5 + periodSeconds: 10 diff --git a/library/common/1.0.0/templates/lib/container/_probes.tpl b/library/common/1.0.0/templates/lib/container/_probes.tpl index d10ec49ab9..6be0ed74cc 100644 --- a/library/common/1.0.0/templates/lib/container/_probes.tpl +++ b/library/common/1.0.0/templates/lib/container/_probes.tpl @@ -1,4 +1,103 @@ {{/* Probes selection logic included by the container. */}} {{- define "ix.v1.common.container.probes" -}} + {{- $primarySeriviceName := (include "ix.v1.common.lib.util.service.primary" .) -}} {{/* Get the name of the primary service, if any */}} + {{- $primaryService := get .Values.service $primarySeriviceName -}} {{/* Get service values of the primary service, if any */}} + {{- $primaryPort := "" -}} + {{- if $primaryService -}} + {{- $primaryPort = get $primaryService.ports (include "ix.v1.common.lib.util.service.ports.primary" (dict "serviceName" $primarySeriviceName "values" $primaryService)) -}} + {{- end -}} + {{- $probeType := "TCP" -}} + {{- range $probeName, $probe := .Values.probes -}} + {{- if and (ne $probeName "liveness") (ne $probeName "readiness") (ne $probeName "startup") -}} + {{- fail (printf "Invalid probe name (%s). Valid options are (liveness, readiness, startup)" $probeName) -}} + {{- end -}} + {{- if $probe.enabled -}} + {{- "" | nindent 0 -}} {{/* Needed to create a new line */}} + {{- $probeName }}Probe: + {{- if $probe.custom -}} {{/* Allows to add a custom definition on the probe */}} + {{- $probe.spec | toYaml | nindent 2 }} + {{- else if eq ($probe.type | lower) "exec" -}} + {{- print "exec:" | nindent 2 }} + {{- if $probe.command -}} + {{- print "command:" | nindent 4 }} + {{- include "ix.v1.common.container.command" (dict "commands" $probe.command "root" $) | trim | nindent 6 }} + {{- include "ix.v1.common.container.probes.timings" (dict "probe" $probe "probeName" $probeName) }} + {{- else -}} + {{- fail (printf "No commands were defined for exec type on probe (%s)" $probeName) -}} + {{- end -}} + {{- else -}} + {{- if and $primaryService $primaryPort -}} + {{- if $probe.type -}} + {{- if eq ($probe.type | upper) "AUTO" -}} + {{- $probeType = $primaryPort.protocol -}} + {{- else -}} + {{- if and (ne $probe.type "TCP") (ne $probe.type "HTTP") (ne $probe.type "HTTPS") (ne ($probe.type | upper) "GRPC") -}} + {{- fail (printf "Invalid probe type (%s) on probe (%s)" $probe.type $probeName) -}} + {{- end -}} + {{- $probeType = $probe.type -}} + {{- end -}} + {{- end -}} + {{- if or (eq ($probeType | upper) "HTTPS") (eq ($probeType | upper) "HTTP") -}} + {{- if not $probe.path -}} + {{- fail (printf " must be defined for HTTP/HTTPS probe types in probe (%s)" $probeName) -}} + {{- end -}} + {{- print "httpGet:" | nindent 2 }} + {{- printf "path: %v" (tpl $probe.path $) | nindent 4 }} + {{- printf "scheme: %v" $probeType | nindent 4 }} + {{- with $probe.httpHeaders }} + {{- printf "httpHeaders:" | nindent 4 }} + {{- range $k, $v := . }} + {{- if or (kindIs "slice" $v) (kindIs "map" $v) -}} + {{- fail (printf "Lists or Dicts are not allowed in httpHeaders on probe (%s)" $probeName) -}} + {{- end -}} + {{- printf "- name: %s" $k | nindent 6 }} + {{- printf " value: %s" (tpl (toString $v) $) | nindent 6 }} + {{- end }} + {{- end }} + {{- else if (eq $probeType "TCP") -}} + {{- print "tcpSocket:" | nindent 2 }} + {{- else if (eq ($probeType | lower) "grpc") -}} + {{- printf "grpc:" | nindent 2 }} + {{- else if (eq $probeType "UDP") -}} + {{- fail "UDP Probes are not supported. Please set a different UDP probe or disable probes." -}} + {{- end -}} + + {{- $probePort := $primaryPort.port -}} + {{- if $probe.port -}} + {{- $probePort = (tpl ($probe.port | toString) $) -}} + {{- else if $primaryPort.targetPort -}} + {{- $probePort = $primaryPort.targetPort -}} + {{- end -}} + + {{- printf "port: %v" $probePort | nindent 4 }} + {{- include "ix.v1.common.container.probes.timings" (dict "probe" $probe "probeName" $probeName) }} + {{- else -}} + {{- fail (printf "Only custom probes are allowed when service is disabled (%s)" $probeName) -}} + {{- end -}} + {{- end -}} + {{- end -}} + {{- end -}} +{{- end -}} + +{{- define "ix.v1.common.container.probes.timings" -}} + {{- $probe := .probe -}} + {{- $probeName := .probeName -}} + {{/* ints are usually parsed as floats in helm */}} + {{- if and (not (kindIs "float64" $probe.spec.initialDelaySeconds)) (not (kindIs "int" $probe.spec.initialDelaySeconds)) -}} + {{- fail (printf " cannot be empty in probe (%s)" $probeName) -}} + {{- end -}} + {{- if and (not (kindIs "float64" $probe.spec.failureThreshold)) (not (kindIs "int" $probe.spec.failureThreshold)) -}} + {{- fail (printf " cannot be empty in probe (%s)" $probeName) -}} + {{- end -}} + {{- if and (not (kindIs "float64" $probe.spec.timeoutSeconds)) (not (kindIs "int" $probe.spec.timeoutSeconds)) -}} + {{- fail (printf " cannot be empty in probe (%s)" $probeName) -}} + {{- end -}} + {{- if and (not (kindIs "float64" $probe.spec.periodSeconds)) (not (kindIs "int" $probe.spec.periodSeconds)) -}} + {{- fail (printf " cannot be empty in probe (%s)" $probeName) -}} + {{- end -}} + {{- printf "initialDelaySeconds: %v" $probe.spec.initialDelaySeconds | nindent 2 }} + {{- printf "failureThreshold: %v" $probe.spec.failureThreshold | nindent 2 }} + {{- printf "timeoutSeconds: %v" $probe.spec.timeoutSeconds | nindent 2 }} + {{- printf "periodSeconds: %v" $probe.spec.periodSeconds | nindent 2 }} {{- end -}} diff --git a/library/common/1.0.0/templates/lib/controller/_container.tpl b/library/common/1.0.0/templates/lib/controller/_container.tpl index c6b7814ac4..c7f1de2c4c 100644 --- a/library/common/1.0.0/templates/lib/controller/_container.tpl +++ b/library/common/1.0.0/templates/lib/controller/_container.tpl @@ -39,23 +39,27 @@ {{- end }} {{- with .Values.termination.messagePolicy }} terminationMessagePolicy: {{ tpl . $ }} - {{- end }} + {{- end -}} {{- with (include "ix.v1.common.container.envVars" (dict "envs" .Values.env "envList" .Values.envList "root" $) | trim) }} env: {{- . | nindent 4 }} {{/* env and envList */}} - {{- end }} + {{- end -}} {{- with (include "ix.v1.common.container.envFrom" (dict "envFrom" .Values.envFrom "root" $) | trim) }} envFrom: {{- . | nindent 4 }} - {{- end }} + {{- end -}} {{- with (include "ix.v1.common.container.ports" . | trim) }} ports: {{- . | nindent 4 }} - {{- end }} + {{- end -}} {{- with (include "ix.v1.common.container.volumeMounts" . | trim) }} volumeMounts: {{- . | nindent 4 }} {{- end -}} + {{- with (include "ix.v1.common.container.probes" . | trim) }} + probes: + {{- . | nindent 4 }} + {{- end -}} {{- end -}} {{/* diff --git a/library/common/1.0.0/templates/lib/util/_primary_port.tpl b/library/common/1.0.0/templates/lib/util/_primary_port.tpl new file mode 100644 index 0000000000..95b7883a15 --- /dev/null +++ b/library/common/1.0.0/templates/lib/util/_primary_port.tpl @@ -0,0 +1,32 @@ +{{/* Return the primary port for a given Service object. */}} +{{- define "ix.v1.common.lib.util.service.ports.primary" -}} + {{- $enabledPorts := dict -}} + {{- range $name, $port := .values.ports -}} + {{- if $port.enabled -}} + {{- $_ := set $enabledPorts $name . -}} + {{- end -}} + {{- end -}} + + {{- if not $enabledPorts -}} + {{- fail (printf "No ports are enabled for the service (%s)" .serviceName) -}} + {{- end -}} + + {{- $result := "" -}} + {{- range $name, $port := $enabledPorts -}} + {{- if $result -}} + {{- fail "More than one ports are set as primary in the primary service. This is not supported." -}} + {{- end -}} + {{- if (hasKey $port "primary") -}} + {{- if $port.primary -}} + {{- $result = $name -}} + {{- end -}} + {{- end -}} + {{- end -}} + + {{- if not $result -}} + {{- $result = keys $enabledPorts | first -}} + {{- end -}} + + {{- $result -}} +{{- end -}} +{{/* A dict containing .values and .serviceName is passed when this function is called */}} diff --git a/library/common/1.0.0/templates/lib/util/_primary_service.tpl b/library/common/1.0.0/templates/lib/util/_primary_service.tpl new file mode 100644 index 0000000000..8bc63f76e7 --- /dev/null +++ b/library/common/1.0.0/templates/lib/util/_primary_service.tpl @@ -0,0 +1,27 @@ +{{/* Returns the primary service object */}} +{{- define "ix.v1.common.lib.util.service.primary" -}} + {{- $enabledServices := dict -}} + {{- range $name, $service := .Values.service -}} + {{- if $service.enabled -}} + {{- $_ := set $enabledServices $name . -}} + {{- end -}} + {{- end -}} + + {{- $result := "" -}} + {{- range $name, $service := $enabledServices -}} + {{- if $result -}} + {{- fail "More than one services are set as primary. This is not supported." -}} + {{- end -}} + {{- if (hasKey $service "primary") -}} + {{- if $service.primary -}} + {{- $result = $name -}} + {{- end -}} + {{- end -}} + {{- end -}} + + {{- if not $result -}} + {{- $result = keys $enabledServices | first -}} + {{- end -}} + + {{- $result -}} +{{- end -}} diff --git a/library/common/1.0.0/values.yaml b/library/common/1.0.0/values.yaml index 309dd4a594..a247bc4373 100644 --- a/library/common/1.0.0/values.yaml +++ b/library/common/1.0.0/values.yaml @@ -167,8 +167,11 @@ service: # -- Enables or disables the port enabled: true # enabled: false + # -- Make this the primary port (used in probes, notes, etc...) + # If there is more than 1 service, make sure that only 1 port is marked as primary. + primary: true # -- The port number (Default port is required if enabled: true) - port: 999999 # TODO: + port: 999999 #TODO: # -- Port protocol. # Support values are `HTTP`, `HTTPS`, `TCP` and `UDP`. # HTTPS and HTTPS spawn a TCP service and get used for internal URL and name generation @@ -181,6 +184,88 @@ service: # [[ref]](https://kubernetes.io/docs/concepts/services-networking/service/#type-nodeport) nodePort: +# -- Define probes. Helm template enabled on, path, port, httpHeader values +probes: + # -- Liveness probe configuration + # @default -- See below + liveness: + # -- Enable the liveness probe + enabled: true + # -- Set this to `true` if you wish to specify your own livenessProbe + custom: false + # -- sets the probe type when not using a custom probe + # @default -- "TCP" + type: AUTO + # -- If an HTTP probe is used (default for HTTP/HTTPS services) this path is used. Helm tpl enabled + # @default -- "/" + path: "/" + # -- If an exec is used, it sets the commands. Helm tpl enabled. + command: [] + # -- If an HTTP probe is used (default for HTTP/HTTPS services) this headers are used + httpHeaders: {} + # some_header: some_value + # -- The spec field contains the values for the default livenessProbe. + # If you selected `custom: true`, this field holds the definition of the livenessProbe. + # @default -- See below + spec: + initialDelaySeconds: 10 + periodSeconds: 10 + timeoutSeconds: 5 + failureThreshold: 5 + + # -- Redainess probe configuration + # @default -- See below + readiness: + # -- Enable the readiness probe + enabled: true + # -- Set this to `true` if you wish to specify your own readinessProbe + custom: false + # -- sets the probe type when not using a custom probe + # @default -- "TCP" + type: AUTO + # -- If a HTTP probe is used (default for HTTP/HTTPS services) this path is used + # @default -- "/" + path: "/" + # -- If an exec is used, it sets the commands. Helm tpl enabled. + command: [] + # -- The spec field contains the values for the default readinessProbe. + # If you selected `custom: true`, this field holds the definition of the readinessProbe. + # @default -- See below + spec: + initialDelaySeconds: 10 + periodSeconds: 10 + timeoutSeconds: 5 + failureThreshold: 5 + + # -- Startup probe configuration + # @default -- See below + startup: + # -- Enable the startup probe + enabled: true + # -- Set this to `true` if you wish to specify your own startupProbe + custom: false + # -- sets the probe type when not using a custom probe + # @default -- "TCP" + type: AUTO + # -- If a HTTP probe is used (default for HTTP/HTTPS services) this path is used + # @default -- "/" + path: "/" + # -- If an exec is used, it sets the commands. Helm tpl enabled. + command: [] + # -- set to override the default port without using custom startupProbe + # Accepts TPL + # @default -- "" + port: "" + # -- The spec field contains the values for the default startupProbe. + # If you selected `custom: true`, this field holds the definition of the startupProbe. + # @default -- See below + spec: + initialDelaySeconds: 10 + timeoutSeconds: 2 + ## This means it has a maximum of 5*30=150 seconds to start up before it fails + periodSeconds: 5 + failureThreshold: 60 + # -- Configure persistence for the chart here. # Additional items can be added by adding a dictionary key similar to the 'pvc-example' key. # @default -- See below diff --git a/run_common_tests.sh b/run_common_tests.sh index b95740c764..57454f07fe 100755 --- a/run_common_tests.sh +++ b/run_common_tests.sh @@ -5,7 +5,7 @@ # helm plugin install https://github.com/quintush/helm-unittest curr_dir=${pwd} -common_test_path=library/common-test +common_test_path="library/common-test" echo "Building common..." helm dependency build "$common_test_path"