From fb29bff220978079c24adf36919455633345f9cd Mon Sep 17 00:00:00 2001
From: Nicolas Lenz <nicolas@eisfunke.com>
Date: Sun, 19 Nov 2023 12:11:04 +0100
Subject: [PATCH] feat: add support for http-errors section

---
 README.md                 |  3 ++
 tasks/configure.yml       | 58 +++++++++++++++++++++++++++++++++++++++
 templates/frontend.cfg    |  6 +++-
 templates/http-errors.cfg |  9 ++++++
 4 files changed, 75 insertions(+), 1 deletion(-)
 create mode 100644 templates/http-errors.cfg

diff --git a/README.md b/README.md
index a70e441..da0437d 100644
--- a/README.md
+++ b/README.md
@@ -35,6 +35,9 @@ Role Variables
 * `haproxy_listen`
 
     A list of listen proxies.
+* `haproxy_http_errors`
+
+    A list of http-errors sections containing errorfiles for various status codes.
 
 Here is a complete list of variables:
 ```
diff --git a/tasks/configure.yml b/tasks/configure.yml
index 9fe1e3d..47e9ca5 100644
--- a/tasks/configure.yml
+++ b/tasks/configure.yml
@@ -102,6 +102,56 @@
   loop: "{{ haproxy_backends }}"
   when: haproxy_backends is defined
 
+## ASSEMBLE CONFIG - HTTP-ERRORS
+
+- name: Create directory for the error files
+  ansible.builtin.file:
+    path: "{{ haproxy_config_dir }}/custom_errors"
+    state: directory
+    owner: root
+    group: root
+    mode: "0755"
+
+- name: Copy error pages
+  ansible.builtin.copy:
+    src: "{{ item }}"
+    dest: "{{ haproxy_config_dir }}/custom_errors"
+    mode: "0644"
+  with_fileglob:
+    - "{{ inventory_hostname }}/custom_errors/*"
+
+- name: 'Create directory for the http-errors'
+  ansible.builtin.file:
+    path: "{{ haproxy_config_dir }}/http-errors.d"
+    state: directory
+    owner: root
+    group: root
+    mode: "0755"
+
+- name: "List files for the http-errors"
+  ansible.builtin.find:
+    paths: "{{ haproxy_config_dir }}/http-errors.d"
+    patterns: "*.cfg"
+  register: directory_contents
+  changed_when: false
+
+- name: "Remove unmanaged files for the http-errors"
+  ansible.builtin.file:
+    path: "{{ item.path }}"
+    state: absent
+  when: (item.path | basename) not in (haproxy_http_errors | json_query('[*].name') | map('regex_replace',  '(^.*$)', '\\1.cfg') | list)
+  loop: "{{ directory_contents.files }}"
+
+- name: 'Build up the http-errors'
+  ansible.builtin.template:
+    src: "http-errors.cfg"
+    dest: "{{ haproxy_config_dir }}/http-errors.d/{{ item.name }}.cfg"
+    owner: root
+    group: root
+    mode: "0644"
+  loop: "{{ haproxy_http_errors }}"
+  when: haproxy_http_errors is defined
+
 ## ASSEMBLE CONFIG - LISTEN
 
 - name: 'Create directory for the listen sections'
@@ -239,6 +289,14 @@
     group: root
     mode: "0644"
 
+- name: 'Assemble the http-errors configuration file'
+  ansible.builtin.assemble:
+    src: "{{ haproxy_config_dir }}/http-errors.d"
+    dest: "{{ haproxy_config_dir }}/compiled/07-http-errors.cfg"
+    owner: root
+    group: root
+    mode: "0644"
+
 - name: 'Assemble the final configuration file'
   ansible.builtin.assemble:
     src: "{{ haproxy_config_dir }}/compiled"
diff --git a/templates/frontend.cfg b/templates/frontend.cfg
index 8c2ac37..94c3217 100644
--- a/templates/frontend.cfg
+++ b/templates/frontend.cfg
@@ -110,6 +110,10 @@ frontend {{ item.name }} {%if item.ip is defined %}{{ item.ip }}{% endif %}{%if
 
     {%- if item.use_backend is defined -%}
     {%- for backend in item.use_backend -%}
-         use_backend {{ backend.name }} {{ backend.condition }}
+        use_backend {{ backend.name }} {{ backend.condition }}
     {% endfor -%}
     {% endif -%}
+
+    {%- if item.errorfiles is defined -%}
+        errorfiles {{ item.errorfiles }}
+    {% endif %}
diff --git a/templates/http-errors.cfg b/templates/http-errors.cfg
new file mode 100644
index 0000000..b012531
--- /dev/null
+++ b/templates/http-errors.cfg
@@ -0,0 +1,9 @@
+{%- import '_macros.j2' as macros with context -%}
+
+#{{ ansible_managed }}
+http-errors {{ item.name }}
+    {% if item.errorfiles is defined %}
+    {%- for errorfile in item.errorfiles -%}
+        errorfile {{ errorfile.status }} {{ errorfile.file }}
+    {% endfor -%}
+    {% endif -%}
-- 
GitLab