HAProxy config,
rendered from your templates.

HAPTIC — the HAProxy Template Ingress Controller — is an open-source Kubernetes controller that builds your HAProxy config from templates you control. Watch Ingress, the Gateway API, or any custom resource, and generate configuration from their fields.

$ haptic --features

Extend with templates

Add an annotation, a header rewrite, or support for a new API by editing a template.

Control the configuration

Scriggo — a Go-native template engine — renders haproxy.cfg and auxiliary files. Override a bundled snippet or supply your own templates.

Watch any resource

HAPTIC watches any Kubernetes resource — a built-in kind or a CRD of your own. No resource type is baked into the controller; your templates decide what to read.

Validate changes

The admission webhook checks routing changes, and template tests check fixture scenarios in CI. Each pod's HAProxy binary must accept a reload before the new worker takes over.

Start with the bundled routing libraries.

Bundled libraries support Ingress, Gateway API, and HAPTIC annotations by default. When migrating, enable the compatibility library for ingress-nginx, HAProxy Technologies, or haproxy-ingress. Check its supported annotations before switching traffic.

$ haptic --extend

Let each Ingress choose a request-ID header for its own backends. Add this snippet under controller.config.templateSnippets in your Helm values:

values.yaml Run live
controller:
  config:
    templateSnippets:
      backend-directives-300-request-id:
        template: |
          {%- if ingress != nil %}
          {%- var header = ingress.metadata.annotations["example.com/request-id-header"] %}
          {%- if header != "" %}
          {%- if !regex_search(header, "^[A-Za-z0-9-]+$") %}
          {{ fail("example.com/request-id-header must contain only letters, digits, or hyphens.") }}
          {%- end %}
          http-request set-header {{ header }} %[uuid()]
          {%- end %}
          {%- end %}

Set example.com/request-id-header: "X-Request-ID" on an Ingress. Header names use letters, digits, and hyphens. Changes to this backend directive require a reload.

$ haptic --install

bash — install
$ helm install \
    haptic oci://registry.gitlab.com/haproxy-haptic/haptic/charts/haptic \
    --version 0.2.0-alpha.3
$ kubectl get haproxytemplateconfig

$ haptic --docs

~/docs

Documentation

From your first Helm install to writing your own templates — deploying with Helm, watching resources, template rendering, config validation, and operating HAProxy in production.

Available versions

Loading…
~/playground

Playground

Edit a config and watch HAProxy render in your browser — the same engine the controller runs, no install. Tweak a resource, flip a version, share a link to exactly what you see.

// Built for operators who'd rather write a template than file a feature request.

Apache-2.0 · Playground · Source on GitLab

Community project — independent and not affiliated with or endorsed by HAProxy Technologies.