Preserve state when disabling gomuks, use valid persistent VAPID keys, require usable authentication credentials, and pin the container image. Bring role variables, file permissions, documentation, changelog, and SPDX attribution in line with project conventions. Fix gomuks mount flag for older Docker: --mount type=bind ... rw is invalid on Docker < 23 (requires key=value). Other roles use bare dst=/data for rw (default) and ,ro for readonly. This fixes a systemctl failure: invalid field 'rw' must be a key=value pair.pull/5574/head
| @@ -1,3 +1,12 @@ | |||
| # 2026-08-26 | |||
| ## Support for gomuks | |||
| The playbook can now install [gomuks](docs/configuring-playbook-client-gomuks.md), a Matrix client with a Go backend and a web frontend. The backend stores encryption keys and continues syncing while the browser is closed. | |||
| gomuks is disabled by default. Enabling it requires a separate password to protect the backend. Its database and encryption keys remain on the server if the component is disabled later. | |||
| # 2026-08-20 | |||
| ## MatrixRTC transports are advertised in the client well-known again | |||
| @@ -1,5 +1,6 @@ | |||
| <!-- | |||
| SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| SPDX-License-Identifier: AGPL-3.0-or-later | |||
| --> | |||
| @@ -8,7 +9,7 @@ SPDX-License-Identifier: AGPL-3.0-or-later | |||
| The playbook can install and configure [gomuks](https://github.com/gomuks/gomuks) for you. | |||
| gomuks is a Matrix client written in Go. The `gomuks` container in this playbook runs the gomuks backend which serves the web frontend. It acts as a bouncer — keeping your encryption keys and syncing in the background, even when the browser is closed. See the project's [documentation](https://docs.mau.fi/gomuks/) to learn what it does and why it might be useful to you. | |||
| gomuks is a Matrix client written in Go. The `gomuks` container runs the backend and serves the web frontend. The backend stores your encryption keys and continues syncing while the browser is closed. See the project's [documentation](https://docs.mau.fi/gomuks/) for more information. | |||
| By default, this playbook does not install gomuks. Element Web remains the default client. | |||
| @@ -16,7 +17,7 @@ By default, this playbook does not install gomuks. Element Web remains the defau | |||
| By default, this playbook installs gomuks on the `gomuks.` subdomain (`gomuks.example.com`) and requires you to create a CNAME record for `gomuks`, which targets `matrix.example.com`. | |||
| When setting, replace `example.com` with your own. | |||
| When creating the record, replace `example.com` with your own domain. | |||
| ## Adjusting the playbook configuration | |||
| @@ -24,11 +25,16 @@ To enable gomuks, add the following configuration to your `inventory/host_vars/m | |||
| ```yaml | |||
| matrix_client_gomuks_enabled: true | |||
| # This protects the gomuks backend and is separate from your Matrix password. | |||
| matrix_client_gomuks_auth_password: "YOUR_STRONG_PASSWORD_HERE" | |||
| ``` | |||
| Replace `YOUR_STRONG_PASSWORD_HERE` with a strong password. | |||
| ### Adjusting the gomuks URL (optional) | |||
| By tweaking the `matrix_client_gomuks_hostname` and `matrix_client_gomuks_path_prefix` variables, you can easily make the service available at a **different hostname and/or path** than the default one. | |||
| You can make the service available at a different hostname or path by changing `matrix_client_gomuks_hostname` and `matrix_client_gomuks_path_prefix`. | |||
| Example additional configuration for your `vars.yml` file: | |||
| @@ -45,35 +51,26 @@ After changing the domain, **you may need to adjust your DNS** records to point | |||
| If you've decided to reuse the `matrix.` domain, you won't need to do any extra DNS configuration. | |||
| **Note**: `matrix_client_gomuks_path_prefix` must either be `/` or not end with a slash (e.g. `/gomuks`). | |||
| ### Adjusting authentication (optional) | |||
| gomuks protects its web interface with a basic-auth username and password (separate from your Matrix account). The playbook auto-generates these from `matrix_homeserver_generic_secret_key`: | |||
| `matrix_client_gomuks_path_prefix` must either be `/` or not end with a slash, such as `/gomuks`. | |||
| - `matrix_client_gomuks_auth_username` — defaults to `gomuks` | |||
| - `matrix_client_gomuks_auth_password` — auto-generated, truncated hash of the secret key | |||
| ### Configuring authentication | |||
| To set your own credentials, add the following to your `vars.yml`: | |||
| gomuks protects its web interface with a basic-auth username and password which are separate from your Matrix account. `matrix_client_gomuks_auth_username` defaults to `gomuks`. You must define `matrix_client_gomuks_auth_password` when enabling the service, unless you disable gomuks authentication as described below: | |||
| ```yaml | |||
| matrix_client_gomuks_auth_username: "myuser" | |||
| matrix_client_gomuks_auth_password: "mysupersecretpassword" | |||
| matrix_client_gomuks_auth_username: "gomuks" | |||
| matrix_client_gomuks_auth_password: "YOUR_STRONG_PASSWORD_HERE" | |||
| ``` | |||
| The playbook derives a bcrypt hash automatically. You can also set the hash directly: | |||
| The playbook stores only a bcrypt hash of this password in the gomuks configuration file. | |||
| ```yaml | |||
| matrix_client_gomuks_auth_password_hash: "$2a$12$..." | |||
| ``` | |||
| If your gomuks instance is behind an authenticating reverse proxy and you prefer to handle auth there, you can disable gomuks' own auth: | |||
| If your gomuks instance is behind an authenticating reverse proxy and you prefer to handle authentication there, you can disable gomuks authentication: | |||
| ```yaml | |||
| matrix_client_gomuks_disable_auth: true | |||
| ``` | |||
| When disabling auth, be careful not to expose gomuks to untrusted networks. See the [gomuks FAQ](https://docs.mau.fi/gomuks/faq.html#can-i-run-the-backend-behind-a-reverse-proxy) for details. | |||
| `matrix_client_gomuks_auth_password` is not required when authentication is disabled. Be careful not to expose gomuks to untrusted networks. See the [gomuks FAQ](https://docs.mau.fi/gomuks/faq.html#can-i-run-the-backend-behind-a-reverse-proxy) for details. | |||
| ### Extending the configuration | |||
| @@ -81,15 +78,17 @@ There are some additional things you may wish to configure about the component. | |||
| Take a look at: | |||
| - `roles/custom/matrix-client-gomuks/defaults/main.yml` for some variables that you can customize via your `vars.yml` file | |||
| - `roles/custom/matrix-client-gomuks/templates/config.yaml.j2` for the component's default runtime configuration. gomuks stores additional settings (like VAPID keys, `token_key`, etc.) in `/data/config/config.yaml`; the playbook generates them from your `matrix_homeserver_generic_secret_key` so that they remain stable across restarts | |||
| - `roles/custom/matrix-client-gomuks/defaults/main.yml` for variables that you can customize via your `vars.yml` file | |||
| - `roles/custom/matrix-client-gomuks/templates/config.yaml.j2` for the default runtime configuration | |||
| By default, gomuks generates a VAPID key pair for Web Push on first startup. The playbook preserves this pair on later runs. You can instead supply a pair with `matrix_client_gomuks_push_vapid_private_key` and `matrix_client_gomuks_push_vapid_public_key`; both variables must be set together. | |||
| Additional useful variables include: | |||
| Other useful variables include: | |||
| - `matrix_client_gomuks_container_image` — override the container image | |||
| - `matrix_client_gomuks_web_listen_address` — listen address inside the container | |||
| - `matrix_client_gomuks_origin_patterns` — allowed `Origin` header patterns | |||
| - `matrix_client_gomuks_insecure_cookies` — allow cookies over plain HTTP (useful without TLS, not recommended) | |||
| - `matrix_client_gomuks_container_image` to override the container image | |||
| - `matrix_client_gomuks_web_listen_address` to change the listen address inside the container | |||
| - `matrix_client_gomuks_origin_patterns` to change the allowed `Origin` header patterns | |||
| - `matrix_client_gomuks_insecure_cookies` to allow cookies over plain HTTP, which is not recommended | |||
| ## Installing | |||
| @@ -109,25 +108,25 @@ The shortcut commands with the [`just` program](just.md) are also available: `ju | |||
| After installation, gomuks will be available at `https://gomuks.example.com` (or your custom hostname/path). | |||
| 1. Open the URL in your browser. | |||
| 2. You will be prompted for the gomuks basic-auth credentials (see [Adjusting authentication](#adjusting-authentication-optional)). This is **not** your Matrix password — it's the bouncer protection. | |||
| 2. Enter the gomuks basic-auth credentials described in [Configuring authentication](#configuring-authentication). These are not your Matrix credentials. | |||
| 3. Log in with your Matrix account (user ID, password, homeserver). | |||
| Your encryption keys stay on the server's `/matrix/client-gomuks/data` directory, so the backend keeps syncing even when no browser is open. | |||
| All gomuks data (config, database, logs) lives under `{{ matrix_client_gomuks_data_path }}` (`/matrix/client-gomuks` by default) on the server. | |||
| The `matrix_client_gomuks_data_path` variable controls where gomuks stores its configuration, database, cache, and logs. Its default value is `/matrix/client-gomuks`. Disabling gomuks stops and removes the service but preserves this directory. | |||
| ## Troubleshooting | |||
| As with all other services, you can find the logs in [systemd-journald](https://www.freedesktop.org/software/systemd/man/systemd-journald.service.html) by logging in to the server with SSH and running `journalctl -fu matrix-client-gomuks`. | |||
| If you changed `matrix_client_gomuks_auth_password` and cannot log in, note that the browser may have cached the old basic-auth credentials — try a private window or clear site data. | |||
| If you changed `matrix_client_gomuks_auth_password` and cannot log in, the browser may have cached the old basic-auth credentials. Try a private window or clear the site's data. | |||
| If you see errors about `origin_patterns`, verify that `matrix_client_gomuks_hostname` and `matrix_client_gomuks_origin_patterns` include the hostname you are using to access gomuks (without `https://` and with explicit port if non-standard). | |||
| To reset gomuks completely (removes database and forces re-login), stop the service and remove its data directory, then re-run the playbook: | |||
| To log out and remove the locally stored Matrix account state, stop the service and remove its data and cache directories. This preserves the gomuks configuration and VAPID keys: | |||
| ```sh | |||
| systemctl stop matrix-client-gomuks | |||
| rm -rf /matrix/client-gomuks/data/* | |||
| # then re-run: just setup-all --tags=setup-client-gomuks | |||
| rm -rf /matrix/client-gomuks/data /matrix/client-gomuks/cache | |||
| just install-service client-gomuks | |||
| ``` | |||
| @@ -99,7 +99,6 @@ Web clients for Matrix that you can host on your own domains. | |||
| - [Setting up gomuks](configuring-playbook-client-gomuks.md), if you've enabled [gomuks](https://github.com/gomuks/gomuks), a bouncer-style Matrix client with a web frontend | |||
| ### Authentication and user-related | |||
| Extend and modify how users are authenticated on your homeserver. | |||
| @@ -4792,13 +4792,13 @@ matrix_client_gomuks_enabled: false | |||
| matrix_client_gomuks_scheme: "{{ 'https' if matrix_playbook_ssl_enabled else 'http' }}" | |||
| matrix_client_gomuks_hostname: "gomuks.{{ matrix_domain }}" | |||
| matrix_client_gomuks_hostname: "{{ matrix_server_fqn_gomuks }}" | |||
| matrix_client_gomuks_container_http_host_bind_port: "{{ (matrix_playbook_service_host_bind_interface_prefix ~ '29325') if matrix_playbook_service_host_bind_interface_prefix else '' }}" | |||
| matrix_client_gomuks_container_network: "{{ matrix_addons_container_network }}" | |||
| matrix_client_gomuks_container_additional_networks: "{{ [matrix_playbook_reverse_proxyable_services_additional_network] if (matrix_client_gomuks_container_labels_traefik_enabled and matrix_playbook_reverse_proxyable_services_additional_network) else [] }}" | |||
| matrix_client_gomuks_container_additional_networks_auto: "{{ [matrix_playbook_reverse_proxyable_services_additional_network] if (matrix_client_gomuks_container_labels_traefik_enabled and matrix_playbook_reverse_proxyable_services_additional_network) else [] }}" | |||
| matrix_client_gomuks_container_labels_traefik_enabled: "{{ matrix_playbook_reverse_proxy_type in ['playbook-managed-traefik', 'other-traefik-container'] }}" | |||
| matrix_client_gomuks_container_labels_traefik_docker_network: "{{ matrix_playbook_reverse_proxyable_services_additional_network }}" | |||
| @@ -4808,6 +4808,8 @@ matrix_client_gomuks_container_labels_traefik_tls_certResolver: "{{ traefik_cert | |||
| matrix_client_gomuks_container_labels_traefik_compression_middleware_enabled: "{{ matrix_playbook_reverse_proxy_traefik_middleware_compression_enabled }}" | |||
| matrix_client_gomuks_container_labels_traefik_compression_middleware_name: "{{ matrix_playbook_reverse_proxy_traefik_middleware_compression_name if matrix_playbook_reverse_proxy_traefik_middleware_compression_enabled else '' }}" | |||
| matrix_client_gomuks_self_check_validate_certificates: "{{ matrix_playbook_ssl_enabled }}" | |||
| ###################################################################### | |||
| # | |||
| # /matrix-client-gomuks | |||
| @@ -1,4 +1,5 @@ | |||
| # SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| # SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| # SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| # | |||
| # SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -9,7 +10,7 @@ | |||
| matrix_client_gomuks_enabled: false | |||
| # renovate: datasource=docker depName=dock.mau.dev/gomuks/gomuks | |||
| matrix_client_gomuks_version: latest | |||
| matrix_client_gomuks_version: v0.2608.0 | |||
| matrix_client_gomuks_container_image: "{{ matrix_client_gomuks_container_image_registry_prefix }}gomuks/gomuks:{{ matrix_client_gomuks_version }}" | |||
| matrix_client_gomuks_container_image_registry_prefix: "{{ matrix_client_gomuks_container_image_registry_prefix_upstream }}" | |||
| @@ -24,7 +25,9 @@ matrix_client_gomuks_container_network: '' | |||
| # A list of additional container networks that the container would be connected to. | |||
| # The role does not create these networks, so make sure they already exist. | |||
| # Use this to expose this container to a reverse proxy, which runs in a different container network. | |||
| matrix_client_gomuks_container_additional_networks: [] | |||
| matrix_client_gomuks_container_additional_networks: "{{ matrix_client_gomuks_container_additional_networks_auto + matrix_client_gomuks_container_additional_networks_custom }}" | |||
| matrix_client_gomuks_container_additional_networks_auto: [] | |||
| matrix_client_gomuks_container_additional_networks_custom: [] | |||
| # The in-container port that gomuks listens on. | |||
| matrix_client_gomuks_container_port: 29325 | |||
| @@ -81,8 +84,11 @@ matrix_client_gomuks_container_labels_additional_labels: '' | |||
| # A list of extra arguments to pass to the container | |||
| matrix_client_gomuks_container_extra_arguments: [] | |||
| # List of systemd services that matrix-client-gomuks.service depends on | |||
| matrix_client_gomuks_systemd_required_services_list: "{{ [devture_systemd_docker_base_docker_service_name] if devture_systemd_docker_base_docker_service_name else [] }}" | |||
| # List of systemd services that matrix-client-gomuks.service depends on. | |||
| matrix_client_gomuks_systemd_required_services_list: "{{ matrix_client_gomuks_systemd_required_services_list_default + matrix_client_gomuks_systemd_required_services_list_auto + matrix_client_gomuks_systemd_required_services_list_custom }}" | |||
| matrix_client_gomuks_systemd_required_services_list_default: "{{ [devture_systemd_docker_base_docker_service_name] if devture_systemd_docker_base_docker_service_name else [] }}" | |||
| matrix_client_gomuks_systemd_required_services_list_auto: [] | |||
| matrix_client_gomuks_systemd_required_services_list_custom: [] | |||
| # Specifies the value of the `X-Frame-Options` header. | |||
| matrix_client_gomuks_http_header_x_frame_options: SAMEORIGIN | |||
| @@ -125,24 +131,24 @@ matrix_client_gomuks_self_check_validate_certificates: true | |||
| # The address the gomuks web server listens on inside the container. | |||
| matrix_client_gomuks_web_listen_address: "0.0.0.0:{{ matrix_client_gomuks_container_port }}" | |||
| # Username for the gomuks web basic auth (NOT your Matrix account). | |||
| # Leave empty to let the playbook generate one from matrix_homeserver_generic_secret_key, | |||
| # or set to your preferred username. | |||
| matrix_client_gomuks_auth_username: "{{ 'gomuks' }}" | |||
| # Username for the gomuks web basic auth (not your Matrix account). | |||
| matrix_client_gomuks_auth_username: gomuks | |||
| # Password for the gomuks web basic auth (NOT your Matrix account). | |||
| # Leave empty to auto-generate from matrix_homeserver_generic_secret_key. | |||
| # Password for the gomuks web basic auth (not your Matrix account). | |||
| # This is the plaintext password the user will enter in the browser. | |||
| # The playbook will derive a bcrypt hash from it for the config file. | |||
| matrix_client_gomuks_auth_password: "{{ (matrix_homeserver_generic_secret_key + ':gomuks.auth_password') | hash('sha512') | truncate(24, True, '') }}" | |||
| # The playbook derives a bcrypt hash from it for the config file. | |||
| matrix_client_gomuks_auth_password: '' | |||
| # Salt used for deterministic bcrypt hashing of the above password. | |||
| # Changing this will change the derived password hash and trigger a restart. | |||
| matrix_client_gomuks_auth_password_salt: "{{ (matrix_homeserver_generic_secret_key + ':gomuks.password_salt') | hash('sha512') | truncate(22, True, '') }}" | |||
| # gomuks requires credentials in its configuration even when its authentication bypass is enabled. | |||
| # Use an inaccessible fallback password in that case so gomuks can start without weakening the fallback behavior. | |||
| matrix_client_gomuks_auth_password_actual: "{{ matrix_client_gomuks_auth_password if not (matrix_client_gomuks_disable_auth | bool) else ((matrix_homeserver_generic_secret_key + ':gomuks.disabled_auth_password') | hash('sha512')) }}" | |||
| # Bcrypt hash of the password. The role computes it from the plaintext password and salt. | |||
| # You can override this directly if you wish to provide your own hash. | |||
| matrix_client_gomuks_auth_password_hash: "{{ matrix_client_gomuks_auth_password | password_hash('bcrypt', matrix_client_gomuks_auth_password_salt) }}" | |||
| matrix_client_gomuks_auth_password_hash: "{{ matrix_client_gomuks_auth_password_actual | password_hash('bcrypt', matrix_client_gomuks_auth_password_salt) }}" | |||
| # Token key used for signing auth tokens. Auto-generated from the generic secret key. | |||
| matrix_client_gomuks_token_key: "{{ (matrix_homeserver_generic_secret_key + ':gomuks.token_key') | hash('sha512') | b64encode | truncate(64, True, '') | regex_replace('[^A-Za-z0-9]', 'A') }}" | |||
| @@ -178,8 +184,15 @@ matrix_client_gomuks_media_thumbnail_size: 120 | |||
| # Push / VAPID configuration. | |||
| matrix_client_gomuks_push_fcm_gateway: "https://push.gomuks.app" | |||
| matrix_client_gomuks_push_vapid_private_key: "{{ (matrix_homeserver_generic_secret_key + ':gomuks.vapid_private') | hash('sha512') | b64encode | truncate(43, True, '') | regex_replace('[^A-Za-z0-9_-]', 'A') }}" | |||
| matrix_client_gomuks_push_vapid_public_key: "{{ (matrix_homeserver_generic_secret_key + ':gomuks.vapid_public') | hash('sha512') | b64encode | truncate(87, True, '') | regex_replace('[^A-Za-z0-9_-]', 'B') }}" | |||
| # Leave both keys empty to let gomuks generate a VAPID key pair on first startup. | |||
| # The role preserves the generated pair on later runs. To supply your own pair, set both variables. | |||
| matrix_client_gomuks_push_vapid_private_key: '' | |||
| matrix_client_gomuks_push_vapid_public_key: '' | |||
| # Internal variables populated by the installation tasks. Do not set these in your configuration. | |||
| matrix_client_gomuks_push_vapid_private_key_actual: '' | |||
| matrix_client_gomuks_push_vapid_public_key_actual: '' | |||
| # Logging configuration. | |||
| matrix_client_gomuks_logging_min_level: info | |||
| @@ -1,4 +1,5 @@ | |||
| # SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| # SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| # SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| # | |||
| # SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -1,4 +1,5 @@ | |||
| # SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| # SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| # SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| # | |||
| # SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -18,5 +19,5 @@ | |||
| - name: Fail if gomuks self-check fails | |||
| ansible.builtin.fail: | |||
| msg: "Failed checking gomuks is up at `{{ matrix_client_gomuks_scheme }}://{{ matrix_client_gomuks_hostname }}{{ matrix_client_gomuks_path_prefix }}` (checked `{{ matrix_client_gomuks_scheme }}://{{ matrix_client_gomuks_hostname }}{{ matrix_client_gomuks_path_prefix | regex_replace('/$', '') }}/`). Is gomuks running? Is the hostname correct? Is Trafiek forwarding correctly? ({{ matrix_client_gomuks_self_check_result.msg }})" | |||
| msg: "Failed checking gomuks is up at `{{ matrix_client_gomuks_scheme }}://{{ matrix_client_gomuks_hostname }}{{ matrix_client_gomuks_path_prefix }}` (checked `{{ matrix_client_gomuks_scheme }}://{{ matrix_client_gomuks_hostname }}{{ matrix_client_gomuks_path_prefix | regex_replace('/$', '') }}/`). Is gomuks running? Is the hostname correct? Is Traefik forwarding correctly? ({{ matrix_client_gomuks_self_check_result.msg }})" | |||
| when: "matrix_client_gomuks_self_check_result.failed | default(false) or matrix_client_gomuks_self_check_result.status not in [200, 302]" | |||
| @@ -1,4 +1,5 @@ | |||
| # SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| # SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| # SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| # | |||
| # SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -19,6 +20,58 @@ | |||
| - {path: "{{ matrix_client_gomuks_data_path }}/data", when: true} | |||
| when: "item.when | bool" | |||
| - name: Initialize existing gomuks configuration | |||
| ansible.builtin.set_fact: | |||
| matrix_client_gomuks_existing_config: {} | |||
| no_log: true | |||
| - name: Check whether the gomuks configuration exists | |||
| ansible.builtin.stat: | |||
| path: "{{ matrix_client_gomuks_data_path }}/config/config.yaml" | |||
| register: matrix_client_gomuks_config_stat | |||
| - name: Read the existing gomuks configuration | |||
| when: matrix_client_gomuks_config_stat.stat.exists | bool | |||
| ansible.builtin.slurp: | |||
| src: "{{ matrix_client_gomuks_data_path }}/config/config.yaml" | |||
| register: matrix_client_gomuks_config_slurp | |||
| no_log: true | |||
| - name: Parse the existing gomuks configuration | |||
| when: matrix_client_gomuks_config_stat.stat.exists | bool | |||
| ansible.builtin.set_fact: | |||
| matrix_client_gomuks_existing_config: "{{ matrix_client_gomuks_config_slurp.content | b64decode | from_yaml }}" | |||
| no_log: true | |||
| - name: Select the gomuks VAPID key pair | |||
| vars: | |||
| matrix_client_gomuks_existing_push_config: "{{ matrix_client_gomuks_existing_config.get('push') or {} }}" | |||
| matrix_client_gomuks_existing_vapid_private_key: "{{ matrix_client_gomuks_existing_push_config.get('vapid_private_key', '') }}" | |||
| matrix_client_gomuks_existing_vapid_public_key: "{{ matrix_client_gomuks_existing_push_config.get('vapid_public_key', '') }}" | |||
| matrix_client_gomuks_existing_vapid_key_pair_valid: >- | |||
| {{ | |||
| matrix_client_gomuks_existing_vapid_private_key is match('^[A-Za-z0-9_-]{43}$') | |||
| and matrix_client_gomuks_existing_vapid_public_key is match('^B[A-Za-z0-9_-]{86}$') | |||
| }} | |||
| ansible.builtin.set_fact: | |||
| matrix_client_gomuks_push_vapid_private_key_actual: >- | |||
| {{ | |||
| matrix_client_gomuks_push_vapid_private_key | |||
| if matrix_client_gomuks_push_vapid_private_key | |||
| else matrix_client_gomuks_existing_vapid_private_key | |||
| if matrix_client_gomuks_existing_vapid_key_pair_valid | |||
| else '' | |||
| }} | |||
| matrix_client_gomuks_push_vapid_public_key_actual: >- | |||
| {{ | |||
| matrix_client_gomuks_push_vapid_public_key | |||
| if matrix_client_gomuks_push_vapid_public_key | |||
| else matrix_client_gomuks_existing_vapid_public_key | |||
| if matrix_client_gomuks_existing_vapid_key_pair_valid | |||
| else '' | |||
| }} | |||
| no_log: true | |||
| - name: Ensure gomuks container image is pulled | |||
| community.docker.docker_image_pull: | |||
| name: "{{ matrix_client_gomuks_container_image }}" | |||
| @@ -41,12 +94,12 @@ | |||
| ansible.builtin.template: | |||
| src: "{{ item.src }}" | |||
| dest: "{{ matrix_client_gomuks_data_path }}/{{ item.name }}" | |||
| mode: '0644' | |||
| mode: "{{ item.mode }}" | |||
| owner: "{{ matrix_user_name }}" | |||
| group: "{{ matrix_group_name }}" | |||
| with_items: | |||
| - {src: "{{ role_path }}/templates/labels.j2", name: "labels"} | |||
| - {src: "{{ role_path }}/templates/env.j2", name: "env"} | |||
| - {src: "{{ role_path }}/templates/labels.j2", name: "labels", mode: "0644"} | |||
| - {src: "{{ role_path }}/templates/env.j2", name: "env", mode: "0640"} | |||
| register: matrix_client_gomuks_support_files_result | |||
| - name: Ensure gomuks container network is created | |||
| @@ -1,4 +1,5 @@ | |||
| # SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| # SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| # SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| # | |||
| # SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -23,8 +24,3 @@ | |||
| ansible.builtin.file: | |||
| path: "{{ devture_systemd_docker_base_systemd_path }}/matrix-client-gomuks.service" | |||
| state: absent | |||
| - name: Ensure gomuks path doesn't exist | |||
| ansible.builtin.file: | |||
| path: "{{ matrix_client_gomuks_data_path }}" | |||
| state: absent | |||
| @@ -1,4 +1,5 @@ | |||
| # SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| # SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| # SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| # | |||
| # SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -14,10 +15,29 @@ | |||
| - {'name': 'matrix_client_gomuks_hostname', when: true} | |||
| - {'name': 'matrix_client_gomuks_path_prefix', when: true} | |||
| - {'name': 'matrix_client_gomuks_container_network', when: true} | |||
| - {'name': 'matrix_client_gomuks_auth_username', when: "{{ not matrix_client_gomuks_disable_auth | bool }}"} | |||
| - {'name': 'matrix_client_gomuks_auth_username', when: true} | |||
| - {'name': 'matrix_client_gomuks_auth_password', when: "{{ not matrix_client_gomuks_disable_auth | bool }}"} | |||
| - {'name': 'matrix_client_gomuks_token_key', when: true} | |||
| - name: Fail if only one gomuks VAPID key is supplied | |||
| ansible.builtin.fail: | |||
| msg: >- | |||
| `matrix_client_gomuks_push_vapid_private_key` and `matrix_client_gomuks_push_vapid_public_key` must either both be set or both be empty. | |||
| when: (matrix_client_gomuks_push_vapid_private_key | length == 0) != (matrix_client_gomuks_push_vapid_public_key | length == 0) | |||
| - name: Fail if the supplied gomuks VAPID keys have invalid encodings | |||
| ansible.builtin.fail: | |||
| msg: >- | |||
| The supplied gomuks VAPID keys are not raw URL-safe base64-encoded P-256 keys. | |||
| The private key must contain 43 characters and the uncompressed public key must contain 87 characters and start with `B`. | |||
| when: | |||
| - matrix_client_gomuks_push_vapid_private_key | length > 0 | |||
| - >- | |||
| not ( | |||
| matrix_client_gomuks_push_vapid_private_key is match('^[A-Za-z0-9_-]{43}$') | |||
| and matrix_client_gomuks_push_vapid_public_key is match('^B[A-Za-z0-9_-]{86}$') | |||
| ) | |||
| - when: matrix_client_gomuks_container_labels_traefik_enabled | bool | |||
| block: | |||
| - name: Fail if required gomuks Traefik settings not defined | |||
| @@ -1,15 +1,14 @@ | |||
| {# | |||
| SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| SPDX-License-Identifier: AGPL-3.0-or-later | |||
| #} | |||
| web: | |||
| listen_address: {{ matrix_client_gomuks_web_listen_address | to_json }} | |||
| {% if not matrix_client_gomuks_disable_auth | bool %} | |||
| username: {{ matrix_client_gomuks_auth_username | to_json }} | |||
| password_hash: {{ matrix_client_gomuks_auth_password_hash | to_json }} | |||
| {% endif %} | |||
| token_key: {{ matrix_client_gomuks_token_key | to_json }} | |||
| debug_endpoints: {{ matrix_client_gomuks_debug_endpoints | to_json }} | |||
| event_buffer_size: {{ matrix_client_gomuks_event_buffer_size | to_json }} | |||
| @@ -26,8 +25,10 @@ matrix: | |||
| set_presence: {{ matrix_client_gomuks_matrix_set_presence | to_json }} | |||
| push: | |||
| fcm_gateway: {{ matrix_client_gomuks_push_fcm_gateway | to_json }} | |||
| vapid_private_key: {{ matrix_client_gomuks_push_vapid_private_key | to_json }} | |||
| vapid_public_key: {{ matrix_client_gomuks_push_vapid_public_key | to_json }} | |||
| {% if matrix_client_gomuks_push_vapid_private_key_actual %} | |||
| vapid_private_key: {{ matrix_client_gomuks_push_vapid_private_key_actual | to_json }} | |||
| vapid_public_key: {{ matrix_client_gomuks_push_vapid_public_key_actual | to_json }} | |||
| {% endif %} | |||
| media: | |||
| thumbnail_size: {{ matrix_client_gomuks_media_thumbnail_size | to_json }} | |||
| logging: | |||
| @@ -1,5 +1,6 @@ | |||
| {# | |||
| SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| SPDX-License-Identifier: AGPL-3.0-or-later | |||
| #} | |||
| @@ -1,5 +1,6 @@ | |||
| {# | |||
| SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| SPDX-License-Identifier: AGPL-3.0-or-later | |||
| #} | |||
| @@ -1,6 +1,7 @@ | |||
| #jinja2: lstrip_blocks: True | |||
| {# | |||
| SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||
| SPDX-FileCopyrightText: 2026 Matěj Cepl | |||
| SPDX-FileCopyrightText: 2026 MDAD project contributors | |||
| SPDX-License-Identifier: AGPL-3.0-or-later | |||
| @@ -33,7 +34,7 @@ ExecStartPre={{ devture_systemd_docker_base_host_command_docker }} create \ | |||
| --label-file={{ matrix_client_gomuks_data_path }}/labels \ | |||
| --env-file={{ matrix_client_gomuks_data_path }}/env \ | |||
| --tmpfs=/tmp:rw,noexec,nosuid,size=100m \ | |||
| --mount type=bind,src={{ matrix_client_gomuks_data_path }},dst=/data,rw \ | |||
| --mount type=bind,src={{ matrix_client_gomuks_data_path }},dst=/data \ | |||
| {% for arg in matrix_client_gomuks_container_extra_arguments %} | |||
| {{ arg }} \ | |||
| {% endfor %} | |||