--- - name: Swarm hosts: - swarm become: true # # corentinth/it-tools:latest => dinguerie # # apt-get install sshpass # # # # @author Stéphane Gratias (2021). # pre_tasks: # - name: Create node_exporter cert dir # file: # path: "{{ item }}" # state: directory # owner: root # group: root # loop: # - /etc/node_exporter ####lala ### lala # - name: Generate an OpenSSL private key with the default values (4096 bits, RSA) # community.crypto.openssl_privatekey: # path: /etc/node_exporter/tls.key # mode: 0644 # # /etc/node_exporter# chmod 644 tls.key # - name: Generate an OpenSSL Certificate Signing Request # community.crypto.openssl_csr: # path: /etc/node_exporter/tls.csr # privatekey_path: /etc/node_exporter/tls.key # common_name: "{{ inventory_hostname }}.netbird.cloud" # - name: Generate a Self Signed OpenSSL certificate # community.crypto.x509_certificate: # path: /etc/node_exporter/tls.cert # privatekey_path: /etc/node_exporter/tls.key # csr_path: /etc/node_exporter/tls.csr # provider: selfsigned # roles: # # - { role: geerlingguy.docker, tags: docker } # - { role: thomasjpfan.docker-swarm, tags: pip } # # touch /etc/docker/daemon.json # - ansible.builtin.include_role: # name: softing.swarm.softing_swarm_server # vars: # swarm_server_node_ip: "0.0.0.0" # swarm_server_hostname: "{{ hostname }}" # swarm_server_ca_domain: "{{ domain }}" # swarm_server_ca_folder: "/resources/swarm" # roles: # - { role: geerlingguy.pip, tags: pip } # - { role: geerlingguy.docker, tags: docker } # - { role: asg1612.dockerswarm, tags: swarm } tasks: - name: Create network community.docker.docker_network: name: "{{ item.name }}" scope: swarm driver: overlay internal: false attachable: "{{ item.attachable }}" run_once: true loop: - name: agent_network attachable: true - name: public attachable: false when: inventory_hostname in groups['docker_swarm_manager'] #! create inside stack file # - name: Create volume # community.docker.docker_volume: # name: "{{ item }}" # run_once: true # loop: # # - portainer_data # - db-data # - influx-data # when: inventory_hostname in groups['docker_swarm_manager'] - name: Create secret (from a file on the control machine) community.docker.docker_secret: name: "{{ item.name }}" # If the file is JSON or binary, Ansible might modify it (because # it is first decoded and later re-encoded). Base64-encoding the # file directly after reading it prevents this to happen. data: "{{ lookup('file', '{{ playbook_dir }}/{{ item.path }}') | b64encode }}" data_is_b64: true state: present loop: - name: wildcard-jingoh-private.crt path: /files/swarm/tls/jingoh.private.crt - name: wildcard-jingoh-private.key path: /files/swarm/tls/jingoh.private.key run_once: true when: inventory_hostname in groups['docker_swarm_manager'] - name: Create config (from a file on the control machine) community.docker.docker_config: name: traefik-dynamic-configuration # If the file is JSON or binary, Ansible might modify it (because # it is first decoded and later re-encoded). Base64-encoding the # file directly after reading it prevents this to happen. data: "{{ lookup('file', '{{ playbook_dir }}/files/swarm/config/traefik-dynamic-configuration.yml') | b64encode }}" data_is_b64: true state: present run_once: true when: inventory_hostname in groups['docker_swarm_manager'] # - name: Change file ownership, group and permissions # ansible.builtin.file: # path: /opt/stack.yml # owner: root # group: root # mode: '0644' # state: touch # when: inventory_hostname in groups['docker_swarm_manager'] - name: Copy the stack ansible.builtin.copy: content: "version: '3.13'" dest: /opt/stack.yml when: inventory_hostname in groups['docker_swarm_manager'] # - name: Copy file with owner and permissions # ansible.builtin.copy: # src: /{{ playbook_dir }}/files/swarm/stack.yml # dest: /opt/stack.yml # owner: root # group: root # mode: '0644' # run_once: true # when: inventory_hostname in groups['docker_swarm_manager'] - name: Remove stack docker_stack: name: cluster state: absent run_once: true when: inventory_hostname in groups['docker_swarm_manager'] - name: Deploy stack from a compose file community.docker.docker_stack: state: present name: cluster compose: - /opt/stack.yml - version: '3.13' # https://github.com/akhil/traefik-docker-swarm-example/blob/master/traefik.yml - services: traefik: # Image tag (replace with yours) image: traefik:latest command: - "--log.level=DEBUG" - "--accesslog=true" - "--api.dashboard=true" - "--api.insecure=true" - "--entryPoints.web.address=:80" - "--entryPoints.websecure.address=:443" - "--providers.docker=true" - "--providers.docker.watch=true" - "--providers.swarm=true" - "--providers.docker.network=public" - "--providers.docker.endpoint=unix:///var/run/docker.sock" - "--providers.docker.exposedByDefault=false" - "--providers.file.filename=/etc/traefik/configs/traefik-dynamic-configuration.yml" # - "--metrics.prometheus=true" # - "--metrics.prometheus.buckets=0.1,0.3,1.2,5.0" - "--global.checkNewVersion=true" - "--global.sendAnonymousUsage=false" volumes: - "/var/run/docker.sock:/var/run/docker.sock:ro" networks: - public # ports: # - "80:80" # - "443:443" ports: - target: 80 published: 80 protocol: tcp mode: host - target: 443 published: 443 protocol: tcp mode: host # - target: 443 # published: 443 # protocol: udp # mode: host # For Mattermost # - "8443:8443" configs: - source: traefik-dynamic-configuration target: /etc/traefik/configs/traefik-dynamic-configuration.yml secrets: - wildcard-jingoh-private.crt - wildcard-jingoh-private.key deploy: mode: replicated replicas: 1 placement: constraints: - node.role == manager update_config: delay: 15s parallelism: 1 monitor: 10s failure_action: rollback max_failure_ratio: 0.55 labels: - "traefik.enable=true" # Traefik URL (replace with yours) - "traefik.http.routers.dashboard.rule=Host(`lb.jingoh.private`)" - "traefik.http.routers.dashboard.service=api@internal" - "traefik.http.routers.dashboard.entrypoints=websecure" - "traefik.http.services.dashboard.loadbalancer.server.port=8080" - "traefik.http.routers.dashboard.tls=true" - "traefik.http.services.dashboard.loadbalancer.passhostheader=true" - "traefik.http.routers.http-catchall.rule=HostRegexp(`{host:.+}`)" - "traefik.http.routers.http-catchall.entrypoints=web" - "traefik.http.routers.http-catchall.middlewares=redirect-to-https" - "traefik.http.middlewares.redirect-to-https.redirectscheme.scheme=https" - "traefik.http.middlewares.privatevpn.ipwhitelist.sourcerange=100.96.0.0/16" - "traefik.http.routers.dashboard.middlewares=privatevpn,forward-auth" whoami: image: "traefik/whoami" deploy: labels: - "traefik.enable=true" - "traefik.http.routers.whoami-https.rule=Host(`whoamitest.jingoh.private`)" - "traefik.http.routers.whoami-https.entrypoints=websecure" - "traefik.http.routers.whoami-https.service=whoami" - "traefik.http.services.whoami.loadbalancer.server.port=80" - "traefik.http.routers.whoami-https.tls=true" - "traefik.http.routers.whoami-https.middlewares=privatevpn" networks: - public dozzle: container_name: dozzle image: amir20/dozzle:latest environment: - DOZZLE_MODE=swarm volumes: - /var/run/docker.sock:/var/run/docker.sock deploy: mode: global labels: - "traefik.enable=true" - "traefik.http.routers.dozzle-https.rule=Host(`log.jingoh.private`)" - "traefik.http.routers.dozzle-https.entrypoints=websecure" - "traefik.http.routers.dozzle-https.service=dozzle" - "traefik.http.services.dozzle.loadbalancer.server.port=8080" - "traefik.http.routers.dozzle-https.tls=true" - "traefik.http.routers.dozzle-https.middlewares=privatevpn,forward-auth" networks: - public forward-auth: container_name: forward-auth image: thomseddon/traefik-forward-auth:2.2.0 environment: - DEFAULT_PROVIDER=oidc - PROVIDERS_OIDC_CLIENT_ID=X8mqPTQZV0 - PROVIDERS_OIDC_CLIENT_SECRET=Oov5ooTh!u0wee2 - PROVIDERS_OIDC_ISSUER_URL=https://dex.jingoh.fr - SECRET=phuob8ihuJooC - AUTH_HOST=auth.jingoh.private - COOKIE_DOMAIN=jingoh.private - INSECURE_COOKIE=true volumes: - /var/run/docker.sock:/var/run/docker.sock deploy: mode: replicated replicas: 1 labels: - "traefik.enable=true" - "traefik.http.routers.auth.rule=Host(`auth.jingoh.private`)" - "traefik.http.routers.auth.entrypoints=websecure" - "traefik.http.routers.auth.tls=true" - "traefik.http.routers.auth.middlewares=privatevpn,forward-auth" - "traefik.http.routers.auth.service=auth@swarm" - "traefik.http.services.auth.loadbalancer.server.port=4181" - "traefik.http.middlewares.forward-auth.forwardauth.address=http://forward-auth:4181" - "traefik.http.middlewares.forward-auth.forwardauth.trustForwardHeader=true" - "traefik.http.middlewares.forward-auth.forwardauth.authResponseHeaders=X-Forwarded-User" placement: constraints: - node.role == manager networks: - public dozzle-from-file: container_name: dozzle-from-file image: alpine volumes: - /var/log/syslog:/var/log/stream.log - /var/log/auth.log:/var/log/auth.log command: - tail - -f - /var/log/stream.log - /var/log/auth.log restart: unless-stopped deploy: mode: global labels: - "traefik.enable=false" networks: - public networks: public: external: true agent_network: external: true attachable: true volumes: grafana-lib: configs: traefik-dynamic-configuration: external: true secrets: wildcard-jingoh-private.crt: external: true wildcard-jingoh-private.key: external: true run_once: true when: inventory_hostname in groups['docker_swarm_manager'] tags: deploy # docker network create -d overlay agent_network # docker network create -d overlay public # docker volume create portainer_data # Create a secret for storing the certificate using the command: # docker secret create wildcard-jingoh-private.crt jingoh.private.crt # Create a secret for storing the key using the command: # docker secret create wildcard-jingoh-private.key jingoh.private.key # Create a config for storing the Traefik configuration using the command: # docker config create traefik-dynamic-configuration.yml traefik-dynamic-configuration.yml # docker stack deploy -c stack.yml stack # - ansible.builtin.include_role: # name: softing.swarm.softing_swarm_certs # apply: # become: false # delegate_to: "localhost" # run_once: true # vars: # swarm_certs_domain: "swarm.domain.com" # swarm_certs_folder: "{{ playbook_dir }}/resources/swarm" # swarm_certs_nodes: # - ip: 192.168.50.4 # hostname: manager # domain: domain.com # - ip: 192.168.50.40 # hostname: worker1 # domain: domain.com # - ip: 192.168.50.44 # hostname: worker2 # domain: domain.com # - ansible.builtin.include_role: # name: softing.swarm.softing_swarm_initialize # public: yes # vars: # swarm_master_ip: 192.168.50.4 # - ansible.builtin.include_role: # name: "softing_swarm_worker" # vars: # swarm_worker_token: "{{ worker_token }}" # swarm_master_host: "192.168.121.47" # when: inventory_hostname in group['testworker']