personal_infra/ansible/roles/caddy_site/templates/site.conf.j2

35 lines
888 B
Text
Raw Normal View History

caddy: add the caddy_site role Replaces the four-task Caddy vhost block currently copy-pasted into 10 playbooks. Nothing calls it yet; this commit only adds the role. Verified by rendering all 10 sites through the template and diffing against what the current playbooks produce: 9 of 10 byte-identical. The tenth is datum-gateway, where the resolvers comment is standardised, rewriting one comment line Caddy ignores. Then dry-run against the live hosts (--check, nothing written): - vipy: forgejo, vaultwarden, lnbits, personal-blog, ntfy-emergency-app all report ok/unchanged against the real files - watchtower: ntfy renders identical via caddy_site_body, blank line and {host}{uri} placeholders intact - spacey: headscale renders identical when given the config that is actually running - memos, mempool, datum-gateway report changed - the comment, as expected All 14 site files on all 3 hosts confirmed unchanged afterwards. Two things the build turned up: - Ansible does not template dict *keys*, so caddy_site_basic_auth is a list of {user, hash}. As a dict, a Jinja username passes through literally. The assert refuses a mapping. - `caddy validate` does accept a single site fragment - rc=0 on a good one, rc=1 with a line number on a broken one. This was the plan's one untested claim. A failed validate leaves the live file untouched. The reload is now a handler, so it fires once at end of play rather than immediately; anything needing the new config live mid-play must flush_handlers first. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-11 23:10:43 +02:00
{{ caddy_site_domain }} {
{% if caddy_site_body %}
{{ caddy_site_body | trim | indent(4, first=True) }}
{% else %}
{% if caddy_site_basic_auth %}
basic_auth {
{% for cred in caddy_site_basic_auth %}
{{ cred.user }} {{ cred.hash }}
{% endfor %}
}
{% endif %}
{% if caddy_site_root %}
root * {{ caddy_site_root }}
file_server
{% endif %}
{% if caddy_site_upstream %}
{% if caddy_site_headers_up or caddy_site_resolvers %}
reverse_proxy {{ caddy_site_upstream }} {
{% for key, value in caddy_site_headers_up.items() %}
header_up {{ key }} {{ value }}
{% endfor %}
{% if caddy_site_resolvers %}
# Use Tailscale MagicDNS to resolve the upstream hostname
transport http {
resolvers {{ caddy_site_resolvers }}
}
{% endif %}
}
{% else %}
reverse_proxy {{ caddy_site_upstream }}
{% endif %}
{% endif %}
{% endif %}
}