Ingress

This generates Kubernetes Ingress objects .

Property Description
Resource type ingress
Account type None

Inputs

Values

Name Type Description
api_version string [Optional] The API version of the ingress object to produce. Must be one of v1beta1 or v1 . Defaults to v1
class string [Optional] The ingress controller class. Will be inserted as an annotation or in the ingressClassName property depending on api_version.
annotations object [Optional] An object with values of type string that will be inserted as annotations  on the generated Ingress object.
labels object [Optional] An object with values of type string that will be inserted as labels  on the generated Ingress object.
no_tls boolean [Optional] Does not generate a TLS section even if a tls_secret_name is supplied. Useful if TLS termination happens on the Load Balancer.
tls_secret_name string [Optional] Overrides the Humanitec provided secret. Useful if secrets are injected by another mechanism for example, Cert Manager or Rancher.

Secrets

None

Notes

If class is omitted, then the generated ingress object will not have an ingress class defined. See Default Ingress Class in the Kubernetes documentation  for possible behaviors.

Custom Resource Type for dns

When introducing a Custom Resource Type for dns, you will also need to supply your own Resource Definition for the ingress Type using a Driver other than the humanitec/ingress Driver. That Driver relies on the built-in dns Resource Type and will fail to properly locate the dns Resources. Specifically, the ingress Default Resource Definition also uses that Driver and cannot be used anymore.

To create a replacement for the default ingress Resource Definition, use the ingress-default example from the Template Driver ingress examples and adjust all references to the dns Resource to use your Custom Type, like so:

host: ${resources['ORG_ID/dns'].outputs.host}
routePaths: ${resources['ORG_ID/dns<route'].outputs.path}
routePorts: ${resources['ORG_ID/dns<route'].outputs.port}
routeServices: ${resources['ORG_ID/dns<route'].outputs.service}
Default ingress (YAML format)

ingress-default.yaml (view on GitHub ) :

# This Resource Definition provisions the equivalent of the humanitec/ingress driver with tls
apiVersion: entity.humanitec.io/v1b1
kind: Definition
metadata:
  id: default-ingress
entity:
  name: default-ingress
  type: ingress
  driver_type: humanitec/template
  driver_inputs:
    values:
      templates:
        manifests: |
          {{- /*
            Only generate an ingress manifest if there are any routes defined.
          */ -}}
          {{- if gt (len .driver.values.routePaths ) 0 -}}
          ingress.yaml:
            location: namespace
            data:
              apiVersion: networking.k8s.io/v1
              kind: Ingress
              metadata:
                {{- if hasKey .driver.values "annotations" }}
                annotations:
                  {{- range $k, $v := .driver.values.annotations }}
                  {{ $k | toRawJson }}: {{ $v | toRawJson }}
                  {{- end}}
                {{- end}}
                {{- if hasKey .driver.values "labels" }}
                labels:
                  {{- range $k, $v := .driver.values.labels }}
                  {{ $k | toRawJson }}: {{ $v | toRawJson }}
                  {{- end}}
                {{- end}}
                name: {{ .id }}-ingress
              spec:
                {{- if .driver.values.class }}
                ingressClassName: {{ .driver.values.class | toRawJson }}
                {{- end }}
                rules:
                - host: {{ .driver.values.host | toRawJson }}
                  http:
                    paths:
                    {{- /*
                      We are guaranteed that .driver.values.routePaths is non-zero in
                      length from the top level if statement, so we don't need
                      to deal with the empty condition.
                    */ -}}
                    {{- range $index, $path := .driver.values.routePaths }}
                    - path: {{ $path | toRawJson }}
                      pathType: {{ $.driver.values.path_type | default "Prefix" | toRawJson }}
                      backend:
                        service:
                          name: {{ index $.driver.values.routeServices $index  | toRawJson }}
                          port:
                            number: {{ index $.driver.values.routePorts $index }}
                    {{- end }}
                tls:
                - hosts:
                  - {{ .driver.values.host | toRawJson }}
                  secretName: {{ .driver.values.tlsSecretName | toRawJson }}
          {{- end -}}
        outputs: |
          id: {{ .id }}-ingress
  # The host will be used from the dns resource with the same
  # ResID and Class as this ingress.
  host: ${resources.dns.outputs.host}

  # These 3 selectors are guaranteed to return JSON arrays.
  # They will all be empty if there are no routes referencing this.
  routePaths: ${resources.dns&lt;route.outputs.path}
  routePorts: ${resources.dns&lt;route.outputs.port}
  routeServices: ${resources.dns&lt;route.outputs.service}

  tlsSecretName: ${resources.tls-cert.outputs.tls_secret_name}

  # The following fields can be set based on the documented driver inputs
  # for humanitec/ingress.
  # Uncomment and add values.

  # annotations: {}
  # class: nginx
  # labels: {}
  # path_type: Prefix

