diff --git a/defaults/main.yml b/defaults/main.yml index 5ddf0e1..f671227 100644 --- a/defaults/main.yml +++ b/defaults/main.yml @@ -20,6 +20,20 @@ grafana_disable_sanitize_html: true pgadmin_version: 'latest' pgadmin_watchtower_enable: true +### n8n +# n8n_domain: required... +# n8n_encryption_key: required... +n8n_version: 'latest' +n8n_timezone: 'Europe/Paris' +n8n_watchtower_enable: true +n8n_basic_auth_active: false +# n8n_db_type: 'sqlite' # or 'postgresql' +# When n8n_db_type == 'postgresql': +# n8n_db_password: required... +n8n_db_name: 'n8n' +n8n_db_user: 'n8n' +n8n_db_postgres_version: '16' + ### Gitlab # gitlab_root_password: required... gitlab_external_url: 'https://{{ gitlab_domain }}' diff --git a/handlers/main.yml b/handlers/main.yml index 555350e..5951d3f 100644 --- a/handlers/main.yml +++ b/handlers/main.yml @@ -75,3 +75,10 @@ state: restarted ignore_errors: '{{ ansible_check_mode }}' tags: ['docker_pgadmin'] + +- name: n8n-restart + systemd: + name: docker-compose@n8n + state: restarted + ignore_errors: '{{ ansible_check_mode }}' + tags: ['docker_n8n'] diff --git a/tasks/main.yml b/tasks/main.yml index 88bd179..ab97455 100644 --- a/tasks/main.yml +++ b/tasks/main.yml @@ -18,5 +18,6 @@ - docker_gitlab - docker-gitlab-runner - docker_pgadmin + - docker_n8n with_items: - "{{ docker_services }}" diff --git a/tasks/n8n.yml b/tasks/n8n.yml new file mode 100644 index 0000000..1755b32 --- /dev/null +++ b/tasks/n8n.yml @@ -0,0 +1,32 @@ +--- +- name: n8n | check vars are defined + assert: + that: + - n8n_domain is defined + - n8n_encryption_key is defined + tags: ['docker_n8n'] + +- include_tasks: base.yml + tags: ['docker_n8n'] + +- name: n8n | create docker volume data + docker_volume: + name: n8n__home_node_n8n + when: docker_services_external_volumes + tags: ['docker_n8n'] + +- name: n8n | create docker volume for postgres + docker_volume: + name: n8n_db__var_lib_postgresql_data + when: + - docker_services_external_volumes + - n8n_db_type | default('sqlite') == 'postgresql' + tags: ['docker_n8n'] + +- name: n8n | create docker network + docker_network: + name: n8n + when: + - docker_services_external_networks + - n8n_db_type | default('sqlite') == 'postgresql' + tags: ['docker_n8n'] diff --git a/templates/compose/n8n.yml.j2 b/templates/compose/n8n.yml.j2 new file mode 100644 index 0000000..37f4300 --- /dev/null +++ b/templates/compose/n8n.yml.j2 @@ -0,0 +1,100 @@ +networks: +{% if docker_services_external_networks %} + traefik: + external: true +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + n8n: + external: true +{% endif %} +{% else %} + traefik: + name: traefik +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + n8n: + name: n8n +{% endif %} +{% endif %} + +volumes: +{% if docker_services_external_volumes %} + n8n__home_node_n8n: + external: true +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + n8n_db__var_lib_postgresql_data: + external: true +{% endif %} +{% else %} + n8n__home_node_n8n: + name: n8n__home_node_n8n +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + n8n_db__var_lib_postgresql_data: + name: n8n_db__var_lib_postgresql_data +{% endif %} +{% endif %} + +services: +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + n8n_db: + image: postgres:{{ n8n_db_postgres_version | default('16') }}-alpine + container_name: n8n_db + restart: unless-stopped + environment: + POSTGRES_DB: "{{ n8n_db_name | default('n8n') }}" + POSTGRES_USER: "{{ n8n_db_user | default('n8n') }}" + POSTGRES_PASSWORD: "{{ n8n_db_password }}" + volumes: + - n8n_db__var_lib_postgresql_data:/var/lib/postgresql/data + networks: + - n8n + labels: + com.centurylinklabs.watchtower.enable: "false" + +{% endif %} + n8n: + image: docker.n8n.io/n8nio/n8n:{{ n8n_version | default("latest") }} + container_name: n8n + restart: unless-stopped +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + depends_on: + - n8n_db +{% endif %} + environment: + N8N_HOST: "{{ n8n_domain }}" + N8N_PORT: "5678" + N8N_PROTOCOL: "https" + WEBHOOK_URL: "https://{{ n8n_domain }}/" + N8N_ENCRYPTION_KEY: "{{ n8n_encryption_key }}" + GENERIC_TIMEZONE: "{{ n8n_timezone | default('Europe/Paris') }}" + TZ: "{{ n8n_timezone | default('Europe/Paris') }}" +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + DB_TYPE: "postgresdb" + DB_POSTGRESDB_HOST: "n8n_db" + DB_POSTGRESDB_PORT: "5432" + DB_POSTGRESDB_DATABASE: "{{ n8n_db_name | default('n8n') }}" + DB_POSTGRESDB_USER: "{{ n8n_db_user | default('n8n') }}" + DB_POSTGRESDB_PASSWORD: "{{ n8n_db_password }}" +{% endif %} +{% if n8n_basic_auth_active | default(false) %} + N8N_BASIC_AUTH_ACTIVE: "true" + N8N_BASIC_AUTH_USER: "{{ n8n_basic_auth_user }}" + N8N_BASIC_AUTH_PASSWORD: "{{ n8n_basic_auth_password }}" +{% endif %} + volumes: + - n8n__home_node_n8n:/home/node/.n8n + labels: + traefik.enable: true + traefik.docker.network: traefik + traefik.http.routers.n8n.rule: Host(`{{ n8n_domain }}`) + traefik.http.routers.n8n.tls: true + traefik.http.routers.n8n.tls.certresolver: letsencrypt + traefik.http.routers.n8n.entrypoints: websecure +{% if traefik_ipwhitelist is defined %} + traefik.http.routers.n8n.middlewares: "clientips@docker" +{% endif %} + traefik.http.services.n8n.loadbalancer.server.port: 5678 + com.centurylinklabs.watchtower.enable: {{ n8n_watchtower_enable | default('true') }} + networks: + - traefik +{% if n8n_db_type | default('sqlite') == 'postgresql' %} + - n8n +{% endif %}