Explorar el Código

Merge 641b9e989d into 20399b4827

pull/5462/merge
Coo van Leeuwen hace 23 horas
committed by GitHub
padre
commit
76966f0655
No se encontró ninguna clave conocida en la base de datos para esta firma ID de clave GPG: B5690EEEBB952194
Se han modificado 18 ficheros con 1200 adiciones y 0 borrados
  1. +9
    -0
      CHANGELOG.md
  2. +1
    -0
      README.md
  3. +97
    -0
      docs/configuring-playbook-bridge-beeper-line.md
  4. +2
    -0
      docs/configuring-playbook.md
  5. +1
    -0
      docs/container-images.md
  6. +1
    -0
      docs/self-building.md
  7. +96
    -0
      group_vars/matrix_servers
  8. +225
    -0
      roles/custom/matrix-bridge-beeper-line/defaults/main.yml
  9. +25
    -0
      roles/custom/matrix-bridge-beeper-line/tasks/main.yml
  10. +143
    -0
      roles/custom/matrix-bridge-beeper-line/tasks/setup_install.yml
  11. +25
    -0
      roles/custom/matrix-bridge-beeper-line/tasks/setup_uninstall.yml
  12. +26
    -0
      roles/custom/matrix-bridge-beeper-line/tasks/validate_config.yml
  13. +440
    -0
      roles/custom/matrix-bridge-beeper-line/templates/config.yaml.j2
  14. +4
    -0
      roles/custom/matrix-bridge-beeper-line/templates/config.yaml.j2.license
  15. +49
    -0
      roles/custom/matrix-bridge-beeper-line/templates/labels.j2
  16. +51
    -0
      roles/custom/matrix-bridge-beeper-line/templates/systemd/matrix-beeper-line.service.j2
  17. +4
    -0
      roles/custom/matrix-bridge-beeper-line/templates/systemd/matrix-beeper-line.service.j2.license
  18. +1
    -0
      setup.yml

+ 9
- 0
CHANGELOG.md Ver fichero

@@ -1,3 +1,12 @@
# 2026-07-23

## Support for bridging to LINE via beeper-line

