Unlike the other mautrix bridges, the mautrix-slack role had no Traefik label infrastructure at all, so this builds the scaffold first (a new labels.j2, the container_labels_traefik_* vars, the label-file wiring in the systemd service and setup_install.yml, and the group_vars wiring), then exposes the bridge's appservice HTTP API under https://matrix.<domain>/bridges/slack like the other bridges. The provisioning shared secret was already auto-generated. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>pull/4317/merge
| @@ -1659,9 +1659,16 @@ matrix_mautrix_slack_container_additional_networks_auto: |- | |||||
| ([] if matrix_addons_homeserver_container_network == '' else [matrix_addons_homeserver_container_network]) | ([] if matrix_addons_homeserver_container_network == '' else [matrix_addons_homeserver_container_network]) | ||||
| + | + | ||||
| ([postgres_container_network] if (postgres_enabled and matrix_mautrix_slack_database_hostname == postgres_connection_hostname and matrix_mautrix_slack_container_network != postgres_container_network) else []) | ([postgres_container_network] if (postgres_enabled and matrix_mautrix_slack_database_hostname == postgres_connection_hostname and matrix_mautrix_slack_container_network != postgres_container_network) else []) | ||||
| + | |||||
| ([matrix_playbook_reverse_proxyable_services_additional_network] if matrix_playbook_reverse_proxyable_services_additional_network and matrix_mautrix_slack_container_labels_traefik_enabled else []) | |||||
| ) | unique | ) | unique | ||||
| }} | }} | ||||
| matrix_mautrix_slack_container_labels_traefik_enabled: "{{ matrix_playbook_reverse_proxy_type in ['playbook-managed-traefik', 'other-traefik-container'] }}" | |||||
| matrix_mautrix_slack_container_labels_traefik_docker_network: "{{ matrix_playbook_reverse_proxyable_services_additional_network }}" | |||||
| matrix_mautrix_slack_container_labels_traefik_entrypoints: "{{ traefik_entrypoint_primary }}" | |||||
| matrix_mautrix_slack_container_labels_traefik_tls_certResolver: "{{ traefik_certResolver_primary }}" | |||||
| matrix_mautrix_slack_appservice_token: "{{ (matrix_homeserver_generic_secret_key + ':mauslack.as.tok') | hash('sha512') | to_uuid }}" | matrix_mautrix_slack_appservice_token: "{{ (matrix_homeserver_generic_secret_key + ':mauslack.as.tok') | hash('sha512') | to_uuid }}" | ||||
| matrix_mautrix_slack_homeserver_address: "{{ matrix_addons_homeserver_client_api_url }}" | matrix_mautrix_slack_homeserver_address: "{{ matrix_addons_homeserver_client_api_url }}" | ||||
| @@ -1686,6 +1693,11 @@ matrix_mautrix_slack_database_password: "{{ (matrix_homeserver_generic_secret_ke | |||||
| matrix_mautrix_slack_provisioning_shared_secret: "{{ (matrix_homeserver_generic_secret_key + ':mau.slack.prov') | hash('sha512') | to_uuid }}" | matrix_mautrix_slack_provisioning_shared_secret: "{{ (matrix_homeserver_generic_secret_key + ':mau.slack.prov') | hash('sha512') | to_uuid }}" | ||||
| matrix_mautrix_slack_public_media_signing_key: "{{ (matrix_homeserver_generic_secret_key + ':mau.slack.pmed') | hash('sha512') | to_uuid }}" | matrix_mautrix_slack_public_media_signing_key: "{{ (matrix_homeserver_generic_secret_key + ':mau.slack.pmed') | hash('sha512') | to_uuid }}" | ||||
| matrix_mautrix_slack_scheme: "{{ 'https' if matrix_playbook_ssl_enabled else 'http' }}" | |||||
| matrix_mautrix_slack_exposure_enabled: "{{ matrix_bridges_exposure_enabled }}" | |||||
| matrix_mautrix_slack_exposure_hostname: "{{ matrix_bridges_exposure_hostname }}" | |||||
| matrix_mautrix_slack_exposure_path_prefix: "{{ matrix_bridges_exposure_path_prefix }}/slack" | |||||
| ###################################################################### | ###################################################################### | ||||
| # | # | ||||
| # /matrix-bridge-mautrix-slack | # /matrix-bridge-mautrix-slack | ||||
| @@ -36,6 +36,13 @@ matrix_mautrix_slack_homeserver_domain: "{{ matrix_domain }}" | |||||
| matrix_mautrix_slack_homeserver_async_media: false | matrix_mautrix_slack_homeserver_async_media: false | ||||
| matrix_mautrix_slack_appservice_address: "http://matrix-mautrix-slack:8080" | matrix_mautrix_slack_appservice_address: "http://matrix-mautrix-slack:8080" | ||||
| # Scheme of the bridge's public address (see `matrix_mautrix_slack_bridge_public_address`). | |||||
| matrix_mautrix_slack_scheme: https | |||||
| # The public base URL at which this bridge's HTTP API is reachable from outside (when exposed). | |||||
| # Used for the provisioning API's external-server (OpenID) flow and for public media links. | |||||
| matrix_mautrix_slack_bridge_public_address: "{{ (matrix_mautrix_slack_scheme + '://' + matrix_mautrix_slack_exposure_hostname + matrix_mautrix_slack_exposure_path_prefix) if matrix_mautrix_slack_exposure_enabled else '' }}" | |||||
| matrix_mautrix_slack_msc4190_enabled: "{{ matrix_bridges_msc4190_enabled }}" | matrix_mautrix_slack_msc4190_enabled: "{{ matrix_bridges_msc4190_enabled }}" | ||||
| matrix_mautrix_slack_self_sign_enabled: "{{ matrix_bridges_self_sign_enabled }}" | matrix_mautrix_slack_self_sign_enabled: "{{ matrix_bridges_self_sign_enabled }}" | ||||
| @@ -74,6 +81,33 @@ matrix_mautrix_slack_container_additional_networks: "{{ matrix_mautrix_slack_con | |||||
| matrix_mautrix_slack_container_additional_networks_auto: [] | matrix_mautrix_slack_container_additional_networks_auto: [] | ||||
| matrix_mautrix_slack_container_additional_networks_custom: [] | matrix_mautrix_slack_container_additional_networks_custom: [] | ||||
| # matrix_mautrix_slack_container_labels_traefik_enabled controls whether labels to assist a Traefik reverse-proxy will be attached to the container. | |||||
| # See `../templates/labels.j2` for details. | |||||
| # | |||||
| # To inject your own other container labels, see `matrix_mautrix_slack_container_labels_additional_labels`. | |||||
| matrix_mautrix_slack_container_labels_traefik_enabled: true | |||||
| matrix_mautrix_slack_container_labels_traefik_docker_network: "{{ matrix_mautrix_slack_container_network }}" | |||||
| matrix_mautrix_slack_container_labels_traefik_entrypoints: web-secure | |||||
| matrix_mautrix_slack_container_labels_traefik_tls_certResolver: default # noqa var-naming | |||||
| # Controls whether labels will be added that expose mautrix-slack's HTTP API | |||||
| # (used by tools like mautrix-manager for bridge login) at `https://<hostname><path_prefix>`. | |||||
| matrix_mautrix_slack_container_labels_exposure_enabled: "{{ matrix_mautrix_slack_exposure_enabled }}" | |||||
| matrix_mautrix_slack_container_labels_exposure_traefik_rule: "Host(`{{ matrix_mautrix_slack_exposure_hostname }}`) && PathPrefix(`{{ matrix_mautrix_slack_exposure_path_prefix }}`)" | |||||
| matrix_mautrix_slack_container_labels_exposure_traefik_priority: 0 | |||||
| matrix_mautrix_slack_container_labels_exposure_traefik_entrypoints: "{{ matrix_mautrix_slack_container_labels_traefik_entrypoints }}" | |||||
| matrix_mautrix_slack_container_labels_exposure_traefik_tls: "{{ matrix_mautrix_slack_container_labels_exposure_traefik_entrypoints != 'web' }}" | |||||
| matrix_mautrix_slack_container_labels_exposure_traefik_tls_certResolver: "{{ matrix_mautrix_slack_container_labels_traefik_tls_certResolver }}" # noqa var-naming | |||||
| # matrix_mautrix_slack_container_labels_additional_labels contains a multiline string with additional labels to add to the container label file. | |||||
| # See `../templates/labels.j2` for details. | |||||
| # | |||||
| # Example: | |||||
| # matrix_mautrix_slack_container_labels_additional_labels: | | |||||
| # my.label=1 | |||||
| # another.label="here" | |||||
| matrix_mautrix_slack_container_labels_additional_labels: '' | |||||
| # A list of extra arguments to pass to the container | # A list of extra arguments to pass to the container | ||||
| matrix_mautrix_slack_container_extra_arguments: [] | matrix_mautrix_slack_container_extra_arguments: [] | ||||
| @@ -189,6 +223,11 @@ matrix_mautrix_slack_bridge_encryption_pickle_key: maunium.net/go/mautrix-whatsa | |||||
| matrix_mautrix_slack_provisioning_shared_secret: '' | matrix_mautrix_slack_provisioning_shared_secret: '' | ||||
| matrix_mautrix_slack_public_media_signing_key: '' | matrix_mautrix_slack_public_media_signing_key: '' | ||||
| # Controls whether mautrix-slack's HTTP API is exposed publicly (used by tools like mautrix-manager for bridge login). | |||||
| matrix_mautrix_slack_exposure_enabled: false | |||||
| matrix_mautrix_slack_exposure_hostname: '' | |||||
| matrix_mautrix_slack_exposure_path_prefix: '' | |||||
| # Controls whether relay mode is enabled | # Controls whether relay mode is enabled | ||||
| matrix_mautrix_slack_bridge_relay_enabled: "{{ matrix_bridges_relay_enabled }}" | matrix_mautrix_slack_bridge_relay_enabled: "{{ matrix_bridges_relay_enabled }}" | ||||
| @@ -97,6 +97,17 @@ | |||||
| group: "{{ matrix_group_name }}" | group: "{{ matrix_group_name }}" | ||||
| register: matrix_mautrix_slack_registration_result | register: matrix_mautrix_slack_registration_result | ||||
| - name: Ensure mautrix-slack support files installed | |||||
| ansible.builtin.template: | |||||
| src: "{{ role_path }}/templates/{{ item }}.j2" | |||||
| dest: "{{ matrix_mautrix_slack_base_path }}/{{ item }}" | |||||
| mode: '0640' | |||||
| owner: "{{ matrix_user_name }}" | |||||
| group: "{{ matrix_group_name }}" | |||||
| with_items: | |||||
| - labels | |||||
| register: matrix_mautrix_slack_support_files_result | |||||
| - name: Ensure matrix-mautrix-slack container network is created | - name: Ensure matrix-mautrix-slack container network is created | ||||
| when: matrix_mautrix_slack_container_network != 'host' | when: matrix_mautrix_slack_container_network != 'host' | ||||
| community.general.docker_network: | community.general.docker_network: | ||||
| @@ -119,6 +130,7 @@ | |||||
| matrix_mautrix_slack_migration_requires_restart | default(false) | matrix_mautrix_slack_migration_requires_restart | default(false) | ||||
| or matrix_mautrix_slack_config_result.changed | default(false) | or matrix_mautrix_slack_config_result.changed | default(false) | ||||
| or matrix_mautrix_slack_registration_result.changed | default(false) | or matrix_mautrix_slack_registration_result.changed | default(false) | ||||
| or matrix_mautrix_slack_support_files_result.changed | default(false) | |||||
| or matrix_mautrix_slack_systemd_service_result.changed | default(false) | or matrix_mautrix_slack_systemd_service_result.changed | default(false) | ||||
| or matrix_mautrix_slack_container_image_pull_result.changed | default(false) | or matrix_mautrix_slack_container_image_pull_result.changed | default(false) | ||||
| or matrix_mautrix_slack_container_image_build_result.changed | default(false) | or matrix_mautrix_slack_container_image_build_result.changed | default(false) | ||||
| @@ -213,7 +213,7 @@ appservice: | |||||
| address: {{ matrix_mautrix_slack_appservice_address | to_json }} | address: {{ matrix_mautrix_slack_appservice_address | to_json }} | ||||
| # A public address that external services can use to reach this appservice. | # A public address that external services can use to reach this appservice. | ||||
| # This value doesn't affect the registration file. | # This value doesn't affect the registration file. | ||||
| public_address: https://bridge.example.com | |||||
| public_address: {{ matrix_mautrix_slack_bridge_public_address | to_json }} | |||||
| # The hostname and port where this appservice should listen. | # The hostname and port where this appservice should listen. | ||||
| # For Docker, you generally have to change the hostname to 0.0.0.0. | # For Docker, you generally have to change the hostname to 0.0.0.0. | ||||
| @@ -0,0 +1,50 @@ | |||||
| {# | |||||
| SPDX-FileCopyrightText: 2026 Slavi Pantaleev | |||||
| SPDX-License-Identifier: AGPL-3.0-or-later | |||||
| #} | |||||
| {% if matrix_mautrix_slack_container_labels_traefik_enabled %} | |||||
| traefik.enable=true | |||||
| {% if matrix_mautrix_slack_container_labels_traefik_docker_network %} | |||||
| traefik.docker.network={{ matrix_mautrix_slack_container_labels_traefik_docker_network }} | |||||
| {% endif %} | |||||
| {% if matrix_mautrix_slack_container_labels_exposure_enabled %} | |||||
| ############################################################ | |||||
| # # | |||||
| # Bridge API exposure # | |||||
| # # | |||||
| ############################################################ | |||||
| traefik.http.services.matrix-mautrix-slack-exposure.loadbalancer.server.port=8080 | |||||
| traefik.http.middlewares.matrix-mautrix-slack-exposure-strip-prefix.stripprefix.prefixes={{ matrix_mautrix_slack_exposure_path_prefix }} | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.middlewares=matrix-mautrix-slack-exposure-strip-prefix | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.rule={{ matrix_mautrix_slack_container_labels_exposure_traefik_rule }} | |||||
| {% if matrix_mautrix_slack_container_labels_exposure_traefik_priority | int > 0 %} | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.priority={{ matrix_mautrix_slack_container_labels_exposure_traefik_priority }} | |||||
| {% endif %} | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.service=matrix-mautrix-slack-exposure | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.entrypoints={{ matrix_mautrix_slack_container_labels_exposure_traefik_entrypoints }} | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.tls={{ matrix_mautrix_slack_container_labels_exposure_traefik_tls | to_json }} | |||||
| {% if matrix_mautrix_slack_container_labels_exposure_traefik_tls %} | |||||
| traefik.http.routers.matrix-mautrix-slack-exposure.tls.certResolver={{ matrix_mautrix_slack_container_labels_exposure_traefik_tls_certResolver }} | |||||
| {% endif %} | |||||
| ############################################################ | |||||
| # # | |||||
| # /Bridge API exposure # | |||||
| # # | |||||
| ############################################################ | |||||
| {% endif %} | |||||
| {% endif %} | |||||
| {{ matrix_mautrix_slack_container_labels_additional_labels }} | |||||
| @@ -25,6 +25,7 @@ ExecStartPre={{ devture_systemd_docker_base_host_command_docker }} create \ | |||||
| --network={{ matrix_mautrix_slack_container_network }} \ | --network={{ matrix_mautrix_slack_container_network }} \ | ||||
| --mount type=bind,src={{ matrix_mautrix_slack_config_path }},dst=/config,ro \ | --mount type=bind,src={{ matrix_mautrix_slack_config_path }},dst=/config,ro \ | ||||
| --mount type=bind,src={{ matrix_mautrix_slack_data_path }},dst=/data \ | --mount type=bind,src={{ matrix_mautrix_slack_data_path }},dst=/data \ | ||||
| --label-file={{ matrix_mautrix_slack_base_path }}/labels \ | |||||
| --workdir=/data \ | --workdir=/data \ | ||||
| {% for arg in matrix_mautrix_slack_container_extra_arguments %} | {% for arg in matrix_mautrix_slack_container_extra_arguments %} | ||||
| {{ arg }} \ | {{ arg }} \ | ||||