diff --git a/.sops.yaml b/.sops.yaml
index 98aaf3c..3b728e2 100644
--- a/.sops.yaml
+++ b/.sops.yaml
@@ -33,15 +33,25 @@ keys:
- &host_public_reverse_proxy_ansible_pull_age_key age1p7pxgq5kwcpdkhkh3qq4pvnltrdk4gwf60hdhv8ka0mdxmgnjepqyleyen
- &host_zammad_ansible_pull_age_key age1sv7uhpnk9d3u3je9zzvlux0kd83f627aclpamnz2h3ksg599838qjgrvqs
- &host_ntfy_ansible_pull_age_key age1dkecypmfuj0tcm2cz8vnvq5drpu2ddhgnfkzxvscs7m4e79gpseqyhr9pg
+ external:
+ age: &host_external_age_keys
+ - &host_status_ansible_pull_age_key age1yl9ts8k6ceymaxjs72r5puetes5mtuzxuger7qgme9qkagfrm9hqzxx9qr
creation_rules:
- # group vars
+ ## group vars
- path_regex: inventories/chaosknoten/group_vars/all.*
key_groups:
- pgp:
*admin_gpg_keys
age:
*host_chaosknoten_age_keys
- # host vars
+ - path_regex: inventories/external/group_vars/all.*
+ key_groups:
+ - pgp:
+ *admin_gpg_keys
+ age:
+ *host_external_age_keys
+ ## host vars
+ # chaosknoten hosts
- path_regex: inventories/chaosknoten/host_vars/cloud.*
key_groups:
- pgp:
@@ -150,6 +160,14 @@ creation_rules:
*admin_gpg_keys
age:
- *host_public_reverse_proxy_ansible_pull_age_key
+ # external hosts
+ - path_regex: inventories/external/host_vars/status.*
+ key_groups:
+ - pgp:
+ *admin_gpg_keys
+ age:
+ - *host_status_ansible_pull_age_key
+ # z9 hosts
- path_regex: inventories/z9/host_vars/dooris.*
key_groups:
- pgp:
diff --git a/inventories/external/group_vars/all.sops.yaml b/inventories/external/group_vars/all.sops.yaml
new file mode 100644
index 0000000..06eeb17
--- /dev/null
+++ b/inventories/external/group_vars/all.sops.yaml
@@ -0,0 +1,210 @@
+msmtp__smtp_password: ENC[AES256_GCM,data:0vb2d0BMSiG4DLwNeKk52/kGYM9rQpfRrtYiarbyVW9YOP/WIdpwesUZuad+o6XSODkAGqnU2RQZFs1h,iv:a/LwVf+tQKviYR4mIoSDiEgmsVyCl2v1vWXVFQkn6M4=,tag:bNf+N1bTIk8ppMEabcC6jg==,type:str]
+sops:
+ age:
+ - recipient: age1yl9ts8k6ceymaxjs72r5puetes5mtuzxuger7qgme9qkagfrm9hqzxx9qr
+ enc: |
+ -----BEGIN AGE ENCRYPTED FILE-----
+ YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBkL1F2VVhGTGZ3QWlrZi8w
+ c2JVMVlnNGVHdUxJQVRZeDBlSkJjR3V4NHowCmdQVVJRVEZlWWVHZjdSYzRlcnRN
+ clVuRU1rRXdDSUJ6Tk4rajl1R3U3YzAKLS0tIFg0QXBieXdjYmRab2duckNsNWRQ
+ aGdmdDcwY3RPc28waGt0cm1salpNRkkK+X6LF1lCpxIS8P8nEUE7t3VxB817jm4Y
+ mXjKqdaM39MR3CyXWq8bVQ/QRxg1xA6MV7mLrQpJCSpr6uDJD84iJQ==
+ -----END AGE ENCRYPTED FILE-----
+ lastmodified: "2026-01-15T21:28:28Z"
+ mac: ENC[AES256_GCM,data:Z9uyXhnckrVJ0LZM1aT8cSUZCPdQ0ufBC1HYxpzAGb6FS/p3Jni5tFfgijaCT3/T3yDGiV1zQqoSDLwjd48UaMjCtJYCUCAiVo7i4YJ3+aZfS87b4h4VsOFlTLFlBklNYxHd4pcPFl5X9fZGdD10Tvmtm6TlJ33Ma7gmuFs3Og4=,iv:tNeG2I9qNAgzbGwxTbCrrN7KorCneJtFildGvtPVX88=,tag:e0rXgetLFenA3zNBNe631A==,type:str]
+ pgp:
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAxK/JaB2/SdtARAAlJ6HHQZKe3t86f1Y/DsKmO4f+xaMRd9mw9sNlxvmuX3I
+ b8Tvyl1abbJSEf+6SV3SXxlu+05DZEzerMQHdSNHCpO6oSMBH/fEBbtJh3mxYzwY
+ /fS09/CPpq1HYcaOUEB8YHKGDY7okN8ZCHYFF2fWmWsPNLq38nmtCQY3lKPdhKDu
+ Jg8w+9XT/kHJEjQRPjlJG0iRk90cMMBLaR5ToJVzpM3rOSkK/dFALP9PUGhjDVT/
+ e27KW0OQERCxoc401DXFPJg5xrGMJaDpMlDxm+kzNC2/rt/OhhFd1pqMEMGHwZ8B
+ inHjCL8SNy4w3jKs3xvpE38vEUmKgbHavjjd4j8PU/z8PnIAKBCZClTbBARevMYw
+ P1qgwbAXEv0LwN6/Eu4mN6ogbREFk671PTabJ1O9zWFZBPKSOWVjvs6ka/5nRdow
+ RMobY/t6FDOe1i4eQM90QKyTcyBzyFZCl3piBKDvpG9tTEVHriX4bTXNtnGw3h1W
+ XoMUz27G0IZmKZRcYFkqSNPeg3yLXBgsL6by+euw/OwOXuxcR3G/5HpiO4XgWdDn
+ gYvOGvVa4WbG3yASWPJNJZ6ivtLhAgts44ClMIk5mjDgHz0yL2iwx93g6bUzmswV
+ HcpCLSy7wm5XNl4l5p4l90iy6/K32Zp0a7ftobA7U7VyeWfPalE3IYE3s6b+1gTS
+ XAFWL49B69eVA4YJ/iRSZcfqEPMkKzQUplODPUfaHHtLRwR7BhpFX/u3lly/YNQH
+ tCN+vKShpC2PM/Jw8+UxDZXoXNiGCtTIDFq5+VaifkYsEAIVqEFv5noY95/a
+ =Xw0f
+ -----END PGP MESSAGE-----
+ fp: EF643F59E008414882232C78FFA8331EEB7D6B70
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA6EyPtWBEI+2ARAAqcJfa4paWWvQxKnNQT230iT2iRCCskzkzrG9z9rnSbR+
+ U4BO0QVcKZ06+4/WatZC6HuxIPyajAQthNsmMMBr83OFiT8FPHnOOGHc9lemO0/L
+ eshneJhJ7LeYUh3dOeN5lVwCQuw2Hy4MXmKJgdt2Nr5dXmRD8ypKxD/i5Nc4nkXW
+ TY61C/Q9QJF+HZG4toHt+zq+ROjdsTbIhNceRWnt4mIGvqIzhRwk65o5WILbCFQc
+ OL7R+JyyqouN579tO1O6bRT594ufnyQ6oxLRDQqKMdTHYwWijRuA/FyzieuYGbmo
+ b7e6tZeJzlm3H8sSz1WwAD6RoA/O3yyCw1gL9UWFLSfF7iwEKmr+oSN+mEUPJdhR
+ 8zZqSQUH3n59IVNdD4UyJB/I5AHmGW6QV3ZF42lwmmstIoY3uDzgf3US+ZvPPsem
+ Scg3PIDSxg+SV9G/53TJM+Og7V2XAA02EWIemiIaJZ7rPiySq1RmQOjnx4ZX+ORk
+ +PDF0gDpA10sTPXQM5NoN8YSilIV1VENjUnESfo+36BlCepmbC88Yr6oexIK2xoq
+ 5SnDYNOkVClYcEV6/URo0zr6Eh6+pWaK1MqruyZpRrZFbribK+5t65eIq0fc8oNb
+ ip7VfArpcpYINfL1GuWoFMI0Uj/IMevlN64Ci/Ub9NddCWCQy5WF7u8lAVNMoVbS
+ XAE70ICHJqH9SqHe/dchwYcsLIPwX7r2KoaI23XkK7iROX1NL6LC2nISh/Y5P+X7
+ RX5sBhgiaSwY8L6QseSQzyqTmwxCaq7e/f/+grSUYKmf1FSJe+VxGsJ6Ji0u
+ =k6m5
+ -----END PGP MESSAGE-----
+ fp: F155144FC925A1BEA1F8A2C59A2A4CD59BFDC5EC
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAz5uSgHG2iMJARAAzD/3ycZW/qMLjjSG2T/7378ogylYenCyV5r97m7//MTJ
+ z2jCtWiAPDkiuDDfcqt5LxthPxCr3A/WSTaSsfZQ/zWedQlm/U/RBMEs30DBIUQr
+ AIckqIrJUrgPEo8A0/SnCBNS116BVspI+9n/u7PBPVb70JX3j4Xp3dRGrEYHVpwX
+ EGSk4GirHwutIRE6xP9fnvQxyK64jYTDCfo4t6cIUf2/we0LyK+fU4zrm6wRffzd
+ txiEu4YXvsGbxWeAV3/7/BRo2HJBc/Xqb7mzTnfScltC7hiRD2McmFJs1Hfv0Lg3
+ CGaMOJ5w6Gk8Q+9pgg6R2MQu8DZA7PILm51Bc98ZdiVwg0i8l24ndswUx9+WIWeX
+ AeOxvIVvF0XtQK/JJAkoyoVssIQSFI1OjTDnSHWjFw0Vgev8hRzwqS6HKJUfCrnt
+ KeuGuUOa9QBf3bnbIINyL8QEj9/cnNDCQGoXSZIqPXUs7tIqcLgNryGVnrEn4dDf
+ 53Tudml438QRgzV1d87jEKSmUBtqzUDRNQdZqNbzOdaCQaQgkgZlQvWQtbZNMSdQ
+ iQ+v3Hz7pI4yKHhqxXrWrxPwC3KdGTA5qymUS1d1G0BwOWSr+cU6xJBeSqRc6fZn
+ Q8rBKS/gL2Lm3BAVhHBVWGwtbdBhV5ZL/bdT436pJd5ku3cWFTuiMY2SEC1ZvNXS
+ XAFb+jgjB5XzlRZhRosWl1X/qyWO4GXN4aypi14eAQDsbCjGnFZh6utoV3rNmNFX
+ OJ3kRhyHmF+gbp/e0YRq/BnWu+5uzTZQso4fzepgjui+rF/qk/2Oe1nODtM0
+ =seAB
+ -----END PGP MESSAGE-----
+ fp: 18DFCE01456DAB52EA38A6584EDC64F35FA1D6A5
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAw5vwmoEJHQ1AQ/+J9MXLZrMucsbcgdZ/yflnA7Ai2WynSZ9NEzLX24NybGZ
+ ynq9daa+61w5S5thnEV1Be4YEyFXIXfD0bs9KEO2kv41HUySD9FR5QXXSiad5Ij7
+ vPzZMMwjCfNg/JvGQ9p4h2Syc5LYtJ+4BNnl52zjKCJdp1scJqAist3aWbaHoCAh
+ GiJCjv/02NP25WoVShw9pNvvYPEhtPbvO1j3bnvUARXT8IzhblNbfntDwPb+fK4R
+ ksMBIvAN1171l530s0zPzzkJTkxRBohyCixvtgZKoEnYeUAAHk5Clah6GrLGErvA
+ q0XUAEridgDwe4xG+WpzFWwTaGzQPBLR5NPqtph13/02CdaABctbr80WQPoch5vN
+ F1BnObne8ZE+do30v0KYNTkFKhK5ek+w4RS/1rlBEgQMaNyGHsjUtoO1/6JfFXyT
+ 968gsga/YR/shZwLaxLQePi5qTcvUzGNgNvFLjy4sRlbWiNCrtZo0JpMmRc1YTXb
+ Tq7KhivgEB3gCYLdzWTCeYw3aZXsTFUFM8MpH0BMABpfpNCdiDrd+RZmgDa2KShH
+ RlpqvN1cXPVY4niGqb0TjQJGbmCrMfSbEXCCYLMP+T+jH+MUs0Br4IVcuXIV9EWM
+ WrYY/r2tCblU9DaVbgzLlIIu/2BtKV0/Iu4KLV2vWBocLPNlKnbhS8NxnIf1eHbS
+ XAFxlY0r1uOCI7d55ZRpih3NnccBWYKmxs/WZavFdooPcRS6QKV6d2ByZtjqlO0T
+ X8xmDpyoxkNahauxi3Vw4o78HyxEqQz2u0HNBJlFC6iFQJnylkOyitIyNCTt
+ =t5WG
+ -----END PGP MESSAGE-----
+ fp: 87AB00D45D37C9E9167B5A5A333448678B60E505
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hF4DerEtaFuTeewSAQdArBEh0/AnTDRmDT2r74ejRgmbbZpWjVBmvC7mgFdEq0gw
+ OdEsqFl/ihieW3XkAC0UWxUhacc03Vq3FTY4Fpj7eQTQdfDdn8X10YQcH94XGLxu
+ 0lwBvUseBCslA8gjyzFEtFp4TnDEi2JZV3nhfQg8SxrYIQ2Uo6vlsTzvYBvikwaD
+ kLu7fV7lxV09qoROlSpXVm6II6sIk0nmiajb49HM15md3ZElulGZf7A+6d86Wg==
+ =8Qs3
+ -----END PGP MESSAGE-----
+ fp: 057870A2C72CD82566A3EC983695F4FCBCAE4912
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAxjNhCKPP69fAQ/7B2zWxGFqZr98hAyQwNaXp+/T534xRU63dXkYV15EL9q2
+ SlmbEWhl5iVwWoZHl3r7yqy4zXZJkH0XX7g/MlwMTHIu/Sslvb+9ME+QmpI26Awm
+ +0pQN6gZXEhQ4RFtDMSc3PIZYgaJ5AdEk1p/nMwYsQ17Gu6RZeuSL/5b4oXEsIwB
+ nc8kqskd846KDspSoa4HprP3QUyfwChy5+d3/S/SMak/iY97UgYm3iyHXWr+sbAm
+ ykXGQo6Y/QpSiBBc9Z8hyekBQBjiftTpH5T/nzSn5O1p2G56NqK837SZj8CgyanH
+ xOIy1JZYbSfYiEzqXVSj7KGs3aNFFUi9H+Fy+wzDaOWeEYt76koTWZnutOg+JwCP
+ 2N5DiDOhoYGygh5aO+dAIoGLQufoTDrlMO9FWnNXXCPIwCUoyH5daiMyn7G9jfwv
+ 4rTkXe2mHXXkoNCDHzjNcAEpndpczdUO0CbDNyOuaZzyEYWObJMOdBP0+fmwhaRP
+ AWd0OSbUUkl6RTI7R9l+3wBC0A/be7kOvqvTru0RSZaY4Ba7zokZaNJsoUTvjjL5
+ fjT5MhV/93wEvaHNmGy+IiXipS7ItTmW0xckaFkEbQUbw9p+9UZMxNqF3l5pw8hV
+ J5tTo+rlHda5KBDpTEEz3vUK7MgbgAzzERqqDaUqzWTJy4KeOjYCUfvNyQiT7m3S
+ XAFxCx0poAo6GCoNMhjyQT00iBfpjvUhDrWSHezKW/J/U+Z+TkcICC3Orsxy35uD
+ QtOZIayVIF5scDAIQa31zETB/Jjaq7YeUZvTzUv7Shhq+sJhVUQ7iUEVEXZn
+ =NJUn
+ -----END PGP MESSAGE-----
+ fp: F38C9D4228FC6F674E322D9C3326D914EB9B8F55
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA1Hthzn+T1OoARAAsc5cxMwr0YCwJq1j5EcQ2AF2LvyxH4dvwuCkyrqxuV33
+ rTxOt40kqHcatZgHLfHt1qvfR/lGisUyvvtJ7Gdw/MEzunqwux6cKisRoyTB0dSU
+ b0DBQdNAxujVuBng6v2aoZDXAZNZ9I0epuGnBRcq2+FRAWjRH3YtwuRuChd/VtqB
+ VJJjUJDczermc0kvdrZ6AZ8bSemOIFOYWfZ1iw7qXMiuIXKJqY23KzWSpYC3F9S6
+ z1XKviqJlWcb7VyCA7LDLfjYCAb6/yvj1mB0+fxYJJps6DWsbxvoZWF5mdh5f4oc
+ y74XZehQZTHp4JMs0uSdsuMV3w8zMGUXvFPEJXB1mvPlYAsyjwusf2fqeAJk3JZk
+ pPF/hkwR+LpbVNKk9KbauQLkt+p6E5YWDir1pzeIN6rsl0Carau0TRT9EEn04f/6
+ DL1nF7crXl+7KTgEOt+ih4VuHpXz9lrboUD/WnUpjVu6XwmMH4wrxJggTq+tJzdS
+ 55PAZ0qiTGwnxtOn8NGa+01JGcrmtLnfwRUGUO6xxpyy4AtcyyHwEvBSjKRlBvV2
+ Yx6v6l6OlpBdYdlKjEeOLPnQqn+iRolQtUTWWk1Hu/a2sfJjZPMpXNSKbgN9tMOS
+ 2zGLe8OOU1M9V9ESdD6He49GRCWNXD00Yv+IUdqFuY7laqxBQCcyIthGA2wfLITS
+ XAGKF54TE7VkuCQ2vw0HZG4TgQtmw7W/hBMcbSatGwFwyPSs2+9wsJFmJUniArCZ
+ e7RUz4C1MIFP97ZSFtfLd8tsIO0zTyK9fRAOUwh8wdAZhvS9Fv5/Mwmctj9h
+ =gUj7
+ -----END PGP MESSAGE-----
+ fp: 5DA93D5C9D7320E1BD3522C79C78172B3551C9FD
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA46L6MuPqfJqAQ/8CKPe91CQYybuRlIb4bRl3sZ2nXYw0OS2p8NYo3sawcsw
+ YFwgwT4GHMAMviZ3U/Dm1VVtUEH0dSZ/tYoPFE0pCOLWYrVjqLY69uM23ZHV1IX4
+ W7A+jzNTv3ODj/lc/azjgBcBVZpSxgAQG2wiyX1Dq4Lx5cpOCYQm4KYp9hD6ddly
+ m6zk8vH3MBRvPAlacg3C6PSy1PV7sTgBZMBIE3DY/HIjv4nzV3/itIPZcf27dYTl
+ AEjiI6eGH6sUWTFRF5mCP4sRycaU2g8iZ471nZdHe7PpldginWJEN9SD06oewZJB
+ QjvXpVNjVu+RQ/hOl5LwIllAAkk0ghK2bRsh7gVB5b5Kjv+mKKNe8yjKxKcpZuVW
+ fUEaRpyILTCwe6aFnmUa6vUtpgU2QRKzv2ycqO1FGil1yZJ/RPVCc0RQoLSpZRsT
+ XvrZzw/OVfLespNRPcC/PTvNwhIhBYyIDvEAgQOnEnRCGoijnPAOE4Z5zA6Rtxfw
+ Kxw+E5s+xV1ff+qo5Dm0J/LyC90FR3vstzSkM5n2HEy5OkbACi9CiLRaIiYxlDfv
+ v5H3Gc0hdVRELkK1T9ND3I2RAyJVdDq0WvxjWRIfdRULLsk86pFoFjus0acx3ukt
+ zotRh1wI1o319j517B06v+Jn49bLx81ipeHfsiz69P0sDSRKyOcN/i4TA/Tj0OfS
+ XAFfmEOJHnhD1WOlbJO2EiGY3QD9PIV/lipja4lQKv7ROWlIPVtdvgBnaaNYAvUb
+ YLIA3oTcZB43vm5QW3hXsTz2cn/w/JvnuojtD0kKzT643dR5BC3D2XsWpHWV
+ =pL2f
+ -----END PGP MESSAGE-----
+ fp: 8996B62CBD159DCADD3B6DC08BB33A8ABCF7BC4A
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hF4DQrf1tCqiJxoSAQdAxf+RXofQmgst0qgbY34RgfqVKCCYHHH3mbCdGKbfXiQw
+ 0307FFijrW2i+wHW/Ugob489EH46zUENkmEjxPcOao+p5TWqOhryWOmj+5K5iKin
+ 0lwBDuM+y3AsogL5PAerDRGMIqmUO9AAuRlKJb67O+n31fA0CSlRdYIlR/0IiXk8
+ KmagDpdTyNWD0M8PRohazoKEiB6OrEuLfRiDwyMhyuRtIXRnckwZ8anC2B2cLg==
+ =slU2
+ -----END PGP MESSAGE-----
+ fp: B71138A6A8964A3C3B8899857B4F70C356765BAB
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hF4DzAGzViGx4qcSAQdAYTkme6X4+jr7/5qNidpUZjiwQzR9nhJMHU9ALot5mQkw
+ bVYbs+lqddtYRVKLh4jhqFb9WGjC05JMnb8o/OVqgvOV516WqCzg9qmn2JMn5CvL
+ 0lYBtBwzrQfqM7RbckekoQcabirca/67RzCAqB9O7Lud85+aQxBR/GB9qE/7FLfp
+ JVT42+KjcKSQBYWS+lyjgfXs7H4WhNYsai8OFn+JzqswG+MpWPQ+Fw==
+ =1DIj
+ -----END PGP MESSAGE-----
+ fp: D2E9C0807BF681F5E164DAFC5EE1B61CD90954CD
+ - created_at: "2026-01-15T21:28:06Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA2pVdGTIrZI+ARAAvoshi1af/mG21B9x8XOtYn2CmsjZCLWYWuhdM+oMe204
+ CJglTK8C8CzuJcXu84IKrdV8nx5Yk0VvtgtSXiKSouDKWeQDHHqhKEsPlc6+FL99
+ e95uzp8ozvODxch4xaBP3FZkbgGgFHDZSF47NIC9AkyyGe4GARq+OvtADUMjpb4R
+ 6WXCzqaH976KRMcgH4PXlWIUiYvFJz+6k+chbLfcf+uJxWL02mvPV+ArSbGc1Ns1
+ M2kRYdEPZ4c6FCU6DYaneJp22ywPNgJm3dL8WU7Nn5uv7iYGDyceh3dnGtF0p0jN
+ Mo5TT8MzobIGgD2RtsP4NrufV56+Y4G5oqk9jPMofC8QUeVR1j2GHDfHrls2N/2L
+ vt0VX1wsv7ToAY9bUUNDLutLnwQlpHNP/sacudw0VpYDl55ULa1dLC97qG/4va8G
+ k3wdzqwNwgzIOPDIiQ3P8xkn4RZ9b4SwPNFb9BRqufFaA+neZcNelfpTqsT3WNfm
+ MYdzDQtQdTNi9u0ADsuZ2JIX2uUVsB1ol5Wgw9D5+yksTeC3n89TTmbmt4PYkCZ/
+ 3MH3gLGGlPLfc9w/q9JqfQ8idiPgWc6CMO83gGXUWbe0SkDCBY4evyP41s9ojSdF
+ XrkZQycNoardD+co14Se4d5g0oxYfhNUCIYEo2JwLkuE11iMXG1bjt8JB+F514vS
+ XAHzAelcyBaqqwZqKw1OKWz1Vr+hy9S+uOs+8Qg5G/H0nxa7BG+PhUB+O5i8x4Dn
+ 96Eq2r2OsVJ3z8YeLcH2FbnVECX+/nj8a4z8yqfpajmoKswOfhp2b2G49aYz
+ =IYeC
+ -----END PGP MESSAGE-----
+ fp: 878FEA3CB6A6F6E7CD80ECBE28506E3585F9F533
+ unencrypted_suffix: _unencrypted
+ version: 3.11.0
diff --git a/inventories/external/group_vars/all.yaml b/inventories/external/group_vars/all.yaml
new file mode 100644
index 0000000..80d3efc
--- /dev/null
+++ b/inventories/external/group_vars/all.yaml
@@ -0,0 +1,16 @@
+# ansible_pull
+# ansible_pull__age_private_key needs to be defined per host (probably HOST.sops.yaml).
+ansible_pull__repo_url: https://git.hamburg.ccc.de/CCCHH/ansible-infra.git
+ansible_pull__inventory: inventories/external
+ansible_pull__playbook: playbooks/maintenance.yaml
+ansible_pull__timer_on_calendar: "*-*-* 04:30:00 Europe/Berlin"
+ansible_pull__failure_notification_address: noc-notifications@lists.hamburg.ccc.de
+ansible_pull__timer_randomized_delay_sec: 30min
+
+# msmtp
+# msmtp__smtp_password is defined in the all.sops.yaml.
+msmtp__smtp_host: cow.hamburg.ccc.de
+msmtp__smtp_port: 465
+msmtp__smtp_tls_method: smtps
+msmtp__smtp_user: any@external-hosts.hamburg.ccc.de
+msmtp__smtp_from: "{{ inventory_hostname }}@external-hosts.hamburg.ccc.de"
diff --git a/inventories/external/host_vars/status.sops.yaml b/inventories/external/host_vars/status.sops.yaml
new file mode 100644
index 0000000..e300459
--- /dev/null
+++ b/inventories/external/host_vars/status.sops.yaml
@@ -0,0 +1,212 @@
+ansible_pull__age_private_key: ENC[AES256_GCM,data:u0tluAG5YmXTs71/F6RjuTITCrEoJco0K7+o/F7An4OMdOAwJVBvvMCnEaYsKhLhdesnMIoA24oz2j22lKRFgZUNtkF08ZwH9gw=,iv:oqTTeOi8l6ig4vvqOKict5bqxjmiBW+kwlZhbozoCSU=,tag:ZL2wuIczCHguGJIhbY0NuQ==,type:str]
+secret__gatus_db_password: ENC[AES256_GCM,data:fwtdWmXVTA7odBsKnlxH7mKKGtplAt/rQqscFBAxbDky6DNqgk6PP2OsqbIEpnpzs9Yn7Kd2VAxzfJfK,iv:ox/Lm+LlxxRcssOPc++nRp6nVa2DF3/46eEsGzTOBmA=,tag:i1e71Gm01ojHr5pGy0S9rA==,type:str]
+secret__gatus_matrix_access_token: ENC[AES256_GCM,data:wp6C2E/LM3grawu8oW5CZZU0Y2+3qnuEbcKmgZr16e8P1KG/v2kfxRQ=,iv:S96oyGg6hI2Co7PJ8BFtrzZag82PTfp2IyIgTbxfdiM=,tag:JROk5PdoaMzXq1qXGgaH7g==,type:str]
+sops:
+ age:
+ - recipient: age1yl9ts8k6ceymaxjs72r5puetes5mtuzxuger7qgme9qkagfrm9hqzxx9qr
+ enc: |
+ -----BEGIN AGE ENCRYPTED FILE-----
+ YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA2Y0Vib1U3ZGpyZTlBNWMx
+ UEtCbnArRzAvZ0o1dmdJL0hSZERTR241RlNrCjZ6QzlJSEFhWk0wazlwRVlDeUlq
+ M0syWDZlc0o2d2NDYmVyUmJpWUdwdzAKLS0tIGR5NUVwMkprRnkxZnI0TmlGUGVk
+ RFl1MnI1K0h2MUhvYk40d2JjbDRaUmMKNlPo1s06hVdxAamKhJy4HhNDX8PKQlq2
+ 13PjdTJub64fydGEJng5NigcnNcPo7goGLz5QV7vE+6bO0gNZxBmmw==
+ -----END AGE ENCRYPTED FILE-----
+ lastmodified: "2026-01-17T23:54:35Z"
+ mac: ENC[AES256_GCM,data:K/uLPclyRgFOMhSxPpFOiH1fQF0EQHKUNnqI/LW0o6+ON07r+UWv9mXaT2M7xUNhgHkv4lVu/qfLAKXZUVGlDga5ufH3A6xbcArqtQ5oyPoE5HX0nbcU4QF1f8JyYLVKCQdI0pBQkLU2cpAFHrGVLI/8+RY/uqrtNee9f7fd4cM=,iv:WRfTSWo4cfJOvjQqeSrSUCOstCf0FggTv2W4eGRcTF8=,tag:GE9cLzmJZt3F11BZd82HFA==,type:str]
+ pgp:
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAxK/JaB2/SdtAQ/+ORxsmaobaTVCnVlaaTlvG3GRPlL0G1NG18eF3Mra2FU/
+ HSY4/QTu4BjGRzwOlKJt3NBMGlFZucwklIecAl1cCDXPSvIRnwuIsAI8gxNnjmVW
+ w7URAscgfVobWxpLqFhlnQ+8ozMPXW7D0ZDLe4wKPa5wNuE/kdzM5ZCl3NB4q3fi
+ o0C8uSnsTAp8clay/xnTtnJxOsyzyJ29JVsinxAyg64m6AYNa53yNZoy5kL6VIIr
+ dnNx4DtOsxFuNhKuvENePoGjuB68i0NWitsfei3G+GLUp+CbPisrzElM6vsXQ0wT
+ QAu2OpTnrQSv/YWi8Dv+1YXIKu6nOuMc+avQGLsiuZ6hagrvfRTmoQirbx6THDB+
+ 97N/ZZUoGVdCtb5BRoBxzl7prwYGXsW+fP7B/PlBBBM5pI/s5jasFMOBfrrlJiDE
+ dyBcE2rjcehmZ0DN0YddZoo1UMYzsn6HEMH+kFp/VD3+y4A47Kk9Ou0d9+Q7ufsf
+ j8ThNihOBrwz8DlvOb5/5HacBFOH5T9b42j6yOmyrlAXnC8sQwFDMDERs7XcVSXT
+ B9SlX6OVZ6/xgG1UjkY5aqYiWkIBUO/9k1OP3OMoZM7WPitIJS0a92u8EASX4zT9
+ cJjyym8oDojsM4+/GWMCHcEA5QVSEFsz5JBONiEJkv9UCYXOWj375SH6WjTHQyPS
+ XgFA0rCYobVrmH4oQ3EzmbqTGwBuejwcDVA++KiUePb6jhK9DGrETHEOzUyOonpI
+ tNfgyohULH3eDRjC/4gR9JDr+UCC2t31Rx5kNmonz4H3KQlgm/5UulKZZfFk6VQ=
+ =HCWY
+ -----END PGP MESSAGE-----
+ fp: EF643F59E008414882232C78FFA8331EEB7D6B70
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA6EyPtWBEI+2AQ/+Is5OSeCOwUDFocaFiGIpKKicsRkF5WJXcV0eTquCvn3M
+ UeDpYww0CatCOmx0u5/ELzyvr2NhLGwoblLxwwb2HA+dTWRzRiTGZrpGJ3DUwEK6
+ KvqFgrOIDttnSCqrGiPsNBkGP3oIH/WIYXF4SJl5stlnujTOW+wNP8f+9gZspyY4
+ JdDXIGL7cbvzEzionilKbroKgDTNCm/o/ATWnlvsd5qv8lsIVkZlaJqldRR+xXuu
+ RLHz9Mav9NgzzFERA0YY0Z56jpGikoywB7iBCbozXvPO5oY9YcuvdLoXELi3Rimf
+ LoqIyGv/dHepZvIIy/d+E7ltlQHLXdH0LMNyBRartVChR/p0G/YAzXDAgnARJm+J
+ SB7vUPBqFwFpkiIE0bRRDVDYW8VlNZta4V+hxb3iXuVHljuYUrIDh77VW3xNQyi5
+ YfKxO9c9PRhq7sfeBj3iB2qAGoODOU1whdaWXJeNIvYmkQJw81eu2rzHT6NHsbrD
+ CcUGvbVAO7cx8xZxLiT2jZlbeRrTM68Uq8zC0ujzHavrLUWvCcAcFdk8Un8UJbaF
+ W4B5La8ZAQUg0HwDavrOEXFbbdkuMT0BIMIxysxrcetqMdRcMjQlbjHz7RuROp4q
+ melLD0F7L8cXAafDRXXkTTpDmaLN8s9v2j953/RzY7lS1FPQMTduWbn4Pg75HrbS
+ XgEWsmhgtxSNSgtg/c+VyS9VAykAaP0J4mVWUJZtpw3T8wtkAVeb2zFjmOWay98e
+ GC9m9N32zdg6MZDLnAABIEhDCGhuB0QjHJaXHcQxbuy8T0mgG081s8spTZnU/74=
+ =v7Jf
+ -----END PGP MESSAGE-----
+ fp: F155144FC925A1BEA1F8A2C59A2A4CD59BFDC5EC
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAz5uSgHG2iMJAQ//f4YuazCNqBuU6RxLg7gbh2RQ7KQ9QDIPSh+YIBr2k9RJ
+ zSjTIR2cPu4JX7Bf9w378oyExhxe6bU00DKvfmQv+CPwjR/4NfzB+/UjmrOEmZqv
+ y/Gc/2ciT2csHiuAgmck/tKCdVLyXmlMpR+ru3LBVpXLc0wRqDLze9RKM22L5o5Y
+ Tkf5LCoj77ixhVWZJ/MUm1GlCKmtAJ5tZpSOUenSApSZ0mbRUMI6SEmLhf7ApmNo
+ FInztB8eMcgyV7vhEmhAiLTkB29kGh8Oe/TtDSmywhn/pTcs4tlY7fRfcxkJaYgw
+ sZFaF3b7/xhF04kJNEugKemTZTCOoXuPvjvDKQ0glojQQ36P5S01uyH1FOHAbItz
+ 8xilRiU5lHuu7BsZcb8rU8qNYnpEzY3DX/Ccpl0AoPWjY925XB7C8H8z1kk8UxR1
+ +b3XXMktUugeTZeiFG2pJsp9dhiRqyuzvW73yJSdHjqZW+Tq4U2D9Je1WeZT4+Au
+ qTQh1uC2dRgQ0PMafX50aTxIK7lPxva+cOPgYeALXP58TCUqeNUyYQmvAGba7yyU
+ yec3Hz/SNLqEhSnOqCx+TXZOhV4PM8fTzpnNhqZQ2RX2uUXwXjuyAZ8fv3v5se8F
+ HvQGW8EvJaDSvLD5GjKblQqwNlFWf0HOPUf5UZSXV3MHsHLzYHKlOE4cJ778ih7S
+ XgGY+6q602ciOETbXexRAK4G0AaAY06iQqIvjqzTRmRgkftMI/8HAV2mfjfRuTXF
+ 9DClJje/SpRp/fS6jXFyRCc1MysABsxcyopIhHPxf2iy4UiipC1c15Z9VVK4cL4=
+ =l9vN
+ -----END PGP MESSAGE-----
+ fp: 18DFCE01456DAB52EA38A6584EDC64F35FA1D6A5
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAw5vwmoEJHQ1ARAAr6u7xDPFlylAf002AQkjASgSyCdLMD0LxXmTEihOxBnp
+ +ZcJN9cpuyCuDaIfSqGdDLUqZ6TuAfVaixtXbxT6Odl2q1DN/GaVkZbDVwGk/W3w
+ +lSjBz4miAcU9kaSFeeJ9BDEdqROduj8/fFc8jLyxpa51nnp6ON7wI3Uup3uNZN1
+ oEwcav8u9hrbE5glS6IMFpGQAhJmvzWH9mHWCQT7A3GGK3DsYBWPH685vVk80VBw
+ 8IO35N2SMVD+ebvFbSnitBSOmSNUzHgv8DaBgJkcHb5EM8bCiZNI3VkbGdi8AmRx
+ wvuAclYkemq/bNu5I0sjpt/uxEOVqsymdPs+gOVgKceEy458ZfyRUPxV0Xp5Yi26
+ MzAas8LCL+m561L8MTt01CfXJKllIh1aeNJEWYKyTtIxnWfhHnhAfiwiRaX+sAdK
+ ApLFSCtwAf2fvpqaUY0PvAwKUNKyEBrncu9cBuqK6EDx5YVQul6Mo2nx6W64G7mj
+ IUGQOoRATZP4y9bJJJMNU5BfK9j7Fdhh/VirB1XSSWSlkUduv8PVx99iLejfnknB
+ b0LVS0RW0W+XgbM0yvjRhDATalrcuBX4R7voQPeGFlw//fdg0qepSe9OeAPA+RNm
+ YTjWVWqXOmGJQ46sms4P1Fhd5NKgyv7qAaZDVf2lDZOensbhwWFKw1R65PSbi4DS
+ XgEDIaRdmRPMHOGoHzcSieR+sxDvklEAWyfUMn8D8u8dkgs1u8WL3gGixDaPMvcF
+ JgS3PA6hl0JOi3+UgBWGh6gx+C/mr+6jly+IhWd78HAsbsJcGIrs4Zlu54T8jV4=
+ =8IWz
+ -----END PGP MESSAGE-----
+ fp: 87AB00D45D37C9E9167B5A5A333448678B60E505
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hF4DerEtaFuTeewSAQdA7STwRBnvhKhEh9mdHz/GWujTMli/vbMrXv8WnZ1boUkw
+ 9Qtj+soJcdr8XxDREm//Q7wgGZJSJe6dBdxW5NC10H7bYDFc9aNkbT0/ceMj0tBM
+ 0l4BNU1LT9rZrkhGUTqA3Gs+bzP4xazBGuiucCkM1mbSvRAjWO2abLb17GKUWODr
+ 1uDStVFrPOTqN/0/O1lAfk/Xv5LQO2X/xVMDD42i9txP9G8+rCF42gKdODWF+DsQ
+ =FVIu
+ -----END PGP MESSAGE-----
+ fp: 057870A2C72CD82566A3EC983695F4FCBCAE4912
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMAxjNhCKPP69fARAAkUEvumeteWHZ31xbvLAWezQr75Q45DVzBAX6MJIPnCcz
+ ofMYuDjz/ujOES7UtAYrRekCW4R+PZQ2pcC3tbNHxKQjdxsA6cY68mBQLj+TJ0+F
+ 15jlkAkL7utwOxOh8P1/yxO+hr3qZl6rmncQwiynRnyiAJa6FHK8dvAHVKhLWcRN
+ pxx2O5m8I/+sF2/XgVs0iq0KWG+WbwJWUlvWKJ+2LNvXDoPYD0sdo8G1hkuQGOLW
+ Lmc1xN4hbTzvgjTBoUt1HUEOgohau8TMWnT7x1jpMLBNqm0hQfcyNmBuK4vA3NYR
+ PjtMUvEuucjOrFvF1g+OaTQ3ZSkd431yqTHRbktZDXdCvhYhSfxJ2TKdqX5U+3p+
+ 27hPOX5cVISd36T8Oxm7LTt2GSZp5JZJ2gzRuSn8HDEHHBa39+jmdsqmGMFjAJfU
+ amK3TNpLx9U/AGw9CYVyQxfnrRPArjuPXE+nVmuZVJhgOcex+5SAA6YRpzPLj5/I
+ bHv0zOQ+84ghaIPvA7OlehgE2DYQjFC7qMGV0Q/jEomzHmwaFLlbDiSX97SQM4+P
+ dwe2gbz5EfgVdXeSwyPH03W5Uq/D8GiNFASxe6ctfwY6G9cUJaY7gj+br2/WSjzc
+ bSQxbyA36q6tSR8sty4lOkRqfhvCsopnACe3UaPDD9aUPu5dkrPFD2DwGZqALjrS
+ XgGQM27HAK2eAWtmQk7wWZcK8EyeO4bPl/JX8hMU8xSnbHrFpY26RNY1C4mjqcnD
+ QoyU68TbPmGX522sseuygCNmEEM/5rhx6wwePH1X+C8WRHMmXyLjKD3eVkFJ3tA=
+ =EPrs
+ -----END PGP MESSAGE-----
+ fp: F38C9D4228FC6F674E322D9C3326D914EB9B8F55
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA1Hthzn+T1OoAQ//arOC3Dpt+X+GzGZFPngYFGl8SHgx9vrbNcNdRQBEBhX0
+ RmkT3rBbXRNbJvZHW6YPzoMRzhDMHEs9osbr7RwpTQxpL4owFd1hx8bhDjZYQplC
+ Gfj1xNjL1iFsQV1kWx7dagpkDEoPVlPaDyTDyHkj/fmgg/aU4y5GVUHc6l7iClN9
+ fn5HL8/sCROAPteReXnwxIWmn/03lldh7VMYwKaVIpiTf3QZzEsHAOYT0EdEcapC
+ 3d5ZhTDmOvOwy2PMfx5w5RpKXKe2cbhoS1N3KEHaZIochlvnvQHpVJ3jhn8YG8j9
+ bJ5tklEauoi1YHsnj5vzm8sgQMj/p5DJHALfVKxzAMCCe0AqcVpVGTW9SR1ZMUXW
+ p0UZOmeNBfqhcOIbKXW+Hj2oSZ25KGxiXZwydF51xnUT8rsau7nPYOgg+9YARAVl
+ USZd85OX/dZcDqhfK1YZjdV3GPiTHGFUrTz53sW/nHrcCCKXL17uADLr1Z/rk3Dm
+ dayNuUVhlqgV6Z0ts0Z9blz2X/Bz2c95TUTze+pUoXCP6oKcxGbrEfHBzJrhqeFa
+ PYGRyna1t96c3Az94bz2orX69Ij3QPyd2p2B0nlv+qYNk55J/aVPIfioZSamnDk9
+ NAQJksb2M7KIq1rjheWsf/CLZYHC1rcrhUnz5SYIXVDe8f3+uNc0JFGYPYZuF7DS
+ XgEa4Lw21RwQs3Es0wAZSnkku+yg1Lg2YJ6/d5xSZJs0c5mCYvvW3q9oTc8u+D3n
+ H1/Lu8HvZtHtGARagLqHw2MORNvoJXoCT0EhcPBK4PlJKSNye96U1ooNfwxbUMo=
+ =0Nal
+ -----END PGP MESSAGE-----
+ fp: 5DA93D5C9D7320E1BD3522C79C78172B3551C9FD
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA46L6MuPqfJqARAAlYT9Xqnfvd7uWr/V8Ca5oKJ003yWKGwAMd06zyPmIYOK
+ ErTHC98r7LXuGaMcIUrJ+oLf6YipYB7PyHwfz+zpxhDRTPAxXTqkF1ecLi7qg2AV
+ Ez3Q1hpPJv1DWASrVfJgpnlQnQtnpqXQsInL7klGc10mtbgc2zHUndWFqjxtkAhl
+ IinLZHZVFaijFw10W+e6T0UUZ9WfIPdCOChcqVp5/86DDyl3S9dBLmAd7wywzbuH
+ i0y1uelIxLyYmzLxYTNgJwEHKzQvF6jrj40AjT8HtUD473ILD5M4p2vdvNCUANu9
+ 1iF4q7YM5g6cgjGC29Y31wOAM4YzdkwNXJsUhn4ACzYNBAItXK7Aw0I8WK9AnUfq
+ lwmSirx5hi870GIfu/OYeNt4I3fWjm4qY1aFwoJJRWrUdH94I4P1O6xXZyTVqpmG
+ m0Ich3O16Ir1vS9oFLdFSFGP7UZgU7D5314OKXNsEGpFLGa9U7AG1ZPHGSb6tAQi
+ 9Df7TsWxYVWKBU2PbI/D9StVlWDVilt2QiKtIcRwLs3/3JrzTPJd9tvUtw6Tyjw7
+ N12/SE3yHwWxVPUXF2AsopmOoHGh67Ki+6oc7xTmxtcJWSITUhBL16ZjMEEXFeHy
+ FMODciBLrXO1jWz65mkB32ttV+oPQuCdtFPTzuKneDhVBybuMJrx7DEIFaf5CmvS
+ XgFrqRe9fua4zRd9r9tJE4RSosQOAhmVgRVCJIg5B+qUGC0l2AwO4ro1+a02t6o7
+ uBGGRHeQYrGv6HVUd/xfirUj/mtrguiSSpOy3UZ5SHIlPxuj/2jf3WxVkU0QP5k=
+ =e4Qe
+ -----END PGP MESSAGE-----
+ fp: 8996B62CBD159DCADD3B6DC08BB33A8ABCF7BC4A
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hF4DQrf1tCqiJxoSAQdAqRvfYgKUyKqP1jy9+s3UQ+vqUWQVxC/zXkcXOs/G3kQw
+ 27MDd3dcADzCI4qrHxc0umrFegUizTg9UmseMgSJnr7oWXtuh6ocjuEe+irXw0Di
+ 0l4B7cvZtRObjrOUf0lupPAp2xPIIKekUcVSxiecn6z7zVUVUwpYvPmS8MBCFc5h
+ 7ad0LWml36Rj5UkBE/ph0YgLvz7ZDoC1yiagBGVX59MTjjZsZBVpRecxZ+ztuaci
+ =68na
+ -----END PGP MESSAGE-----
+ fp: B71138A6A8964A3C3B8899857B4F70C356765BAB
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hF4DzAGzViGx4qcSAQdA95lt4L0inJjhMwQ2v5lvhW74zuvdpgktHsp5BSycbxcw
+ oUR2v3CcCHtNzWzgeWPm8L6JHRUJQWdg+XHsLujlZXsoqKirGI67NvToOk+yttsK
+ 0lgBW9AG8bUVUdXNNPfhc/FN8OJbQ2cj3E2z5kI05ZrkcOoZVXaRfXJiZPQDg1Kz
+ LhuKymMDmXXsSVd/VdLbSXpfeEqMJjTsDS+bU/TZAcRRPKxj9PPDJIWQ
+ =Kpzf
+ -----END PGP MESSAGE-----
+ fp: D2E9C0807BF681F5E164DAFC5EE1B61CD90954CD
+ - created_at: "2026-01-15T21:23:56Z"
+ enc: |-
+ -----BEGIN PGP MESSAGE-----
+
+ hQIMA2pVdGTIrZI+ARAA2IaYLn8z593Kh+wAw2ecOXkW+B3qhi/x0qQLVw7Jc1hO
+ rVhrcTQoabL3elIIPZtxyTYIXq6EpPkSBMOBHO+tmqI8YsB5GvWtcGV1OBpRaZ3I
+ hgKjnxkJtaQizSZqZLgGUVXjMjcdkzTlIQfu7oGeTu8Ke1cwtOE1lvleDpHHK6gc
+ yRLJWsUfHdv3rCOmRCDtguc3NG7qzUUYcknPiFGx66hfnIaA0aJav2pqS3uuRwSD
+ Ay78U2PB7kYVg//Omz9BEuiUVhYsA0sl3hFVpJuKv7FQ9OcJOevQddfq90m2KGyo
+ 2Lpligwtj3evPfPReLR1D16HaGuzknoB9883jD027+fGr4/IFWx7ieVZ9iGeD3jR
+ yw/GdHCMueq1pdtyw8ArREspGmZldEKY3Qw6sfRdd71DAeTkD1zzWORCEk6OQefY
+ YX5ByUAOTUHvTey4Uy5WCj3HOUMW71CnVpsU6lDSuqBUnFlMvELtcjlmEAwvscXz
+ WFpTzphaX1fIqruS4BAzMxpKVTI1V3bnrb6wFRFnsErVjrty24R2auaoHvgslROu
+ 1QUTInC7JpFUpxiK9ke8xbhYlZ5JEhcxOXlfrZcVwlxziEZEqp429L/4gVz+IGVv
+ YQ4wU8ARBcXiEDEOmEl3tCxiprDlCeLpdSrqhq57/y7IMs6Fo7QrkA5XZG+mnfPS
+ XgHFg3iMBk0qKb6AiWiN8g3SHJtcehJgmAZsRxFRP329QKGGa+azQqT7Vp066keY
+ rOsmP8iwl+4KS71+cN9rLx/3U8EcSxRuMU6KtIKvhp7yfr2bhYo8P9JH2vrPTlk=
+ =lbdI
+ -----END PGP MESSAGE-----
+ fp: 878FEA3CB6A6F6E7CD80ECBE28506E3585F9F533
+ unencrypted_suffix: _unencrypted
+ version: 3.11.0
diff --git a/inventories/external/host_vars/status.yaml b/inventories/external/host_vars/status.yaml
new file mode 100644
index 0000000..c2c26b3
--- /dev/null
+++ b/inventories/external/host_vars/status.yaml
@@ -0,0 +1,27 @@
+docker_compose__compose_file_content: "{{ lookup('ansible.builtin.template', 'resources/external/status/docker_compose/compose.yaml.j2') }}"
+docker_compose__configuration_files:
+ - name: "general.yaml"
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/docker_compose/config/general.yaml') }}"
+ - name: "sites.yaml"
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/docker_compose/config/sites.yaml') }}"
+ - name: "services-chaosknoten.yaml"
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/docker_compose/config/services-chaosknoten.yaml') }}"
+ - name: "websites.yaml"
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/docker_compose/config/websites.yaml') }}"
+ - name: "easterhegg-websites.yaml"
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/docker_compose/config/easterhegg-websites.yaml') }}"
+
+nginx__version_spec: ""
+nginx__deploy_redirect_conf: false
+nginx__configurations:
+ - name: status.hamburg.ccc.de
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/nginx/status.hamburg.ccc.de.conf') }}"
+ - name: http_handler
+ content: "{{ lookup('ansible.builtin.file', 'resources/external/status/nginx/http_handler.conf') }}"
+
+certbot__version_spec: ""
+certbot__acme_account_email_address: le-admin@hamburg.ccc.de
+certbot__certificate_domains:
+ - "status.hamburg.ccc.de"
+certbot__new_cert_commands:
+ - "systemctl reload nginx.service"
diff --git a/inventories/external/hosts.yaml b/inventories/external/hosts.yaml
new file mode 100644
index 0000000..435a9bf
--- /dev/null
+++ b/inventories/external/hosts.yaml
@@ -0,0 +1,24 @@
+all:
+ hosts:
+ status:
+ # TODO: Manually set up ufw on the host. Create a role for ufw.
+ ansible_host: status.hamburg.ccc.de
+ ansible_user: chaos
+base_config_hosts:
+ hosts:
+ status:
+docker_compose_hosts:
+ hosts:
+ status:
+nginx_hosts:
+ hosts:
+ status:
+certbot_hosts:
+ hosts:
+ status:
+infrastructure_authorized_keys_hosts:
+ hosts:
+ status:
+ansible_pull_hosts:
+ hosts:
+ status:
diff --git a/resources/external/status/docker_compose/compose.yaml.j2 b/resources/external/status/docker_compose/compose.yaml.j2
new file mode 100644
index 0000000..04abf95
--- /dev/null
+++ b/resources/external/status/docker_compose/compose.yaml.j2
@@ -0,0 +1,36 @@
+# https://gatus.io/
+# https://github.com/TwiN/gatus
+# https://github.com/TwiN/gatus/blob/master/.examples/docker-compose-postgres-storage/compose.yaml
+
+services:
+ database:
+ image: docker.io/library/postgres:18.1
+ volumes:
+ - ./database:/var/lib/postgresql
+ environment:
+ - "POSTGRES_DB=gatus"
+ - "POSTGRES_USER=gatus"
+ - "POSTGRES_PASSWORD={{ secret__gatus_db_password }}"
+ networks:
+ - gatus
+
+ gatus:
+ image: ghcr.io/twin/gatus:v5.34.0
+ restart: always
+ ports:
+ - "8080:8080"
+ environment:
+ - "GATUS_CONFIG_PATH=/config"
+ - "POSTGRES_DB=gatus"
+ - "POSTGRES_USER=gatus"
+ - "POSTGRES_PASSWORD={{ secret__gatus_db_password }}"
+ - "MATRIX_ACCESS_TOKEN={{ secret__gatus_matrix_access_token }}"
+ volumes:
+ - ./configs:/config
+ networks:
+ - gatus
+ depends_on:
+ - database
+
+networks:
+ gatus:
diff --git a/resources/external/status/docker_compose/config/easterhegg-websites.yaml b/resources/external/status/docker_compose/config/easterhegg-websites.yaml
new file mode 100644
index 0000000..87feb4c
--- /dev/null
+++ b/resources/external/status/docker_compose/config/easterhegg-websites.yaml
@@ -0,0 +1,303 @@
+# Easterhegg Websites and Websites (Redirects)
+# (hosted on public-web-static)
+# One could probably also generate this list from the public-web-static config.
+easterhegg-websites-defaults: &easterhegg_websites_defaults
+ group: Websites
+ interval: 5m
+ alerts:
+ - type: matrix
+ failure-threshold: 3
+ success-threshold: 1
+ minimum-reminder-interval: "12h"
+ send-on-resolved: true
+
+easterhegg-websites-redirects-defaults: &easterhegg_websites_redirects_defaults
+ group: Websites (Redirects)
+ interval: 15m
+ alerts:
+ - type: matrix
+ failure-threshold: 3
+ success-threshold: 1
+ minimum-reminder-interval: "24h"
+ send-on-resolved: true
+
+endpoints:
+ # Websites
+ - name: eh03.easterhegg.eu
+ url: "https://eh03.easterhegg.eu"
+ <<: *easterhegg_websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easter(h)egg 2003*)"
+
+ - name: eh05.easterhegg.eu
+ url: "https://eh05.easterhegg.eu"
+ <<: *easterhegg_websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2005 - The workshop weekend*)"
+
+ - name: eh07.easterhegg.eu
+ url: "https://eh07.easterhegg.eu"
+ <<: *easterhegg_websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ - name: eh09.easterhegg.eu
+ url: "https://eh09.easterhegg.eu"
+ <<: *easterhegg_websites_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ - name: eh11.easterhegg.eu
+ url: "https://eh11.easterhegg.eu"
+ <<: *easterhegg_websites_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ - name: eh20.easterhegg.eu
+ url: "https://eh20.easterhegg.eu"
+ <<: *easterhegg_websites_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*EH20 - Back to root*)"
+
+ # Websites (Redirects)
+ # eh03.easterhegg.eu
+ - name: eh2003.hamburg.ccc.de
+ url: "https://eh2003.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easter(h)egg 2003*)"
+
+ - name: www.eh2003.hamburg.ccc.de
+ url: "https://www.eh2003.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easter(h)egg 2003*)"
+
+ - name: easterhegg2003.hamburg.ccc.de
+ url: "https://easterhegg2003.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easter(h)egg 2003*)"
+
+ - name: www.easterhegg2003.hamburg.ccc.de
+ url: "https://www.easterhegg2003.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easter(h)egg 2003*)"
+
+ # eh05.easterhegg.eu
+ - name: eh2005.hamburg.ccc.de
+ url: "https://eh2005.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2005 - The workshop weekend*)"
+
+ - name: www.eh2005.hamburg.ccc.de
+ url: "https://www.eh2005.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2005 - The workshop weekend*)"
+
+ - name: easterhegg2005.hamburg.ccc.de
+ url: "https://easterhegg2005.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2005 - The workshop weekend*)"
+
+ - name: www.easterhegg2005.hamburg.ccc.de
+ url: "https://www.easterhegg2005.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2005 - The workshop weekend*)"
+
+ # eh07.easterhegg.eu
+ - name: eh2007.hamburg.ccc.de
+ url: "https://eh2007.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ - name: www.eh2007.hamburg.ccc.de
+ url: "https://www.eh2007.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ - name: eh07.hamburg.ccc.de
+ url: "https://eh07.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ - name: www.eh07.hamburg.ccc.de
+ url: "https://www.eh07.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ - name: easterhegg2007.hamburg.ccc.de
+ url: "https://easterhegg2007.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ - name: www.easterhegg2007.hamburg.ccc.de
+ url: "https://www.easterhegg2007.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2007 - The Workshop weekend*)"
+
+ # eh09.easterhegg.eu
+ - name: eh2009.hamburg.ccc.de
+ url: "https://eh2009.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ - name: www.eh2009.hamburg.ccc.de
+ url: "https://www.eh2009.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ - name: eh09.hamburg.ccc.de
+ url: "https://eh09.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ - name: www.eh09.hamburg.ccc.de
+ url: "https://www.eh09.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ - name: easterhegg2009.hamburg.ccc.de
+ url: "https://easterhegg2009.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ - name: www.easterhegg2009.hamburg.ccc.de
+ url: "https://www.easterhegg2009.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2009*)"
+
+ # eh11.easterhegg.eu
+ - name: eh2011.hamburg.ccc.de
+ url: "https://eh2011.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ - name: www.eh2011.hamburg.ccc.de
+ url: "https://www.eh2011.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ - name: eh11.hamburg.ccc.de
+ url: "https://eh11.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ - name: www.eh11.hamburg.ccc.de
+ url: "https://www.eh11.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ - name: easterhegg2011.hamburg.ccc.de
+ url: "https://easterhegg2011.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ - name: www.easterhegg2011.hamburg.ccc.de
+ url: "https://www.easterhegg2011.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*Easterhegg 2011*)"
+
+ # eh20.easterhegg.eu
+ - name: www.eh20.easterhegg.eu
+ url: "https://www.eh20.easterhegg.eu"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*EH20 - Back to root*)"
+
+ - name: eh20.hamburg.ccc.de
+ url: "https://eh20.hamburg.ccc.de"
+ <<: *easterhegg_websites_redirects_defaults
+ conditions:
+ - "[status] == 200"
+ - "[certificate_expiration] > 48h"
+ - "[BODY] == pat(*EH20 - Back to root*)"
diff --git a/resources/external/status/docker_compose/config/general.yaml b/resources/external/status/docker_compose/config/general.yaml
new file mode 100644
index 0000000..c67811a
--- /dev/null
+++ b/resources/external/status/docker_compose/config/general.yaml
@@ -0,0 +1,25 @@
+storage:
+ type: postgres
+ path: "postgres://${POSTGRES_USER}:${POSTGRES_PASSWORD}@database:5432/${POSTGRES_DB}?sslmode=disable"
+
+ui:
+ title: CCCHH Status
+ description: Automated uptime monitoring and status page for CCCHH services. Powered by Gatus.
+ header: CCCHH Status
+ buttons:
+ - name: Website
+ link: "https://hamburg.ccc.de"
+ - name: Git
+ link: "https://git.hamburg.ccc.de"
+ - name: Kontakt & Impressum
+ link: "https://hamburg.ccc.de/imprint/"
+ default-sort-by: group
+
+alerting:
+ matrix:
+ server-url: "https://matrix-client.matrix.org"
+ access-token: "${MATRIX_ACCESS_TOKEN}"
+ internal-room-id: "!jG755onbGAH-lZsZo8SRKtlsncSMvq7nzPhwCi5CgdQ"
+
+# A bit more than the default 5 concurrent checks should be fine.
+concurrency: 15
diff --git a/resources/external/status/docker_compose/config/services-chaosknoten.yaml b/resources/external/status/docker_compose/config/services-chaosknoten.yaml
new file mode 100644
index 0000000..0792e95
--- /dev/null
+++ b/resources/external/status/docker_compose/config/services-chaosknoten.yaml
@@ -0,0 +1,264 @@
+# Services (Chaosknoten)
+services-chaosknoten-defaults: &services_chaosknoten_defaults
+ group: Services (Chaosknoten)
+ interval: 1m
+ alerts:
+ - type: matrix
+ failure-threshold: 5
+ success-threshold: 2
+ minimum-reminder-interval: "6h"
+ send-on-resolved: true
+
+endpoints:
+ - name: CCCHH ID/Keycloak (main page/account console)
+ url: "https://id.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*JavaScript is required to use the Account Console.*)"
+
+ - name: CCCHH ID/Keycloak (ccchh realm)
+ url: "https://id.hamburg.ccc.de/realms/ccchh/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY].realm == ccchh"
+
+ - name: ccchoir
+ url: "https://ccchoir.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*The Choir of the Chaos Computer Club*)"
+
+ - name: Cloud (status info)
+ url: "https://cloud.hamburg.ccc.de/status.php"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY].installed == true"
+ - "[BODY].maintenance == false"
+
+ - name: Cloud (main page/login)
+ url: "https://cloud.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Sign in to CCCHH*)"
+
+ - name: cow (main page/login)
+ url: "https://cow.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*mailcow UI*)"
+
+ - name: cow (SMTP port 25)
+ url: "tcp://cow.hamburg.ccc.de:25"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: cow (SMTPS port 465)
+ url: "tls://cow.hamburg.ccc.de:465"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: cow (SMTP with STARTTLS port 587)
+ url: "starttls://cow.hamburg.ccc.de:587"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: cow (IMAP port 143)
+ url: "tcp://cow.hamburg.ccc.de:143"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: cow (IMAPS port 465)
+ url: "tls://cow.hamburg.ccc.de:465"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: Design/penpot
+ url: "https://design.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Penpot - Design Freedom for Teams*)"
+
+ - name: EH22 Website/Wiki
+ url: "https://eh22.easterhegg.eu/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2025*)"
+
+ - name: Git
+ url: "https://git.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*CCCHH Git*)"
+
+ - name: GitLab
+ url: "https://gitlab.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Moin beim Gitlab des CCC Hamburg!*)"
+
+ - name: Grafana
+ url: "https://grafana.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Sign in to CCCHH*)"
+
+ - name: Jitsi
+ url: "https://jitsi.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Jitsi Meet*)"
+
+ - name: Lists
+ url: "https://lists.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Mailing Lists*)"
+
+ - name: Matrix
+ url: "https://matrix.hamburg.ccc.de/_matrix/client/versions"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "has([BODY].versions) == true"
+ - "has([BODY].unstable_features) == true"
+
+ - name: Mumble (tcp)
+ url: "tcp://mumble.hamburg.ccc.de:64738"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: Mumble (udp)
+ url: "udp://mumble.hamburg.ccc.de:64738"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: NetBox
+ url: "https://NetBox.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*NetBox*)"
+
+ - name: ntfy
+ url: "https://ntfy.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*ntfy web requires JavaScript*)"
+
+ - name: OnlyOffice
+ url: "https://onlyoffice.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*ONLYOFFICE Docs Community Edition installed*)"
+
+ - name: Pad
+ url: "https://pad.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*HedgeDoc - Ideas grow better together*)"
+
+ - name: Pretalx (main page)
+ url: "https://pretalx.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*pretalx*)"
+
+ - name: Pretalx (EH22/Easterhegg 2025)
+ url: "https://cfp.eh22.easterhegg.eu/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Easterhegg 2025*)"
+ - "[BODY] == pat(*pretalx*)"
+
+ - name: SpaceAPI
+ url: "https://spaceapi.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY].space == CCCHH"
+
+ - name: Surveillance under Surveillance
+ url: "https://sunders.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Surveillance under Surveillance*)"
+
+ - name: Tickets/pretix
+ url: "https://tickets.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*pretix*)"
+
+ - name: Wiki
+ url: "https://wiki.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*CCCHH Wiki*)"
+
+ - name: Woodpecker
+ url: "https://woodpecker.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Woodpecker*)"
+
+ - name: Zammad
+ url: "https://zammad.hamburg.ccc.de/"
+ <<: *services_chaosknoten_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*zammad*)"
diff --git a/resources/external/status/docker_compose/config/sites.yaml b/resources/external/status/docker_compose/config/sites.yaml
new file mode 100644
index 0000000..7b0ce82
--- /dev/null
+++ b/resources/external/status/docker_compose/config/sites.yaml
@@ -0,0 +1,23 @@
+# Sites
+sites-defaults: &sites_defaults
+ group: Sites
+ interval: 1m
+ alerts:
+ - type: matrix
+ failure-threshold: 5
+ success-threshold: 2
+ minimum-reminder-interval: "6h"
+ send-on-resolved: true
+
+endpoints:
+ - name: Chaosknoten/IRZ42
+ url: "icmp://chaosknoten.hamburg.ccc.de"
+ <<: *sites_defaults
+ conditions:
+ - "[CONNECTED] == true"
+
+ - name: Z9
+ url: "icmp://185.161.129.129"
+ <<: *sites_defaults
+ conditions:
+ - "[CONNECTED] == true"
diff --git a/resources/external/status/docker_compose/config/websites.yaml b/resources/external/status/docker_compose/config/websites.yaml
new file mode 100644
index 0000000..e54337a
--- /dev/null
+++ b/resources/external/status/docker_compose/config/websites.yaml
@@ -0,0 +1,174 @@
+# Websites, Websites (Staging) and Websites (Redirects)
+# (hosted on public-web-static)
+# One could probably also generate this list from the public-web-static config.
+websites-defaults: &websites_defaults
+ group: Websites
+ interval: 1m
+ alerts:
+ - type: matrix
+ failure-threshold: 5
+ success-threshold: 2
+ minimum-reminder-interval: "6h"
+ send-on-resolved: true
+
+websites-staging-defaults: &websites_staging_defaults
+ group: Websites (Staging)
+ interval: 5m
+ alerts:
+ - type: matrix
+ failure-threshold: 3
+ success-threshold: 1
+ minimum-reminder-interval: "24h"
+ send-on-resolved: true
+
+websites-redirects-defaults: &websites_redirects_defaults
+ group: Websites (Redirects)
+ interval: 5m
+ alerts:
+ - type: matrix
+ failure-threshold: 3
+ success-threshold: 1
+ minimum-reminder-interval: "24h"
+ send-on-resolved: true
+
+endpoints:
+ # Websites
+ - name: branding-resources.hamburg.ccc.de
+ url: "https://branding-resources.hamburg.ccc.de/logo/sources.txt"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*file: ccchh-logo.png*)"
+
+ - name: c3cat.de
+ url: "https://c3cat.de"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Cat Ears Operation Center*)"
+
+ - name: cryptoparty-hamburg.de
+ url: "https://cryptoparty-hamburg.de"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Digitale Selbstverteidigung in Hamburg*)"
+
+ - name: element-admin.hamburg.ccc.de
+ url: "https://element-admin.hamburg.ccc.de"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Loading Element Admin*)"
+
+ - name: element.hamburg.ccc.de
+ url: "https://element.hamburg.ccc.de"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Sorry, Element requires JavaScript to be enabled.*)"
+
+ - name: hacker.tours
+ url: "https://hacker.tours"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ # Once suites support alerting, we can also monitor the target as well.
+ - "[BODY] == pat(**)"
+
+ - name: hackertours.hamburg.ccc.de
+ url: "https://hackertours.hamburg.ccc.de"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ # Once suites support alerting, we can also monitor the target as well.
+ - "[BODY] == pat(**)"
+
+ - name: hamburg.ccc.de
+ url: "https://hamburg.ccc.de"
+ <<: *websites_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Wir sind der Chaos Computer Club der Hansestadt Hamburg.*)"
+
+# Websites (Staging)
+ - name: staging.c3cat.de
+ url: "https://staging.c3cat.de"
+ <<: *websites_staging_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*c3cat.de Staging Environment*)"
+
+ - name: staging.cryptoparty-hamburg.de
+ url: "https://staging.cryptoparty-hamburg.de"
+ <<: *websites_staging_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*cryptoparty-hamburg.de Staging Environment*)"
+
+ - name: staging.hacker.tours
+ url: "https://staging.hacker.tours"
+ <<: *websites_staging_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*hacker.tours Staging Environment*)"
+
+ - name: staging.hackertours.hamburg.ccc.de
+ url: "https://staging.hackertours.hamburg.ccc.de"
+ <<: *websites_staging_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*hackertours.hamburg.ccc.de Staging Environment*)"
+
+ - name: staging.hamburg.ccc.de
+ url: "https://staging.hamburg.ccc.de"
+ <<: *websites_staging_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*hamburg.ccc.de Staging Environment*)"
+
+# Website (Redirects)
+ - name: www.c3cat.de
+ url: "https://www.c3cat.de"
+ <<: *websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Cat Ears Operation Center*)"
+
+ - name: cryptoparty.hamburg.ccc.de
+ url: "https://cryptoparty.hamburg.ccc.de"
+ <<: *websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Digitale Selbstverteidigung in Hamburg*)"
+
+ - name: staging.cryptoparty.hamburg.ccc.de
+ url: "https://staging.cryptoparty.hamburg.ccc.de"
+ <<: *websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*cryptoparty-hamburg.de Staging Environment*)"
+
+ - name: www.hamburg.ccc.de
+ url: "https://www.hamburg.ccc.de"
+ <<: *websites_redirects_defaults
+ conditions:
+ - "[STATUS] == 200"
+ - "[CERTIFICATE_EXPIRATION] > 48h"
+ - "[BODY] == pat(*Wir sind der Chaos Computer Club der Hansestadt Hamburg.*)"
diff --git a/resources/external/status/nginx/http_handler.conf b/resources/external/status/nginx/http_handler.conf
new file mode 100644
index 0000000..c989ede
--- /dev/null
+++ b/resources/external/status/nginx/http_handler.conf
@@ -0,0 +1,14 @@
+server {
+ listen 80 default_server;
+ listen [::]:80 default_server;
+
+ server_name status.hamburg.ccc.de;
+
+ location / {
+ return 301 https://$host$request_uri;
+ }
+
+ location /.well-known/acme-challenge/ {
+ proxy_pass http://127.0.0.1:31820/.well-known/acme-challenge/;
+ }
+}
diff --git a/resources/external/status/nginx/status.hamburg.ccc.de.conf b/resources/external/status/nginx/status.hamburg.ccc.de.conf
new file mode 100644
index 0000000..510966a
--- /dev/null
+++ b/resources/external/status/nginx/status.hamburg.ccc.de.conf
@@ -0,0 +1,33 @@
+# partly generated 2022-01-08, Mozilla Guideline v5.6, nginx 1.17.7, OpenSSL 1.1.1k, intermediate configuration
+# https://ssl-config.mozilla.org/#server=nginx&version=1.17.7&config=intermediate&openssl=1.1.1k&guideline=5.6
+server {
+ listen 443 ssl http2 default_server;
+ listen [::]:443 ssl http2 default_server;
+
+ server_name status.hamburg.ccc.de;
+
+ ssl_certificate /etc/letsencrypt/live/status.hamburg.ccc.de/fullchain.pem;
+ ssl_certificate_key /etc/letsencrypt/live/status.hamburg.ccc.de/privkey.pem;
+ # verify chain of trust of OCSP response using Root CA and Intermediate certs
+ ssl_trusted_certificate /etc/letsencrypt/live/status.hamburg.ccc.de/chain.pem;
+
+ # HSTS (ngx_http_headers_module is required) (63072000 seconds)
+ add_header Strict-Transport-Security "max-age=63072000" always;
+
+ proxy_set_header Host $host;
+ proxy_set_header X-Forwarded-Host $host;
+ proxy_set_header X-Real-IP $remote_addr;
+ proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
+ proxy_set_header X-Forwarded-Port 443;
+ # This is https in any case.
+ proxy_set_header X-Forwarded-Proto https;
+ # Hide the X-Forwarded header.
+ proxy_hide_header X-Forwarded;
+ # Assume we are the only Reverse Proxy.
+ # Also provide "_hidden" for by, since it's not relevant.
+ proxy_set_header Forwarded "for=$remote_addr;proto=https;host=$host;by=_hidden";
+
+ location / {
+ proxy_pass http://127.0.0.1:8080/;
+ }
+}