Manages compute resources on Hetzner Cloud.
See requirements.txt for python library dependencies.
Given is a inventory similar as:
[web]
web-1
web-2
web-3The following variables are meant to be set in a top level group, e.g.group_vars/all.yml.
API key:
NOTE: Recommended to encrypt this token with Ansible Vault or use a lookup to your secrets management system!
hcloud__api_token: ...Ensures a private network is created:
hcloud__networks:
- name: internal
network: 10.10.10.0/24Ensure some firewalls and rules are created:
hcloud__firewalls:
- name: default
rules:
- direction: in
protocol: icmp
source_ips:
- 0.0.0.0/0
- ::/0
- direction: in
protocol: tcp
port: "22"
source_ips:
- 0.0.0.0/0
- name: web
rules:
- direction: in
protocol: tcp
port: "80"
source_ips:
- 0.0.0.0/0
- ::/0
- direction: in
protocol: tcp
port: "443"
source_ips:
- 0.0.0.0/0
- ::/0Ensure placment groups are created:
hcloud__placement_groups:
- name: my placement group
labels:
project: genesisConfigure a simple load balancer and add servers as targets later (see server configs):
hcloud__loadbalancers:
- name: my load balancer
type: lb11
services:
- protocol: http
port: 80
- protocol: tcp
port: 443
destination_port: 443Configure a load balancer and use label selector hcloud feature:
hcloud__loadbalancers:
- name: my load balancer
type: lb11
targets:
- type: label_selector
label_selector: app=public
services:
- protocol: http
port: 80
health_check:
interval: 15
port: 80
timeout: 3
retries: 3
protocol: http
http:
# Single wildcard char '?' or glob wildcard '*'
status_codes:
- 2*
- 3*
- 40?
# Optional
path: /
domain: www.example.com
response: hello world
- protocol: tcp
port: 443
destination_port: 443The following configs are server specific and meant to be set in a lower level group_vars or host_vars, e.g. group_vars/web.yml
Server image to use:
hcloud__server_image: debian-11Location to deploy into:
hcloud__server_location: fsn1Ensure web servers have these firewalls configured:
hcloud__server_firewalls:
- default
- webEnsure web servers are attached to these networks:
hcloud__server_networks:
- name: internalEnsure web servers are in a placement group:
hcloud__server_placement_group: my placement groupAdd server to an existing loadbalancer as server target (optionally use private IP):
hcloud__server_loadbalancer_name: my load balancer
hcloud__server_loadbalancer_use_private_ip: trueEnsure web server have this type:
hcloud__server_type: cpx11User data to be executed on boot, e.g.:
hcloud__server_user_data: |
#cloud-config
users:
- name: admin
groups: users, admin
sudo: ALL=(ALL) NOPASSWD:ALL
shell: /bin/bash
ssh_authorized_keys:
- <public_ssh_key>
packages:
- fail2ban
package_update: true
package_upgrade: trueEnsure a volume is created and attached to the server:
HINT: Use the special variable
inventory_hostname_shortas prefix to easily identify which volume is attached to which server.
hcloud__server_volumes:
- name: "{{ inventory_hostname_short }}-vol1"
format: ext4
size: 10A typical playbook would look like this.
---
- name: Provision Cloud servers
hosts: all
serial: 5
gather_facts: false
roles:
- role: ngine_io.hcloud
delegate_to: localhost
post_tasks:
- name: Wait for SSH access
delegate_to: localhost
wait_for:
host: "{{ ansible_host }}"
port: 22
timeout: 60MIT
René Moser (@resmo)