Default ingress (Terraform format)

ingress-default.tf (view on GitHub ) :

resource "humanitec_resource_definition" "default-ingress" {
  driver_type = "humanitec/template"
  id          = "default-ingress"
  name        = "default-ingress"
  type        = "ingress"
  driver_inputs = {
    values_string = jsonencode({
      "templates" = {
        "manifests" = <<END_OF_TEXT
{{- /*
  Only generate an ingress manifest if there are any routes defined.
*/ -}}
{{- if gt (len .driver.values.routePaths ) 0 -}}
ingress.yaml:
  location: namespace
  data:
    apiVersion: networking.k8s.io/v1
    kind: Ingress
    metadata:
      {{- if hasKey .driver.values "annotations" }}
      annotations:
        {{- range $k, $v := .driver.values.annotations }}
        {{ $k | toRawJson }}: {{ $v | toRawJson }}
        {{- end}}
      {{- end}}
      {{- if hasKey .driver.values "labels" }}
      labels:
        {{- range $k, $v := .driver.values.labels }}
        {{ $k | toRawJson }}: {{ $v | toRawJson }}
        {{- end}}
      {{- end}}
      name: {{ .id }}-ingress
    spec:
      {{- if .driver.values.class }}
      ingressClassName: {{ .driver.values.class | toRawJson }}
      {{- end }}
      rules:
      - host: {{ .driver.values.host | toRawJson }}
        http:
          paths:
          {{- /*
            We are guaranteed that .driver.values.routePaths is non-zero in
            length from the top level if statement, so we don't need
            to deal with the empty condition.
          */ -}}
          {{- range $index, $path := .driver.values.routePaths }}
          - path: {{ $path | toRawJson }}
            pathType: {{ $.driver.values.path_type | default "Prefix" | toRawJson }}
            backend:
              service:
                name: {{ index $.driver.values.routeServices $index  | toRawJson }}
                port:
                  number: {{ index $.driver.values.routePorts $index }}
          {{- end }}
      tls:
      - hosts:
        - {{ .driver.values.host | toRawJson }}
        secretName: {{ .driver.values.tlsSecretName | toRawJson }}
{{- end -}}
END_OF_TEXT
        "outputs"   = "id: {{ .id }}-ingress\n"
      }
      "host"          = "$${resources.dns.outputs.host}"
      "routePaths"    = "$${resources.dns<route.outputs.path}"
      "routePorts"    = "$${resources.dns<route.outputs.port}"
      "routeServices" = "$${resources.dns<route.outputs.service}"
      "tlsSecretName" = "$${resources.tls-cert.outputs.tls_secret_name}"
    })
  }
}

Example

The Example Library features a range of examples for using the Ingress Driver.

Notice that the Template Driver may alternatively be used to create Ingress objects with greater flexibility. See these examples in the Example Library.

Use the command below for the interface of your choice to create a Resource Definition that adds NGINX specific annotations  to generated ingress objects in the development Environment type.

Set the following environment variables for the CLI and API commands:

Variable Example Description
HUMANITEC_TOKEN my-token The authentication token for accessing the Humanitec API.
HUMANITEC_ORG my-org-id The unique identifier for the organization in Humanitec.

  1. Create a file defining the Resource Definition you want to create:
cat << EOF > ingress.yaml
apiVersion: entity.humanitec.io/v1b1
kind: Definition
metadata:
  id: custom-ingress
entity:
  driver_type: humanitec/ingress
  name: Custom Ingress
  type: ingress
  driver_inputs:
    values:
      annotations:
        nginx.ingress.kubernetes.io/cors-allow-headers: Keep-Alive,Authorization
        nginx.ingress.kubernetes.io/rewrite-target: /$2
      api_version: v1
      class: nginx
  criteria:
  - env_type: development
EOF
  1. Use the humctl create command to create the Resource Definition in the Organization defined by your configured context:
humctl create -f ingress.yaml
rm ingress.yaml

curl https://api.humanitec.io/orgs/${HUMANITEC_ORG}/resources/defs \
  -X POST \
  -H "Authorization: Bearer ${HUMANITEC_TOKEN}" \
  -H "Content-Type: application/json" \
  --data-binary '
{
  "id": "custom-ingress",
  "name": "Custom Ingress",
  "type": "ingress",
  "criteria": [
    {
      "env_type": "development"
    }
  ],
  "driver_type": "humanitec/ingress",
  "driver_inputs": {
    "values": {
      "api_version": "v1",
      "class":  "nginx",
      "annotations": {
        "nginx.ingress.kubernetes.io/rewrite-target": "/$2",
        "nginx.ingress.kubernetes.io/cors-allow-headers": "Keep-Alive,Authorization"
      }
    }
  }
}'
Top