From 59e7676a7d5a1ad993cbc297692cc1718ecd25c9 Mon Sep 17 00:00:00 2001 From: Robin Sonnabend <robin@fsmpi.rwth-aachen.de> Date: Tue, 1 Sep 2020 17:42:39 +0200 Subject: [PATCH] Add role for wireguard Setup wireguard interfaces, configure and deploy keys. Private keys are stored in a file on the host. Public keys are stored in facts, enable fact-caching to allow running the role on a subset of the peers. The dictionary key (interface name) must be the same on all hosts (it identifies the network). At least one peer needs to have a static port specified, so other peers can connect to it. Peers are specified using an inventory hostpattern. This doesn't setup any packet forwarding, DNS server or other VPN features. It just enabled p2p connections (to potentially multiple peers), e.g. to allow serving usually unencrypted applications (like NFS) over an encrypted connection. --- wireguard/defaults/main.yml | 8 +++++ wireguard/handlers/main.yml | 7 +++++ wireguard/tasks/install-Archlinux.yml | 6 ++++ wireguard/tasks/install-Debian.yml | 6 ++++ wireguard/tasks/main.yml | 43 +++++++++++++++++++++++++++ wireguard/templates/wireguard.conf.j2 | 15 ++++++++++ 6 files changed, 85 insertions(+) create mode 100644 wireguard/defaults/main.yml create mode 100644 wireguard/handlers/main.yml create mode 100644 wireguard/tasks/install-Archlinux.yml create mode 100644 wireguard/tasks/install-Debian.yml create mode 100644 wireguard/tasks/main.yml create mode 100644 wireguard/templates/wireguard.conf.j2 diff --git a/wireguard/defaults/main.yml b/wireguard/defaults/main.yml new file mode 100644 index 0000000..922d991 --- /dev/null +++ b/wireguard/defaults/main.yml @@ -0,0 +1,8 @@ +--- + +wireguard_interfaces: {} + +# wg0: +# addresses: ["10.0.0.1", "fd00::1"] +# peers: hostname pattern (as in inventory) +# port: 40000 (optional, set to make reachable by peers) diff --git a/wireguard/handlers/main.yml b/wireguard/handlers/main.yml new file mode 100644 index 0000000..71b65f1 --- /dev/null +++ b/wireguard/handlers/main.yml @@ -0,0 +1,7 @@ +--- + +- name: restart wireguard + systemd: + name: "wg-quick@{{item.key}}.service" + state: restarted + with_dict: "{{wireguard_interfaces}}" diff --git a/wireguard/tasks/install-Archlinux.yml b/wireguard/tasks/install-Archlinux.yml new file mode 100644 index 0000000..61b77c5 --- /dev/null +++ b/wireguard/tasks/install-Archlinux.yml @@ -0,0 +1,6 @@ +--- + +- name: install wireguard on Arch + pacman: + name: wireguard-tools + state: present diff --git a/wireguard/tasks/install-Debian.yml b/wireguard/tasks/install-Debian.yml new file mode 100644 index 0000000..96acad3 --- /dev/null +++ b/wireguard/tasks/install-Debian.yml @@ -0,0 +1,6 @@ +--- + +- name: install wireguard on Debian + apt: + name: wireguard + state: present diff --git a/wireguard/tasks/main.yml b/wireguard/tasks/main.yml new file mode 100644 index 0000000..e57bfdf --- /dev/null +++ b/wireguard/tasks/main.yml @@ -0,0 +1,43 @@ +--- + +- name: ensure wireguard is installed + include_tasks: "install-{{ansible_facts['os_family']}}.yml" + +- name: ensure we have a private key + shell: + cmd: "wg genkey | tee {{item.key}}.key | wg pubkey > {{item.key}}.pub" + chdir: /etc/wireguard + creates: "/etc/wireguard/{{item.key}}.key" + with_dict: "{{wireguard_interfaces}}" + notify: + - restart wireguard + no_log: true + +- name: get the pubkey + slurp: + src: "/etc/wireguard/{{item.key}}.pub" + register: pubkeys + with_dict: "{{wireguard_interfaces}}" + +- name: store the pubkey in facts + set_fact: + wireguard_pubkeys: "{{dict(pubkeys.results|map(attribute='item')|map(attribute='key') | zip(pubkeys.results|map(attribute='content')|map('b64decode')|map('trim')))}}" + cacheable: true + +- name: configure wireguard + template: + src: wireguard.conf.j2 + dest: /etc/wireguard/{{item.key}}.conf + owner: root + group: root + mode: 0600 + with_dict: "{{wireguard_interfaces}}" + notify: + - restart wireguard + +- name: enable interface + systemd: + name: "wg-quick@{{item.key}}.service" + state: started + enabled: true + with_dict: "{{wireguard_interfaces}}" diff --git a/wireguard/templates/wireguard.conf.j2 b/wireguard/templates/wireguard.conf.j2 new file mode 100644 index 0000000..94ff143 --- /dev/null +++ b/wireguard/templates/wireguard.conf.j2 @@ -0,0 +1,15 @@ +[Interface] +Address = {{ item.value.addresses|join(", ") }} +PostUp = wg set %i private-key /etc/wireguard/{{item.key}}.key +{% if item.value.port is defined %} +ListenPort = {{item.value.port}} +{% endif %} + +{% for peer in lookup('inventory_hostnames', item.value.peers, wantlist=True) %} +[Peer] +PublicKey = {{hostvars[peer]['ansible_facts']['wireguard_pubkeys'][item.key]}} +AllowedIPs = {{hostvars[peer]['wireguard_interfaces'][item.key]['addresses'] | join(', ')}} +{% if hostvars[peer]['wireguard_interfaces'][item.key]['port'] is defined %} +Endpoint = {{hostvars[peer]['ansible_facts']['fqdn']}}:{{hostvars[peer]['wireguard_interfaces'][item.key]['port']}} +{% endif %} +{% endfor %} -- GitLab