The playbook can now bridge [LINE](https://line.me/) via [beeper-line](https://github.com/beeper/line), a bridge based on the modern mautrix bridge framework. It supports LINE accounts with Letter Sealing enabled or disabled and bridges messages, media, reactions, replies, receipts, and other common chat features.

The bridge identifies itself as a LINE Chrome Extension client, so it cannot be used at the same time as the real LINE Chrome Extension. See [Setting up Beeper LINE bridging](docs/configuring-playbook-bridge-beeper-line.md) to get started.


# 2026-07-19

## Tuwunel now exposes its administration and /_tuwunel API paths


+ 1
- 0
README.md Ver fichero

@@ -126,6 +126,7 @@ Bridges can be used to connect your Matrix installation with third-party communi
| [mautrix-meta](https://github.com/mautrix/meta) | ❌ | Bridge to [Messenger](https://messenger.com/) and [Instagram](https://instagram.com/) | Link for [Messenger](docs/configuring-playbook-bridge-mautrix-meta-messenger.md) / [Instagram](docs/configuring-playbook-bridge-mautrix-meta-instagram.md) |
| [mautrix-signal](https://github.com/mautrix/signal) | ❌ | Bridge to [Signal](https://www.signal.org/) | [Link](docs/configuring-playbook-bridge-mautrix-signal.md) |
| [beeper-linkedin](https://github.com/beeper/linkedin) | ❌ | Bridge to [LinkedIn](https://www.linkedin.com/) | [Link](docs/configuring-playbook-bridge-beeper-linkedin.md) |
| [beeper-line](https://github.com/beeper/line) | ❌ | Bridge to [LINE](https://line.me/) | [Link](docs/configuring-playbook-bridge-beeper-line.md) |
| [matrix-appservice-irc](https://github.com/matrix-org/matrix-appservice-irc) | ❌ | Bridge to [IRC](https://wikipedia.org/wiki/Internet_Relay_Chat) | [Link](docs/configuring-playbook-bridge-appservice-irc.md) |
| [matrix-appservice-discord](https://github.com/matrix-org/matrix-appservice-discord) | ❌ | Bridge to [Discord](https://discordapp.com/) | [Link](docs/configuring-playbook-bridge-appservice-discord.md) |
| [matrix-hookshot](https://github.com/matrix-org/matrix-hookshot) | ❌ | Bridge for generic webhooks and multiple project management services, such as GitHub, GitLab, Figma, and Jira in particular | [Link](docs/configuring-playbook-bridge-hookshot.md) |


+ 97
- 0
docs/configuring-playbook-bridge-beeper-line.md Ver fichero

@@ -0,0 +1,97 @@
<!--
SPDX-FileCopyrightText: 2026 MDAD project contributors

SPDX-License-Identifier: AGPL-3.0-or-later
-->

# Setting up Beeper LINE bridging (optional)

<sup>Refer to the common guide for configuring mautrix bridges: [Setting up a Generic Mautrix Bridge](configuring-playbook-bridge-mautrix-bridges.md)</sup>

The playbook can install and configure [beeper-line](https://github.com/beeper/line) for you, for bridging to [LINE](https://line.me/).

See the project's [documentation](https://github.com/beeper/line/blob/main/README.md) to learn what it does and which features it supports.

## Prerequisites

### Prepare your LINE account

The bridge logs in with the email address configured in your LINE account. If your account does not have an email address, set one in the LINE mobile app under **Settings** → **Account** → **Email address** before trying to log in.

The bridge identifies itself to LINE as a Chrome Extension client. LINE only permits one active Chrome Extension session, so the bridge and the real LINE Chrome Extension cannot be used at the same time. Logging in with either one invalidates the other session.

### Enable Appservice Double Puppet (optional)

If you want to set up [Double Puppeting](https://docs.mau.fi/bridges/general/double-puppeting.html) for this bridge automatically, you need to have enabled [Appservice Double Puppet](configuring-playbook-appservice-double-puppet.md) for this playbook.

See [this section](configuring-playbook-bridge-mautrix-bridges.md#set-up-double-puppeting-optional) on the common mautrix bridge guide for details.

## Adjusting the playbook configuration

To enable the bridge, add the following configuration to your `inventory/host_vars/matrix.example.com/vars.yml` file:

```yaml
matrix_bridge_beeper_line_enabled: true
```

### Using another container image

The playbook uses `docker.io/crispyduck/beeper-line` by default. To use an image that you have built and published elsewhere, override the complete image name:

```yaml
matrix_bridge_beeper_line_container_image_self_build: false
matrix_bridge_beeper_line_container_image: docker.io/example/beeper-line:latest
```

The role can also build the bridge directly from a Git repository on the Matrix server:

```yaml
matrix_bridge_beeper_line_container_image_self_build: true
matrix_bridge_beeper_line_container_image_self_build_repo: https://github.com/beeper/line.git
matrix_bridge_beeper_line_container_image_self_build_branch: main
```

Self-building requires more time and resources on the server than pulling a prebuilt image.

### Extending the configuration

There are additional things you may wish to configure about the bridge.

See [this section](configuring-playbook-bridge-mautrix-bridges.md#extending-the-configuration) on the common mautrix bridge guide for details about variables that you can customize and the bridge's default configuration, including [bridge permissions](configuring-playbook-bridge-mautrix-bridges.md#configure-bridge-permissions-optional), [encryption support](configuring-playbook-bridge-mautrix-bridges.md#enable-encryption-optional), [relay mode](configuring-playbook-bridge-mautrix-bridges.md#enable-relay-mode-optional), and the [bot's username](configuring-playbook-bridge-mautrix-bridges.md#set-the-bots-username-optional).

When following the common guide, replace `_mautrix_SERVICENAME_` in variable names with `_beeper_line_`.

## Installing

After configuring the playbook, run it with [playbook tags](playbook-tags.md) as below:

```sh
ansible-playbook -i inventory/hosts setup.yml --tags=setup-all,start
```

The shortcut commands with the [`just` program](just.md) are also available: `just install-all` or `just setup-all`.

`just install-all` is useful for maintaining your setup quickly when its components remain unchanged. If you adjust your `vars.yml` to remove other components, run `just setup-all` so those components are uninstalled.

## Usage

To use the bridge, start a chat with `@linebot:example.com` (where `example.com` is your base domain, not the `matrix.` domain).

Send `login` and follow the prompts to enter your LINE email address and password and approve the new session in the LINE mobile app.

## Troubleshooting

As with all other services, you can find the logs in systemd-journald by logging in to the server with SSH and running:

```sh
journalctl -fu matrix-beeper-line
```

### Increase logging verbosity

The default logging level for this component is `warn`. To increase the verbosity, add the following configuration to your `vars.yml` file and re-run the playbook:

```yaml
# Valid values: fatal, error, warn, info, debug, trace
matrix_bridge_beeper_line_logging_level: debug
```

+ 2
- 0
docs/configuring-playbook.md Ver fichero

@@ -170,6 +170,8 @@ Bridges can be used to connect your Matrix installation with third-party communi

- [Setting up Beeper LinkedIn bridging](configuring-playbook-bridge-beeper-linkedin.md)

- [Setting up Beeper LINE bridging](configuring-playbook-bridge-beeper-line.md)

- [Setting up matrix-hookshot](configuring-playbook-bridge-hookshot.md) — a bridge between Matrix and multiple project management services, such as [GitHub](https://github.com), [GitLab](https://about.gitlab.com) and [JIRA](https://www.atlassian.com/software/jira).

- [Setting up MX Puppet GroupMe bridging](configuring-playbook-bridge-mx-puppet-groupme.md)


+ 1
- 0
docs/container-images.md Ver fichero

@@ -99,6 +99,7 @@ Bridges can be used to connect your Matrix installation with third-party communi
| mautrix-meta (for [Messenger](configuring-playbook-bridge-mautrix-meta-messenger.md) and [Instagram](configuring-playbook-bridge-mautrix-meta-instagram.md)) | [mautrix/meta](https://mau.dev/mautrix/meta/container_registry) | ❌ | Bridge to [Messenger](https://messenger.com/) and [Instagram](https://instagram.com/) |
| [mautrix-signal](configuring-playbook-bridge-mautrix-signal.md) | [mautrix/signal](https://mau.dev/mautrix/signal/container_registry) | ❌ | Bridge to [Signal](https://www.signal.org/) |
| [beeper-linkedin](configuring-playbook-bridge-beeper-linkedin.md) | [beeper/linkedin](https://ghcr.io/beeper/linkedin) | ❌ | Bridge to [LinkedIn](https://www.linkedin.com/) |
| [beeper-line](configuring-playbook-bridge-beeper-line.md) | [crispyduck/beeper-line](https://hub.docker.com/r/crispyduck/beeper-line) | ❌ | Bridge to [LINE](https://line.me/) |
| [matrix-appservice-irc](configuring-playbook-bridge-appservice-irc.md) | [matrixdotorg/matrix-appservice-irc](https://hub.docker.com/r/matrixdotorg/matrix-appservice-irc) | ❌ | Bridge to [IRC](https://wikipedia.org/wiki/Internet_Relay_Chat) |
| [matrix-appservice-discord](configuring-playbook-bridge-appservice-discord.md) | [matrix-org/matrix-appservice-discord](https://ghcr.io/matrix-org/matrix-appservice-discord) | ❌ | Bridge to [Discord](https://discordapp.com/) |
| [matrix-hookshot](configuring-playbook-bridge-hookshot.md) | [halfshot/matrix-hookshot](https://hub.docker.com/r/halfshot/matrix-hookshot) | ❌ | Bridge for generic webhooks and multiple project management services, such as GitHub, GitLab, Figma, and Jira in particular |


+ 1
- 0
docs/self-building.md Ver fichero

@@ -37,6 +37,7 @@ Possibly outdated list of roles where self-building the Docker image is currentl
- `matrix-bridge-hookshot`
- `matrix-bridge-appservice-irc`
- `matrix-bridge-beeper-linkedin`
- `matrix-bridge-beeper-line`
- `matrix-bridge-mautrix-googlechat`
- `matrix-bridge-mautrix-telegram`
- `matrix-bridge-mautrix-signal`


+ 96
- 0
group_vars/matrix_servers Ver fichero

@@ -104,6 +104,8 @@ matrix_homeserver_container_extra_arguments_auto: |
+
(['--mount type=bind,src=' + matrix_bridge_beeper_linkedin_config_path + '/registration.yaml,dst=/matrix-beeper-linkedin-registration.yaml,ro'] if matrix_bridge_beeper_linkedin_enabled else [])
+
(['--mount type=bind,src=' + matrix_bridge_beeper_line_config_path + '/registration.yaml,dst=/matrix-beeper-line-registration.yaml,ro'] if matrix_bridge_beeper_line_enabled else [])
+
(['--mount type=bind,src=' + matrix_bridge_wechat_config_path + '/registration.yaml,dst=/matrix-wechat-registration.yaml,ro'] if matrix_bridge_wechat_enabled else [])
+
(['--mount type=bind,src=' + matrix_bridge_heisenbridge_base_path + '/registration.yaml,dst=/heisenbridge-registration.yaml,ro'] if matrix_bridge_heisenbridge_enabled else [])
@@ -163,6 +165,8 @@ matrix_homeserver_app_service_config_files_auto: |
+
(['/matrix-beeper-linkedin-registration.yaml'] if matrix_bridge_beeper_linkedin_enabled else [])
+
(['/matrix-beeper-line-registration.yaml'] if matrix_bridge_beeper_line_enabled else [])
+
(['/matrix-wechat-registration.yaml'] if matrix_bridge_wechat_enabled else [])
+
(['/heisenbridge-registration.yaml'] if matrix_bridge_heisenbridge_enabled else [])
@@ -377,6 +381,13 @@ devture_systemd_service_manager_services_list_auto: |
'groups': ['matrix', 'bridges', 'beeper-linkedin'],
}] if matrix_bridge_beeper_linkedin_enabled else [])
+
([{
'name': 'matrix-beeper-line.service',
'priority': 2000,
'restart_necessary': (matrix_bridge_beeper_line_restart_necessary | bool),
'groups': ['matrix', 'bridges', 'beeper-line'],
}] if matrix_bridge_beeper_line_enabled else [])
+
([{
'name': 'matrix-wechat.service',
'priority': 2000,
@@ -1342,6 +1353,79 @@ matrix_bridge_beeper_linkedin_database_password: "{{ (matrix_homeserver_generic_
#
######################################################################


######################################################################
#
# matrix-bridge-beeper-line
#
######################################################################

# We don't enable bridges by default.
matrix_bridge_beeper_line_enabled: false

matrix_bridge_beeper_line_systemd_required_services_list_auto: |
{{
matrix_addons_homeserver_systemd_services_list
+
([postgres_identifier ~ '.service'] if (postgres_enabled and matrix_bridge_beeper_line_database_hostname == postgres_connection_hostname) else [])
}}

matrix_bridge_beeper_line_container_image_registry_prefix_upstream: "{{ matrix_container_global_registry_prefix_override if matrix_container_global_registry_prefix_override else matrix_bridge_beeper_line_container_image_registry_prefix_upstream_default }}"

matrix_bridge_beeper_line_container_image_self_build: "{{ matrix_architecture not in ['amd64'] }}"

matrix_bridge_beeper_line_container_network: "{{ matrix_addons_container_network }}"

matrix_bridge_beeper_line_container_additional_networks_auto: |-
{{
(
([] if matrix_addons_homeserver_container_network == '' else [matrix_addons_homeserver_container_network])
+
([postgres_container_network] if (postgres_enabled and matrix_bridge_beeper_line_database_hostname == postgres_connection_hostname and matrix_bridge_beeper_line_container_network != postgres_container_network) else [])
+
([matrix_playbook_reverse_proxyable_services_additional_network] if (matrix_playbook_reverse_proxyable_services_additional_network and matrix_bridge_beeper_line_container_labels_traefik_enabled) else [])
) | unique
}}

matrix_bridge_beeper_line_container_labels_traefik_enabled: "{{ matrix_playbook_reverse_proxy_type in ['playbook-managed-traefik', 'other-traefik-container'] }}"
matrix_bridge_beeper_line_container_labels_traefik_docker_network: "{{ matrix_playbook_reverse_proxyable_services_additional_network }}"
matrix_bridge_beeper_line_container_labels_traefik_entrypoints: "{{ traefik_entrypoint_primary }}"
matrix_bridge_beeper_line_container_labels_traefik_tls_certResolver: "{{ traefik_certResolver_primary }}"

matrix_bridge_beeper_line_appservice_token: "{{ (matrix_homeserver_generic_secret_key + ':line.as.token') | hash('sha512') | to_uuid }}"

matrix_bridge_beeper_line_homeserver_address: "{{ matrix_addons_homeserver_client_api_url }}"
matrix_bridge_beeper_line_homeserver_token: "{{ (matrix_homeserver_generic_secret_key + ':line.hs.token') | hash('sha512') | to_uuid }}"

matrix_bridge_beeper_line_homeserver_async_media: "{{ matrix_homeserver_implementation in ['synapse'] }}"

matrix_bridge_beeper_line_provisioning_shared_secret: "{{ (matrix_homeserver_generic_secret_key + ':line.prov') | hash('sha512') | to_uuid }}"

matrix_bridge_beeper_line_double_puppet_secrets_auto: |-
{{
({
matrix_bridge_beeper_line_homeserver_domain: ("as_token:" + matrix_appservice_double_puppet_registration_as_token)
})
if matrix_appservice_double_puppet_enabled
else {}
}}

matrix_bridge_beeper_line_scheme: "{{ 'https' if matrix_playbook_ssl_enabled else 'http' }}"
matrix_bridge_beeper_line_exposure_enabled: "{{ matrix_bridges_exposure_enabled }}"
matrix_bridge_beeper_line_exposure_hostname: "{{ matrix_bridges_exposure_hostname }}"
matrix_bridge_beeper_line_exposure_path_prefix: "{{ matrix_bridges_exposure_path_prefix }}/line"

matrix_bridge_beeper_line_database_engine: "{{ 'postgres' if postgres_enabled else 'sqlite' }}"
matrix_bridge_beeper_line_database_hostname: "{{ postgres_connection_hostname if postgres_enabled else '' }}"
matrix_bridge_beeper_line_database_password: "{{ (matrix_homeserver_generic_secret_key + ':line.db') | hash('sha512') | to_uuid }}"

######################################################################
#
# /matrix-bridge-beeper-line
#
######################################################################


######################################################################
#
# matrix-bridge-mautrix-bluesky
@@ -4164,6 +4248,12 @@ postgres_managed_databases_auto: |
'password': matrix_bridge_beeper_linkedin_database_password,
}] if (matrix_bridge_beeper_linkedin_enabled and matrix_bridge_beeper_linkedin_database_engine == 'postgres' and matrix_bridge_beeper_linkedin_database_hostname == postgres_connection_hostname) else [])
+
([{
'name': matrix_bridge_beeper_line_database_name,
'username': matrix_bridge_beeper_line_database_username,
'password': matrix_bridge_beeper_line_database_password,
}] if (matrix_bridge_beeper_line_enabled and matrix_bridge_beeper_line_database_engine == 'postgres' and matrix_bridge_beeper_line_database_hostname == postgres_connection_hostname) else [])
+
([{
'name': matrix_bridge_wechat_database_name,
'username': matrix_bridge_wechat_database_username,
@@ -5107,6 +5197,11 @@ matrix_ketesa_config_asManagedUsers_auto: |
'^@linkedin_[a-zA-Z0-9]+:'+(matrix_domain | regex_escape)+'$',
] if matrix_bridge_beeper_linkedin_enabled else [])
+
([
'^@'+(matrix_bridge_beeper_line_appservice_bot_username | default('') | regex_escape)+':'+(matrix_domain | regex_escape)+'$',
'^@line_[a-zA-Z0-9]+:'+(matrix_domain | regex_escape)+'$',
] if matrix_bridge_beeper_line_enabled else [])
+
([
'^@heisenbridge:'+(matrix_domain | regex_escape)+'$',
'^@hbirc_[a-zA-Z0-9]+:'+(matrix_domain | regex_escape)+'$',
@@ -6017,6 +6112,7 @@ matrix_static_files_file_matrix_client_property_org_matrix_msc4143_rtc_foci_auto
matrix_static_files_file_matrix_mautrix_property_fi_mau_bridges_auto: |-
{{
[
matrix_bridge_beeper_line_bridge_public_address if (matrix_bridge_beeper_line_enabled and matrix_bridge_beeper_line_container_labels_traefik_enabled and matrix_bridge_beeper_line_container_labels_exposure_enabled) else '',
matrix_bridge_mautrix_bluesky_appservice_public_address if (matrix_bridge_mautrix_bluesky_enabled and matrix_bridge_mautrix_bluesky_container_labels_traefik_enabled and matrix_bridge_mautrix_bluesky_container_labels_exposure_enabled) else '',
matrix_bridge_mautrix_gmessages_bridge_public_address if (matrix_bridge_mautrix_gmessages_enabled and matrix_bridge_mautrix_gmessages_container_labels_traefik_enabled and matrix_bridge_mautrix_gmessages_container_labels_exposure_enabled) else '',
matrix_bridge_mautrix_gvoice_bridge_public_address if (matrix_bridge_mautrix_gvoice_enabled and matrix_bridge_mautrix_gvoice_container_labels_traefik_enabled and matrix_bridge_mautrix_gvoice_container_labels_exposure_enabled) else '',


+ 225
- 0
roles/custom/matrix-bridge-beeper-line/defaults/main.yml Ver fichero

@@ -0,0 +1,225 @@
# SPDX-FileCopyrightText: 2026 MDAD project contributors
# SPDX-FileCopyrightText: 2026 Nikita Chernyi
#
# SPDX-License-Identifier: AGPL-3.0-or-later

---
# beeper-line is a Matrix <-> LINE bridge
# Project source code URL: https://github.com/beeper/line

matrix_bridge_beeper_line_enabled: true

matrix_bridge_beeper_line_container_image_self_build: false
matrix_bridge_beeper_line_container_image_self_build_repo: "https://github.com/beeper/line.git"
matrix_bridge_beeper_line_container_image_self_build_branch: "{{ 'main' if matrix_bridge_beeper_line_version == 'latest' else matrix_bridge_beeper_line_version }}"

matrix_bridge_beeper_line_version: 412eda7f028f0ee946d6fe584c64c7e97f27c7a7

# This image is maintained separately from the upstream project.
# To use another prebuilt image, override this variable directly.
matrix_bridge_beeper_line_container_image: "{{ matrix_bridge_beeper_line_container_image_registry_prefix }}crispyduck/beeper-line:{{ matrix_bridge_beeper_line_version }}"
matrix_bridge_beeper_line_container_image_registry_prefix: "{{ 'localhost/' if matrix_bridge_beeper_line_container_image_self_build else matrix_bridge_beeper_line_container_image_registry_prefix_upstream }}"
matrix_bridge_beeper_line_container_image_registry_prefix_upstream: "{{ matrix_bridge_beeper_line_container_image_registry_prefix_upstream_default }}"
matrix_bridge_beeper_line_container_image_registry_prefix_upstream_default: "docker.io/"

matrix_bridge_beeper_line_base_path: "{{ matrix_base_data_path }}/beeper-line"
matrix_bridge_beeper_line_config_path: "{{ matrix_bridge_beeper_line_base_path }}/config"
matrix_bridge_beeper_line_data_path: "{{ matrix_bridge_beeper_line_base_path }}/data"
matrix_bridge_beeper_line_container_src_files_path: "{{ matrix_bridge_beeper_line_base_path }}/docker-src"

matrix_bridge_beeper_line_homeserver_address: ""
# Whether asynchronous uploads via MSC2246 should be enabled for media.
# Requires a homeserver that supports MSC2246 (https://github.com/matrix-org/matrix-spec-proposals/pull/2246).
matrix_bridge_beeper_line_homeserver_async_media: false
matrix_bridge_beeper_line_homeserver_domain: "{{ matrix_domain }}"
matrix_bridge_beeper_line_appservice_address: "http://matrix-beeper-line:29322"

# Scheme of the bridge's public address (see `matrix_bridge_beeper_line_bridge_public_address`).
matrix_bridge_beeper_line_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.
matrix_bridge_beeper_line_bridge_public_address: "{{ (matrix_bridge_beeper_line_scheme + '://' + matrix_bridge_beeper_line_exposure_hostname + matrix_bridge_beeper_line_exposure_path_prefix) if matrix_bridge_beeper_line_exposure_enabled else '' }}"

matrix_bridge_beeper_line_msc4190_enabled: "{{ matrix_bridges_msc4190_enabled }}"
matrix_bridge_beeper_line_self_sign_enabled: "{{ matrix_bridges_self_sign_enabled }}"

matrix_bridge_beeper_line_backfill_enabled: false
matrix_bridge_beeper_line_backfill_max_initial_messages: 50
matrix_bridge_beeper_line_backfill_max_catchup_messages: 500
matrix_bridge_beeper_line_backfill_unread_hours_threshold: 720

matrix_bridge_beeper_line_command_prefix: "!line"

matrix_bridge_beeper_line_container_network: ""

matrix_bridge_beeper_line_container_additional_networks: "{{ matrix_bridge_beeper_line_container_additional_networks_auto + matrix_bridge_beeper_line_container_additional_networks_custom }}"
matrix_bridge_beeper_line_container_additional_networks_auto: []
matrix_bridge_beeper_line_container_additional_networks_custom: []

# matrix_bridge_beeper_line_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_bridge_beeper_line_container_labels_additional_labels`.
matrix_bridge_beeper_line_container_labels_traefik_enabled: true
matrix_bridge_beeper_line_container_labels_traefik_docker_network: "{{ matrix_bridge_beeper_line_container_network }}"
matrix_bridge_beeper_line_container_labels_traefik_entrypoints: web-secure
matrix_bridge_beeper_line_container_labels_traefik_tls_certResolver: default # noqa var-naming

# Controls whether labels will be added that expose beeper-line's HTTP API
# (used by tools like mautrix-manager for bridge login) at `https://<hostname><path_prefix>`.
matrix_bridge_beeper_line_container_labels_exposure_enabled: "{{ matrix_bridge_beeper_line_exposure_enabled }}"
matrix_bridge_beeper_line_container_labels_exposure_traefik_rule: "Host(`{{ matrix_bridge_beeper_line_exposure_hostname }}`) && PathPrefix(`{{ matrix_bridge_beeper_line_exposure_path_prefix }}`)"
matrix_bridge_beeper_line_container_labels_exposure_traefik_priority: 0
matrix_bridge_beeper_line_container_labels_exposure_traefik_entrypoints: "{{ matrix_bridge_beeper_line_container_labels_traefik_entrypoints }}"
matrix_bridge_beeper_line_container_labels_exposure_traefik_tls: "{{ matrix_bridge_beeper_line_container_labels_exposure_traefik_entrypoints != 'web' }}"
matrix_bridge_beeper_line_container_labels_exposure_traefik_tls_certResolver: "{{ matrix_bridge_beeper_line_container_labels_traefik_tls_certResolver }}" # noqa var-naming

# matrix_bridge_beeper_line_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_bridge_beeper_line_container_labels_additional_labels: |
# my.label=1
# another.label="here"
matrix_bridge_beeper_line_container_labels_additional_labels: ''

# A list of extra arguments to pass to the container
matrix_bridge_beeper_line_container_extra_arguments: []

# List of systemd services that matrix-beeper-line.service depends on.
matrix_bridge_beeper_line_systemd_required_services_list: "{{ matrix_bridge_beeper_line_systemd_required_services_list_default + matrix_bridge_beeper_line_systemd_required_services_list_auto + matrix_bridge_beeper_line_systemd_required_services_list_custom }}"
matrix_bridge_beeper_line_systemd_required_services_list_default: "{{ [devture_systemd_docker_base_docker_service_name] if devture_systemd_docker_base_docker_service_name else [] }}"
matrix_bridge_beeper_line_systemd_required_services_list_auto: []
matrix_bridge_beeper_line_systemd_required_services_list_custom: []

# List of systemd services that matrix-beeper-line.service wants
matrix_bridge_beeper_line_systemd_wanted_services_list: []

matrix_bridge_beeper_line_appservice_token: ''
matrix_bridge_beeper_line_homeserver_token: ''

matrix_bridge_beeper_line_appservice_bot_username: linebot
matrix_bridge_beeper_line_appservice_bot_displayname: LINE bridge bot
matrix_bridge_beeper_line_appservice_bot_avatar: ''

# Minimum severity of journal log messages.
# Valid values: fatal, error, warn, info, debug, trace
matrix_bridge_beeper_line_logging_level: 'warn'

# Whether or not created rooms should have federation enabled.
# If false, created portal rooms will never be federated.
matrix_bridge_beeper_line_federate_rooms: true

# Controls whether beeper-line's HTTP API is exposed publicly (used by tools like mautrix-manager for bridge login).
matrix_bridge_beeper_line_exposure_enabled: false
matrix_bridge_beeper_line_exposure_hostname: ''
matrix_bridge_beeper_line_exposure_path_prefix: ''

# Database-related configuration fields.
#
# To use SQLite, stick to these defaults.
#
# To use Postgres:
# - change the engine (`matrix_bridge_beeper_line_database_engine: 'postgres'`)
# - adjust your database credentials via the `matrix_bridge_beeper_line_database_*` variables
matrix_bridge_beeper_line_database_engine: 'sqlite'

matrix_bridge_beeper_line_sqlite_database_path_local: "{{ matrix_bridge_beeper_line_data_path }}/matrix-line.db"
matrix_bridge_beeper_line_sqlite_database_path_in_container: "file:/data/matrix-line.db?_txlock=immediate"

matrix_bridge_beeper_line_database_username: 'matrix_beeper_line'
matrix_bridge_beeper_line_database_password: 'some-password'
matrix_bridge_beeper_line_database_hostname: ''
matrix_bridge_beeper_line_database_port: 5432
matrix_bridge_beeper_line_database_name: 'matrix_beeper_line'
matrix_bridge_beeper_line_database_sslmode: disable

matrix_bridge_beeper_line_database_connection_string: 'postgresql://{{ matrix_bridge_beeper_line_database_username }}:{{ matrix_bridge_beeper_line_database_password }}@{{ matrix_bridge_beeper_line_database_hostname }}:{{ matrix_bridge_beeper_line_database_port }}/{{ matrix_bridge_beeper_line_database_name }}?sslmode={{ matrix_bridge_beeper_line_database_sslmode }}'

matrix_bridge_beeper_line_appservice_database_type: "{{ {
'sqlite': 'sqlite3-fk-wal',
'postgres': 'postgres',
}[matrix_bridge_beeper_line_database_engine] }}"

matrix_bridge_beeper_line_appservice_database_uri: "{{ {
'sqlite': matrix_bridge_beeper_line_sqlite_database_path_in_container,
'postgres': matrix_bridge_beeper_line_database_connection_string,
}[matrix_bridge_beeper_line_database_engine] }}"

matrix_bridge_beeper_line_double_puppet_secrets: "{{ matrix_bridge_beeper_line_double_puppet_secrets_auto | combine(matrix_bridge_beeper_line_double_puppet_secrets_custom) }}"
matrix_bridge_beeper_line_double_puppet_secrets_auto: {}
matrix_bridge_beeper_line_double_puppet_secrets_custom: {}

# Enable End-to-bridge encryption
matrix_bridge_beeper_line_bridge_encryption_allow: "{{ matrix_bridges_encryption_enabled }}"
matrix_bridge_beeper_line_bridge_encryption_default: "{{ matrix_bridges_encryption_default }}"
matrix_bridge_beeper_line_bridge_encryption_require: false
matrix_bridge_beeper_line_bridge_encryption_appservice: false
matrix_bridge_beeper_line_bridge_encryption_key_sharing_allow: "{{ matrix_bridge_beeper_line_bridge_encryption_allow }}"
matrix_bridge_beeper_line_bridge_encryption_pickle_key: mautrix.bridge.e2ee

matrix_bridge_beeper_line_appservice_username_template: "{% raw %}line_{{.}}{% endraw %}"

# Shared secret for authentication of provisioning API requests.
# If set to "disable", the provisioning API will be disabled.
matrix_bridge_beeper_line_provisioning_shared_secret: disable

matrix_bridge_beeper_line_bridge_personal_filtering_spaces: true

matrix_bridge_beeper_line_bridge_permissions: |
{{
{'*': 'relay', matrix_bridge_beeper_line_homeserver_domain: 'user'}
| combine({matrix_admin: 'admin'} if matrix_admin else {})
}}

# Default beeper-line configuration template which covers the generic use case.
# You can customize it by controlling the various variables inside it.
#
# For a more advanced customization, you can extend the default (see `matrix_bridge_beeper_line_configuration_extension_yaml`)
# or completely replace this variable with your own template.
matrix_bridge_beeper_line_configuration_yaml: "{{ lookup('template', 'templates/config.yaml.j2') }}"

matrix_bridge_beeper_line_configuration_extension_yaml: |
# Your custom YAML configuration goes here.
# This configuration extends the default starting configuration (`matrix_bridge_beeper_line_configuration_yaml`).
#
# You can override individual variables from the default configuration, or introduce new ones.
#
# If you need something more special, you can take full control by
# completely redefining `matrix_bridge_beeper_line_configuration_yaml`.

matrix_bridge_beeper_line_configuration_extension: "{{ matrix_bridge_beeper_line_configuration_extension_yaml | from_yaml if matrix_bridge_beeper_line_configuration_extension_yaml | from_yaml is mapping else {} }}"

# Holds the final configuration (a combination of the default and its extension).
# You most likely don't need to touch this variable. Instead, see `matrix_bridge_beeper_line_configuration_yaml`.
matrix_bridge_beeper_line_configuration: "{{ matrix_bridge_beeper_line_configuration_yaml | from_yaml | combine(matrix_bridge_beeper_line_configuration_extension, recursive=True) }}"

matrix_bridge_beeper_line_registration_yaml: |
id: line
url: {{ matrix_bridge_beeper_line_appservice_address }}
as_token: "{{ matrix_bridge_beeper_line_appservice_token }}"
hs_token: "{{ matrix_bridge_beeper_line_homeserver_token }}"
sender_localpart: _bot_{{ matrix_bridge_beeper_line_appservice_bot_username }}
rate_limited: false
namespaces:
users:
- regex: '^@line_.+:{{ matrix_bridge_beeper_line_homeserver_domain | regex_escape }}$'
exclusive: true
- exclusive: true
regex: '^@{{ matrix_bridge_beeper_line_appservice_bot_username | regex_escape }}:{{ matrix_bridge_beeper_line_homeserver_domain | regex_escape }}$'
de.sorunome.msc2409.push_ephemeral: true
receive_ephemeral: true
io.element.msc4190: {{ matrix_bridge_beeper_line_msc4190_enabled | to_json }}

matrix_bridge_beeper_line_registration: "{{ matrix_bridge_beeper_line_registration_yaml | from_yaml }}"

# matrix_bridge_beeper_line_restart_necessary controls whether the service
# will be restarted (when true) or merely started (when false) by the
# systemd service manager role (when conditional restart is enabled).
#
# This value is automatically computed during installation based on whether
# any configuration files, the systemd service file, or the container image changed.
# The default of `false` means "no restart needed", appropriate when the role's
# installation tasks haven't run (e.g., due to --tags skipping them).
matrix_bridge_beeper_line_restart_necessary: false

+ 25
- 0
roles/custom/matrix-bridge-beeper-line/tasks/main.yml Ver fichero

@@ -0,0 +1,25 @@
# SPDX-FileCopyrightText: 2026 MDAD project contributors
# SPDX-FileCopyrightText: 2026 Nikita Chernyi
#
# SPDX-License-Identifier: AGPL-3.0-or-later

---

- tags:
- setup-all
- setup-beeper-line
- install-all
- install-beeper-line
block:
- when: matrix_bridge_beeper_line_enabled | bool
ansible.builtin.include_tasks: "{{ role_path }}/tasks/validate_config.yml"

- when: matrix_bridge_beeper_line_enabled | bool
ansible.builtin.include_tasks: "{{ role_path }}/tasks/setup_install.yml"

- tags:
- setup-all
- setup-beeper-line
block:
- when: not matrix_bridge_beeper_line_enabled | bool
ansible.builtin.include_tasks: "{{ role_path }}/tasks/setup_uninstall.yml"

+ 143
- 0
roles/custom/matrix-bridge-beeper-line/tasks/setup_install.yml Ver fichero

@@ -0,0 +1,143 @@
# SPDX-FileCopyrightText: 2026 MDAD project contributors
# SPDX-FileCopyrightText: 2026 Nikita Chernyi
#
# SPDX-License-Identifier: AGPL-3.0-or-later

---

- ansible.builtin.set_fact:
matrix_bridge_beeper_line_migration_requires_restart: false

- when: "matrix_bridge_beeper_line_database_engine == 'postgres'"
block:
- name: Check if an SQLite database already exists
ansible.builtin.stat:
path: "{{ matrix_bridge_beeper_line_sqlite_database_path_local }}"
register: matrix_bridge_beeper_line_sqlite_database_path_local_stat_result

- when: "matrix_bridge_beeper_line_sqlite_database_path_local_stat_result.stat.exists | bool"
block:
- ansible.builtin.include_role:
name: galaxy/postgres
tasks_from: migrate_db_to_postgres
vars:
postgres_db_migration_request:
src: "{{ matrix_bridge_beeper_line_sqlite_database_path_local }}"
dst: "{{ matrix_bridge_beeper_line_database_connection_string }}"
caller: "{{ role_path | basename }}"
engine_variable_name: 'matrix_bridge_beeper_line_database_engine'
engine_old: 'sqlite'
systemd_services_to_stop: ['matrix-beeper-line.service']
pgloader_options: ['--with "quote identifiers"']

- ansible.builtin.set_fact:
matrix_bridge_beeper_line_migration_requires_restart: true

- name: Ensure Beeper LINE paths exist
ansible.builtin.file:
path: "{{ item.path }}"
state: directory
mode: '0750'
owner: "{{ matrix_user_name }}"
group: "{{ matrix_group_name }}"
with_items:
- {path: "{{ matrix_bridge_beeper_line_base_path }}", when: true}
- {path: "{{ matrix_bridge_beeper_line_config_path }}", when: true}
- {path: "{{ matrix_bridge_beeper_line_data_path }}", when: true}
- {path: "{{ matrix_bridge_beeper_line_container_src_files_path }}", when: "{{ matrix_bridge_beeper_line_container_image_self_build }}"}
when: item.when | bool

- name: Ensure Beeper LINE image is pulled
community.docker.docker_image_pull:
name: "{{ matrix_bridge_beeper_line_container_image }}"
pull: always
when: not matrix_bridge_beeper_line_container_image_self_build
register: matrix_bridge_beeper_line_container_image_pull_result
retries: "{{ devture_playbook_help_container_retries_count }}"
delay: "{{ devture_playbook_help_container_retries_delay }}"
until: matrix_bridge_beeper_line_container_image_pull_result is not failed

- name: Ensure Beeper LINE repository is present on self-build
ansible.builtin.git:
repo: "{{ matrix_bridge_beeper_line_container_image_self_build_repo }}"
dest: "{{ matrix_bridge_beeper_line_container_src_files_path }}"
version: "{{ matrix_bridge_beeper_line_container_image_self_build_branch }}"
force: "yes"
become: true
become_user: "{{ matrix_user_name }}"
register: matrix_bridge_beeper_line_git_pull_results
when: "matrix_bridge_beeper_line_container_image_self_build | bool"

- name: Ensure Beeper LINE Docker image is built
community.docker.docker_image_build:
name: "{{ matrix_bridge_beeper_line_container_image }}"
dockerfile: Dockerfile
path: "{{ matrix_bridge_beeper_line_container_src_files_path }}"
pull: true
rebuild: "{{ 'always' if matrix_bridge_beeper_line_git_pull_results.changed | bool else 'never' }}"
when: "matrix_bridge_beeper_line_container_image_self_build | bool"
register: matrix_bridge_beeper_line_container_image_build_result

- name: Ensure beeper-line config.yaml installed
ansible.builtin.copy:
content: "{{ matrix_bridge_beeper_line_configuration | to_nice_yaml(indent=2, width=999999) }}"
dest: "{{ matrix_bridge_beeper_line_config_path }}/config.yaml"
mode: '0644'
owner: "{{ matrix_user_name }}"
group: "{{ matrix_group_name }}"
register: matrix_bridge_beeper_line_config_result

- name: Ensure beeper-line registration.yaml installed
ansible.builtin.copy:
content: "{{ matrix_bridge_beeper_line_registration | to_nice_yaml(indent=2, width=999999) }}"
dest: "{{ matrix_bridge_beeper_line_config_path }}/registration.yaml"
mode: '0644'
owner: "{{ matrix_user_name }}"
group: "{{ matrix_group_name }}"
register: matrix_bridge_beeper_line_registration_result

- name: Ensure matrix-beeper-line.service installed
ansible.builtin.template:
src: "{{ role_path }}/templates/systemd/matrix-beeper-line.service.j2"
dest: "{{ devture_systemd_docker_base_systemd_path }}/matrix-beeper-line.service"
mode: '0644'
register: matrix_bridge_beeper_line_systemd_service_result

- name: Ensure beeper-line support files installed
ansible.builtin.template:
src: "{{ role_path }}/templates/{{ item }}.j2"
dest: "{{ matrix_bridge_beeper_line_base_path }}/{{ item }}"
mode: '0640'
owner: "{{ matrix_user_name }}"
group: "{{ matrix_group_name }}"
with_items:
- labels
register: matrix_bridge_beeper_line_support_files_result

- name: Ensure matrix-beeper-line container network is created
when: matrix_bridge_beeper_line_container_network != 'host'
community.general.docker_network:
enable_ipv6: "{{ devture_systemd_docker_base_ipv6_enabled }}"
name: "{{ matrix_bridge_beeper_line_container_network }}"
driver: bridge
driver_options: "{{ devture_systemd_docker_base_container_networks_driver_options }}"

- name: Determine whether matrix-beeper-line needs a restart
ansible.builtin.set_fact:
matrix_bridge_beeper_line_restart_necessary: >-
{{
matrix_bridge_beeper_line_migration_requires_restart | default(false)
or matrix_bridge_beeper_line_config_result.changed | default(false)
or matrix_bridge_beeper_line_registration_result.changed | default(false)
or matrix_bridge_beeper_line_support_files_result.changed | default(false)
or matrix_bridge_beeper_line_systemd_service_result.changed | default(false)
or matrix_bridge_beeper_line_container_image_pull_result.changed | default(false)
or matrix_bridge_beeper_line_container_image_build_result.changed | default(false)
}}

- name: Ensure matrix-beeper-line.service restarted, if necessary
ansible.builtin.service:
name: "matrix-beeper-line.service"
state: restarted
daemon_reload: true
when: "matrix_bridge_beeper_line_migration_requires_restart | bool"

+ 25
- 0
roles/custom/matrix-bridge-beeper-line/tasks/setup_uninstall.yml Ver fichero

@@ -0,0 +1,25 @@
# SPDX-FileCopyrightText: 2026 MDAD project contributors
# SPDX-FileCopyrightText: 2026 Nikita Chernyi
#
# SPDX-License-Identifier: AGPL-3.0-or-later

---

- name: Check existence of matrix-beeper-line service
ansible.builtin.stat:
path: "{{ devture_systemd_docker_base_systemd_path }}/matrix-beeper-line.service"
register: matrix_bridge_beeper_line_service_stat

- when: matrix_bridge_beeper_line_service_stat.stat.exists | bool
block:
- name: Ensure matrix-beeper-line is stopped
ansible.builtin.service:
name: matrix-beeper-line
state: stopped
enabled: false
daemon_reload: true

- name: Ensure matrix-beeper-line.service doesn't exist
ansible.builtin.file:
path: "{{ devture_systemd_docker_base_systemd_path }}/matrix-beeper-line.service"
state: absent

+ 26
- 0
roles/custom/matrix-bridge-beeper-line/tasks/validate_config.yml Ver fichero

@@ -0,0 +1,26 @@
# SPDX-FileCopyrightText: 2026 MDAD project contributors
# SPDX-FileCopyrightText: 2026 Nikita Chernyi
#
# SPDX-License-Identifier: AGPL-3.0-or-later

---

- name: (Deprecation) Catch and report renamed settings
ansible.builtin.fail:
msg: >-
Your configuration contains a variable, which now has a different name.
Please rename the variable (`{{ item.old }}` -> `{{ item.new }}`) on your configuration file (vars.yml).
when: "lookup('ansible.builtin.varnames', ('^' + item.old + '$'), wantlist=True) | length > 0"
with_items: []

- name: Fail if required beeper-line settings not defined
ansible.builtin.fail:
msg: >-
You need to define a required configuration setting (`{{ item.name }}`).
when: "item.when | bool and lookup('vars', item.name, default='') | string | length == 0"
with_items:
- {'name': 'matrix_bridge_beeper_line_appservice_token', when: true}
- {'name': 'matrix_bridge_beeper_line_homeserver_address', when: true}
- {'name': 'matrix_bridge_beeper_line_homeserver_token', when: true}
- {'name': 'matrix_bridge_beeper_line_database_hostname', when: "{{ matrix_bridge_beeper_line_database_engine == 'postgres' }}"}
- {'name': 'matrix_bridge_beeper_line_container_network', when: true}

+ 440
- 0
roles/custom/matrix-bridge-beeper-line/templates/config.yaml.j2 Ver fichero

@@ -0,0 +1,440 @@
#jinja2: lstrip_blocks: True
# Network-specific config options
network: {}

# Config options that affect the central bridge module.
bridge:
# The prefix for commands. Only required in non-management rooms.
command_prefix: {{ matrix_bridge_beeper_line_command_prefix | to_json }}
# Should the bridge create a space for each login containing the rooms that account is in?
personal_filtering_spaces: {{ matrix_bridge_beeper_line_bridge_personal_filtering_spaces | to_json }}
# Whether the bridge should set names and avatars explicitly for DM portals.
# This is only necessary when using clients that don't support MSC4171.
private_chat_portal_meta: true
# Should events be handled asynchronously within portal rooms?
# If true, events may end up being out of order, but slow events won't block other ones.
# This is not yet safe to use.
async_events: false
# Should every user have their own portals rather than sharing them?
# By default, users who are in the same group on the remote network will be
# in the same Matrix room bridged to that group. If this is set to true,
# every user will get their own Matrix room instead.
# SETTING THIS IS IRREVERSIBLE AND POTENTIALLY DESTRUCTIVE IF PORTALS ALREADY EXIST.
split_portals: false
# Should the bridge resend `m.bridge` events to all portals on startup?
resend_bridge_info: false
# Should `m.bridge` events be sent without a state key?
# By default, the bridge uses a unique key that won't conflict with other bridges.
no_bridge_info_state_key: false
# Should bridge connection status be sent to the management room as `m.notice` events?
# These contain the same data that can be posted to an external HTTP server using homeserver -> status_endpoint.
# Allowed values: none, errors, all
bridge_status_notices: errors
# How long after an unknown error should the bridge attempt a full reconnect?
# Must be at least 1 minute. The bridge will add an extra ±20% jitter to this value.
unknown_error_auto_reconnect: null
# Maximum number of times to do the auto-reconnect above.
# The counter is per login, but is never reset except on logout and restart.
unknown_error_max_auto_reconnects: 10

# Should leaving Matrix rooms be bridged as leaving groups on the remote network?
bridge_matrix_leave: false
# Should `m.notice` messages be bridged?
bridge_notices: false
# Should room tags only be synced when creating the portal? Tags mean things like favorite/pin and archive/low priority.
# Tags currently can't be synced back to the remote network, so a continuous sync means tagging from Matrix will be undone.
tag_only_on_create: true
# List of tags to allow bridging. If empty, no tags will be bridged.
only_bridge_tags: [m.favourite, m.lowpriority]
# Should room mute status only be synced when creating the portal?
# Like tags, mutes can't currently be synced back to the remote network.
mute_only_on_create: true
# Should the bridge check the db to ensure that incoming events haven't been handled before
deduplicate_matrix_messages: false
# Should cross-room reply metadata be bridged?
# Most Matrix clients don't support this and servers may reject such messages too.
cross_room_replies: false
# If a state event fails to bridge, should the bridge revert any state changes made by that event?
revert_failed_state_changes: false
# In portals with no relay set, should Matrix users be kicked if they're
# not logged into an account that's in the remote chat?
kick_matrix_users: true
# Should the bridge listen to com.beeper.state_request events?
# This is not necessary for anything outside of Beeper.
enable_send_state_requests: false

# What should be done to portal rooms when a user logs out or is logged out?
# Permitted values:
# nothing - Do nothing, let the user stay in the portals
# kick - Remove the user from the portal rooms, but don't delete them
# unbridge - Remove all ghosts in the room and disassociate it from the remote chat
# delete - Remove all ghosts and users from the room (i.e. delete it)
cleanup_on_logout:
# Should cleanup on logout be enabled at all?
enabled: false
# Settings for manual logouts (explicitly initiated by the Matrix user)
manual:
# Action for private portals which will never be shared with other Matrix users.
private: nothing
# Action for portals with a relay user configured.
relayed: nothing
# Action for portals which may be shared, but don't currently have any other Matrix users.
shared_no_users: nothing
# Action for portals which have other logged-in Matrix users.
shared_has_users: nothing
# Settings for credentials being invalidated (initiated by the remote network, possibly through user action).
# Keys have the same meanings as in the manual section.
bad_credentials:
private: nothing
relayed: nothing
shared_no_users: nothing
shared_has_users: nothing

# Settings for relay mode
relay:
# Whether relay mode should be allowed. If allowed, the set-relay command can be used to turn any
# authenticated user into a relaybot for that chat.
enabled: false
# Should only admins be allowed to set themselves as relay users?
# If true, non-admins can only set users listed in default_relays as relays in a room.
admin_only: true
# Should default relays be preferred when an explicit login ID isn't specified even if the user is logged in?
# This applies to the set-relay and bridge commands sent by any user, including admins.
prefer_default: true
# Should non-admins be allowed to use the bridge and sync-chat commands via default relays specified below?
allow_bridge: true
# List of user login IDs which anyone can set as a relay, as long as the relay user is in the room.
default_relays: []
# The formats to use when sending messages via the relaybot.
# Available variables:
# .Sender.UserID - The Matrix user ID of the sender.
# .Sender.Displayname - The display name of the sender (if set).
# .Sender.RequiresDisambiguation - Whether the sender's name may be confused with the name of another user in the room.
# .Sender.DisambiguatedName - The disambiguated name of the sender. This will be the displayname if set,
# plus the user ID in parentheses if the displayname is not unique.
# If the displayname is not set, this is just the user ID.
# .Message - The `formatted_body` field of the message.
# .Caption - The `formatted_body` field of the message, if it's a caption. Otherwise an empty string.
# .FileName - The name of the file being sent.
message_formats:
m.text: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b>: {{ .Message }}{% endraw %}"
m.notice: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b>: {{ .Message }}{% endraw %}"
m.emote: "{% raw %}* <b>{{ .Sender.DisambiguatedName }}</b> {{ .Message }}{% endraw %}"
m.file: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b> sent a file{{ if .Caption }}: {{ .Caption }}{{ end }}{% endraw %}"
m.image: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b> sent an image{{ if .Caption }}: {{ .Caption }}{{ end }}{% endraw %}"
m.audio: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b> sent an audio file{{ if .Caption }}: {{ .Caption }}{{ end }}{% endraw %}"
m.video: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b> sent a video{{ if .Caption }}: {{ .Caption }}{{ end }}{% endraw %}"
m.location: "{% raw %}<b>{{ .Sender.DisambiguatedName }}</b> sent a location{{ if .Caption }}: {{ .Caption }}{{ end }}{% endraw %}"

# Filter for automatically creating portals.
portal_create_filter:
# The mode for filtering, either `deny` or `allow`
mode: deny
# The list of portal IDs to deny or allow depending on the mode config.
# Items here can either be the plain portal ID as a string, or an object with `id` and `receiver` fields.
# The receiver field is necessary if you want to target a specific DM portal for example.
list: []
# A list of user login IDs from which to always deny creating portals.
# This is meant to be used with default relays, such that the relay bot
# being added to a group wouldn't automatically trigger portal creation.
always_deny_from_login: []

# Permissions for using the bridge.
# Permitted values:
# relay - Talk through the relaybot (if enabled), no access otherwise
# commands - Access to use commands in the bridge, but not login.
# user - Access to use the bridge with puppeting.
# admin - Full access, user level with some additional administration tools.
# Permitted keys:
# * - All Matrix users
# domain - All users on that homeserver
# mxid - Specific user
permissions: {{ matrix_bridge_beeper_line_bridge_permissions | to_json }}

# Config for the bridge's database.
database:
# The database type. "sqlite3-fk-wal" and "postgres" are supported.
type: {{ matrix_bridge_beeper_line_appservice_database_type | to_json }}
# The database URI.
# SQLite: A raw file path is supported, but `file:<path>?_txlock=immediate` is recommended.
# https://github.com/mattn/go-sqlite3#connection-string
# Postgres: Connection string. For example, postgres://user:password@host/database?sslmode=disable
# To connect via Unix socket, use something like postgres:///dbname?host=/var/run/postgresql
uri: {{ matrix_bridge_beeper_line_appservice_database_uri | to_json }}
# Maximum number of connections.
max_open_conns: 5
max_idle_conns: 1
# Maximum connection idle time and lifetime before they're closed. Disabled if null.
# Parsed with https://pkg.go.dev/time#ParseDuration
max_conn_idle_time: null
max_conn_lifetime: null

# Homeserver details.
homeserver:
# The address that this appservice can use to connect to the homeserver.
# Local addresses without HTTPS are generally recommended when the bridge is running on the same machine,
# but https also works if they run on different machines.
address: {{ matrix_bridge_beeper_line_homeserver_address | to_json }}
# The domain of the homeserver (also known as server_name, used for MXIDs, etc).
domain: {{ matrix_bridge_beeper_line_homeserver_domain | to_json }}

# What software is the homeserver running?
# Standard Matrix homeservers like Synapse, Dendrite and Conduit should just use "standard" here.
software: standard
# The URL to push real-time bridge status to.
# If set, the bridge will make POST requests to this URL whenever a user's remote network connection state changes.
# The bridge will use the appservice as_token to authorize requests.
status_endpoint:
# Endpoint for reporting per-message status.
# If set, the bridge will make POST requests to this URL when processing a message from Matrix.
# It will make one request when receiving the message (step BRIDGE), one after decrypting if applicable
# (step DECRYPTED) and one after sending to the remote network (step REMOTE). Errors will also be reported.
# The bridge will use the appservice as_token to authorize requests.
message_send_checkpoint_endpoint:
# Does the homeserver support https://github.com/matrix-org/matrix-spec-proposals/pull/2246?
async_media: {{ matrix_bridge_beeper_line_homeserver_async_media | to_json }}

# Should the bridge use a websocket for connecting to the homeserver?
# The server side is currently not documented anywhere and is only implemented by mautrix-wsproxy,
# mautrix-asmux (deprecated), and hungryserv (proprietary).
websocket: false
# How often should the websocket be pinged? Pinging will be disabled if this is zero.
ping_interval_seconds: 0

# Application service host/registration related details.
# Changing these values requires regeneration of the registration (except when noted otherwise)
appservice:
# The address that the homeserver can use to connect to this appservice.
# Like the homeserver address, a local non-https address is recommended when the bridge is on the same machine.
# If the bridge is elsewhere, you must secure the connection yourself (e.g. with https or wireguard)
# If you want to use https, you need to use a reverse proxy. The bridge does not have TLS support built in.
address: {{ matrix_bridge_beeper_line_appservice_address | to_json }}
# A public address that external services can use to reach this appservice.
# A reverse proxy is generally necessary when using this field.
# This value doesn't affect the registration file.
public_address: {{ matrix_bridge_beeper_line_bridge_public_address | to_json }}

# The hostname and port where this appservice should listen.
# For Docker, you generally have to change the hostname to 0.0.0.0.
hostname: 0.0.0.0
port: 29322

# The unique ID of this appservice.
id: line
# Appservice bot details.
bot:
# Username of the appservice bot.
username: {{ matrix_bridge_beeper_line_appservice_bot_username | to_json }}
# Display name and avatar for bot. Set to "remove" to remove display name/avatar, leave empty
# to leave display name/avatar as-is.
displayname: {{ matrix_bridge_beeper_line_appservice_bot_displayname | to_json }}
avatar: {{ matrix_bridge_beeper_line_appservice_bot_avatar | to_json }}

# Whether to receive ephemeral events via appservice transactions.
ephemeral_events: true
# Should incoming events be handled asynchronously?
# This may be necessary for large public instances with lots of messages going through.
# However, messages will not be guaranteed to be bridged in the same order they were sent in.
# This value doesn't affect the registration file.
async_transactions: false

# Authentication tokens for AS <-> HS communication. Autogenerated; do not modify.
as_token: {{ matrix_bridge_beeper_line_appservice_token | to_json }}
hs_token: {{ matrix_bridge_beeper_line_homeserver_token | to_json }}

# Localpart template of MXIDs for remote users.
# {% raw %}{{.}}{% endraw %} is replaced with the internal ID of the user.
username_template: {{ matrix_bridge_beeper_line_appservice_username_template | to_json }}

# Config options that affect the Matrix connector of the bridge.
matrix:
# Whether the bridge should send the message status as a custom com.beeper.message_send_status event.
message_status_events: false
# Whether the bridge should send a read receipt after successfully bridging a message.
delivery_receipts: false
# Whether the bridge should send error notices via m.notice events when a message fails to bridge.
message_error_notices: true
# Whether the bridge should update the m.direct account data event when double puppeting is enabled.
sync_direct_chat_list: true
# Whether created rooms should have federation enabled. If false, created portal rooms
# will never be federated. Changing this option requires recreating rooms.
federate_rooms: {{ matrix_bridge_beeper_line_federate_rooms | to_json }}
# The threshold as bytes after which the bridge should roundtrip uploads via the disk
# rather than keeping the whole file in memory.
upload_file_threshold: 5242880
# Should the bridge set additional custom profile info for ghosts?
# This can make a lot of requests, as there's no batch profile update endpoint.
ghost_extra_profile_info: false

# Segment-compatible analytics endpoint for tracking some events, like provisioning API login and encryption errors.
analytics:
# API key to send with tracking requests. Tracking is disabled if this is null.
token: null
# Address to send tracking requests to.
url: https://api.segment.io/v1/track
# Optional user ID for tracking events. If null, defaults to using Matrix user ID.
user_id: null

# Settings for provisioning API
provisioning:
# Shared secret for authentication. If set to "generate" or null, a random secret will be generated,
# or if set to "disable", the provisioning API will be disabled. Must be at least 16 characters.
shared_secret: {{ matrix_bridge_beeper_line_provisioning_shared_secret | to_json }}
# Whether to allow provisioning API requests to be authed using Matrix access tokens.
# This follows the same rules as double puppeting to determine which server to contact to check the token,
# which means that by default, it only works for users on the same server as the bridge.
allow_matrix_auth: true
# Enable debug API at /debug with provisioning authentication.
debug_endpoints: false
# Enable session transfers between bridges. Note that this only validates Matrix or shared secret
# auth before passing live network client credentials down in the response.
enable_session_transfers: false

# Settings for backfilling messages.
# Note that the exact way settings are applied depends on the network connector.
# See https://docs.mau.fi/bridges/general/backfill.html for more details.
backfill:
# Whether to do backfilling at all.
enabled: {{ matrix_bridge_beeper_line_backfill_enabled | to_json }}
# Maximum number of messages to backfill in empty rooms.
# If this is zero or negative, backfill will be disabled in new rooms.
max_initial_messages: {{ matrix_bridge_beeper_line_backfill_max_initial_messages | to_json }}
# Maximum number of missed messages to backfill after bridge restarts.
max_catchup_messages: {{ matrix_bridge_beeper_line_backfill_max_catchup_messages | to_json }}
# If a backfilled chat is older than this number of hours,
# mark it as read even if it's unread on the remote network.
unread_hours_threshold: {{ matrix_bridge_beeper_line_backfill_unread_hours_threshold | to_json }}
# Settings for the backwards backfill queue. This only applies when connecting to
# Beeper as standard Matrix servers don't support inserting messages into history.
queue:
# Should the backfill queue be enabled?
enabled: false
# Should manual calls to backfill queue tasks be allowed?
manual: false
# Number of messages to backfill in one batch.
batch_size: 100
# Delay between batches in seconds.
batch_delay: 20
# Maximum number of batches to backfill per portal.
# If set to -1, all available messages will be backfilled.
max_batches: -1
# Optional network-specific overrides for max batches.
# Interpretation of this field depends on the network connector.
max_batches_override: {}

# Settings for enabling double puppeting
double_puppet:
# Servers to always allow double puppeting from.
# This is only for other servers and should NOT contain the server the bridge is on.
servers: {}
# Whether to allow client API URL discovery for other servers. When using this option,
# users on other servers can use double puppeting even if their server URLs aren't
# explicitly added to the servers map above.
allow_discovery: false
# Shared secrets for automatic double puppeting.
# See https://docs.mau.fi/bridges/general/double-puppeting.html for instructions.
secrets: {{ matrix_bridge_beeper_line_double_puppet_secrets | to_json }}

# End-to-bridge encryption support options.
#
# See https://docs.mau.fi/bridges/general/end-to-bridge-encryption.html for more info.
encryption:
# Whether to enable encryption at all. If false, the bridge will not function in encrypted rooms.
allow: {{ matrix_bridge_beeper_line_bridge_encryption_allow | to_json }}
# Whether to force-enable encryption in all bridged rooms.
default: {{ matrix_bridge_beeper_line_bridge_encryption_default | to_json }}
# Whether to require all messages to be encrypted and drop any unencrypted messages.
require: {{ matrix_bridge_beeper_line_bridge_encryption_require | to_json }}
# Whether to use MSC3202/MSC4203 instead of /sync long polling for receiving encryption-related data.
# This is an experimental option, see the docs for more info.
# Changing this option requires updating the appservice registration file.
appservice: {{ matrix_bridge_beeper_line_bridge_encryption_appservice | to_json }}
# Whether to use MSC4190 instead of appservice login to create the bridge bot device.
# Requires the homeserver to support MSC4190 and the device masquerading parts of MSC3202.
# Only relevant when using end-to-bridge encryption, required when using encryption with next-gen auth (MSC3861).
msc4190: {{ matrix_bridge_beeper_line_msc4190_enabled | to_json }}
# Whether to encrypt reactions and reply metadata as per MSC4392.
# This is not supported by most clients.
msc4392: false
# Should the bridge bot generate a recovery key and cross-signing keys and verify itself?
# Note that without the latest version of MSC4190, this will fail if you reset the bridge database.
# The generated recovery key will be saved in the kv_store table under `recovery_key`.
self_sign: {{ matrix_bridge_beeper_line_self_sign_enabled | to_json }}
# Enable key sharing? If enabled, key requests for rooms where users are in will be fulfilled.
# You must use a client that supports requesting keys from other users to use this feature.
allow_key_sharing: {{ matrix_bridge_beeper_line_bridge_encryption_key_sharing_allow | to_json }}
# Pickle key for encrypting encryption keys in the bridge database.
# If set to generate, a random key will be generated.
pickle_key: {{ matrix_bridge_beeper_line_bridge_encryption_pickle_key | to_json }}
# Options for deleting megolm sessions from the bridge.
delete_keys:
# Beeper-specific: delete outbound sessions when hungryserv confirms
# that the user has uploaded the key to key backup.
delete_outbound_on_ack: false
# Don't store outbound sessions in the inbound table.
dont_store_outbound: false
# Ratchet megolm sessions forward after decrypting messages.
ratchet_on_decrypt: false
# Delete fully used keys (index >= max_messages) after decrypting messages.
delete_fully_used_on_decrypt: false
# Delete previous megolm sessions from same device when receiving a new one.
delete_prev_on_new_session: false
# Delete megolm sessions received from a device when the device is deleted.
delete_on_device_delete: false
# Periodically delete megolm sessions when 2x max_age has passed since receiving the session.
periodically_delete_expired: false
# Delete inbound megolm sessions that don't have the received_at field used for
# automatic ratcheting and expired session deletion. This is meant as a migration
# to delete old keys prior to the bridge update.
delete_outdated_inbound: false
# What level of device verification should be required from users?
#
# Valid levels:
# unverified - Send keys to all device in the room.
# cross-signed-untrusted - Require valid cross-signing, but trust all cross-signing keys.
# cross-signed-tofu - Require valid cross-signing, trust cross-signing keys on first use (and reject changes).
# cross-signed-verified - Require valid cross-signing, plus a valid user signature from the bridge bot.
# Note that creating user signatures from the bridge bot is not currently possible.
# verified - Require manual per-device verification
# (currently only possible by modifying the `trust` column in the `crypto_device` database table).
verification_levels:
# Minimum level for which the bridge should send keys to when bridging messages from the remote network to Matrix.
receive: unverified
# Minimum level that the bridge should accept for incoming Matrix messages.
send: unverified
# Minimum level that the bridge should require for accepting key requests.
share: cross-signed-tofu
# Options for Megolm room key rotation. These options allow you to configure the m.room.encryption event content.
# See https://spec.matrix.org/v1.10/client-server-api/#mroomencryption for more information about that event.
rotation:
# Enable custom Megolm room key rotation settings. Note that these
# settings will only apply to rooms created after this option is set.
enable_custom: false
# The maximum number of milliseconds a session should be used
# before changing it. The Matrix spec recommends 604800000 (a week)
# as the default.
milliseconds: 604800000
# The maximum number of messages that should be sent with a given a
# session before changing it. The Matrix spec recommends 100 as the
# default.
messages: 100
# Disable rotating keys when a user's devices change?
# You should not enable this option unless you understand all the implications.
disable_device_change_key_rotation: false

# Prefix for environment variables. All variables with this prefix must map to valid config fields.
# Nesting in variable names is represented with a dot (.).
# If there are no dots in the name, two underscores (__) are replaced with a dot.
#
# e.g. if the prefix is set to `BRIDGE_`, then `BRIDGE_APPSERVICE__AS_TOKEN` will set appservice.as_token.
# `BRIDGE_appservice.as_token` would work as well, but can't be set in a shell as easily.
#
# If this is null, reading config fields from environment will be disabled.
env_config_prefix: null

# Logging config. See https://github.com/tulir/zeroconfig for details.
logging:
min_level: {{ matrix_bridge_beeper_line_logging_level }}
writers:
- type: stdout
format: pretty

+ 4
- 0
roles/custom/matrix-bridge-beeper-line/templates/config.yaml.j2.license Ver fichero

@@ -0,0 +1,4 @@
SPDX-FileCopyrightText: 2026 MDAD project contributors
SPDX-FileCopyrightText: 2026 Nikita Chernyi

SPDX-License-Identifier: AGPL-3.0-or-later

+ 49
- 0
roles/custom/matrix-bridge-beeper-line/templates/labels.j2 Ver fichero

@@ -0,0 +1,49 @@
{#
SPDX-FileCopyrightText: 2026 MDAD project contributors

SPDX-License-Identifier: AGPL-3.0-or-later
#}

{% if matrix_bridge_beeper_line_container_labels_traefik_enabled %}
traefik.enable=true

{% if matrix_bridge_beeper_line_container_labels_traefik_docker_network %}
traefik.docker.network={{ matrix_bridge_beeper_line_container_labels_traefik_docker_network }}
{% endif %}

{% if matrix_bridge_beeper_line_container_labels_exposure_enabled %}
############################################################
# #
# Bridge API exposure #
# #
############################################################

traefik.http.services.matrix-beeper-line-exposure.loadbalancer.server.port=29322

traefik.http.middlewares.matrix-beeper-line-exposure-strip-prefix.stripprefix.prefixes={{ matrix_bridge_beeper_line_exposure_path_prefix }}
traefik.http.routers.matrix-beeper-line-exposure.middlewares=matrix-beeper-line-exposure-strip-prefix

traefik.http.routers.matrix-beeper-line-exposure.rule={{ matrix_bridge_beeper_line_container_labels_exposure_traefik_rule }}

{% if matrix_bridge_beeper_line_container_labels_exposure_traefik_priority | int > 0 %}
traefik.http.routers.matrix-beeper-line-exposure.priority={{ matrix_bridge_beeper_line_container_labels_exposure_traefik_priority }}
{% endif %}

traefik.http.routers.matrix-beeper-line-exposure.service=matrix-beeper-line-exposure
traefik.http.routers.matrix-beeper-line-exposure.entrypoints={{ matrix_bridge_beeper_line_container_labels_exposure_traefik_entrypoints }}

traefik.http.routers.matrix-beeper-line-exposure.tls={{ matrix_bridge_beeper_line_container_labels_exposure_traefik_tls | to_json }}
{% if matrix_bridge_beeper_line_container_labels_exposure_traefik_tls %}
traefik.http.routers.matrix-beeper-line-exposure.tls.certResolver={{ matrix_bridge_beeper_line_container_labels_exposure_traefik_tls_certResolver }}
{% endif %}

############################################################
# #
# /Bridge API exposure #
# #
############################################################
{% endif %}

{% endif %}

{{ matrix_bridge_beeper_line_container_labels_additional_labels }}

+ 51
- 0
roles/custom/matrix-bridge-beeper-line/templates/systemd/matrix-beeper-line.service.j2 Ver fichero

@@ -0,0 +1,51 @@
#jinja2: lstrip_blocks: True
[Unit]
Description=Matrix Beeper LINE bridge
{% for service in matrix_bridge_beeper_line_systemd_required_services_list %}
Requires={{ service }}
After={{ service }}
{% endfor %}
{% for service in matrix_bridge_beeper_line_systemd_wanted_services_list %}
Wants={{ service }}
{% endfor %}
DefaultDependencies=no

[Service]
Type=simple
Environment="HOME={{ devture_systemd_docker_base_systemd_unit_home_path }}"
ExecStartPre=-{{ devture_systemd_docker_base_host_command_sh }} -c '{{ devture_systemd_docker_base_host_command_docker }} stop -t {{ devture_systemd_docker_base_container_stop_grace_time_seconds }} matrix-beeper-line 2>/dev/null || true'
ExecStartPre=-{{ devture_systemd_docker_base_host_command_sh }} -c '{{ devture_systemd_docker_base_host_command_docker }} rm matrix-beeper-line 2>/dev/null || true'

ExecStartPre={{ devture_systemd_docker_base_host_command_docker }} create \
--rm \
--name=matrix-beeper-line \
--log-driver=none \
--user={{ matrix_user_uid }}:{{ matrix_user_gid }} \
--cap-drop=ALL \
--network={{ matrix_bridge_beeper_line_container_network }} \
--mount type=bind,src={{ matrix_bridge_beeper_line_config_path }},dst=/config,ro \
--mount type=bind,src={{ matrix_bridge_beeper_line_data_path }},dst=/data \
--label-file={{ matrix_bridge_beeper_line_base_path }}/labels \
--workdir=/data \
{% for arg in matrix_bridge_beeper_line_container_extra_arguments %}
{{ arg }} \
{% endfor %}
{{ matrix_bridge_beeper_line_container_image }} \
/usr/bin/matrix-line -c /config/config.yaml -r /config/registration.yaml --no-update

{% if matrix_bridge_beeper_line_container_network != 'host' %}
{% for network in matrix_bridge_beeper_line_container_additional_networks %}
ExecStartPre={{ devture_systemd_docker_base_host_command_docker }} network connect {{ network }} matrix-beeper-line
{% endfor %}
{% endif %}

ExecStart={{ devture_systemd_docker_base_host_command_docker }} start --attach matrix-beeper-line

ExecStop=-{{ devture_systemd_docker_base_host_command_sh }} -c '{{ devture_systemd_docker_base_host_command_docker }} stop -t {{ devture_systemd_docker_base_container_stop_grace_time_seconds }} matrix-beeper-line 2>/dev/null || true'
ExecStop=-{{ devture_systemd_docker_base_host_command_sh }} -c '{{ devture_systemd_docker_base_host_command_docker }} rm matrix-beeper-line 2>/dev/null || true'
Restart=always
RestartSec=30
SyslogIdentifier=matrix-beeper-line

[Install]
WantedBy=multi-user.target

+ 4
- 0
roles/custom/matrix-bridge-beeper-line/templates/systemd/matrix-beeper-line.service.j2.license Ver fichero

@@ -0,0 +1,4 @@
SPDX-FileCopyrightText: 2026 MDAD project contributors
SPDX-FileCopyrightText: 2026 Nikita Chernyi

SPDX-License-Identifier: AGPL-3.0-or-later

+ 1
- 0
setup.yml Ver fichero

@@ -57,6 +57,7 @@
- custom/matrix-bridge-appservice-discord
- custom/matrix-bridge-appservice-irc
- custom/matrix-bridge-beeper-linkedin
- custom/matrix-bridge-beeper-line
- custom/matrix-bridge-wechat
- custom/matrix-bridge-mautrix-twitter
- custom/matrix-bridge-mautrix-googlechat


Cargando…
Cancelar
Guardar