8. 安全

此处的文章涵盖了 Tigase Server 内置的高级安全功能,以及一些用于添加您自己的安全级别的选项。

8.1. XEP-0191:阻止命令

然而,XMPP 服务器中最简单的安全功能是阻止用户和 JIDS 的能力。 XEP-0191 指定不使用隐私列表的简单屏蔽的参数。以下是细分和一些您可能会发现有用的示例命令。要启用此功能,请确保您的 config.tdsl 文件中包含以下内容:

}
'sess-man' {
    'urn:xmpp:blocking' () {}
}

如果您有其他插件正在运行,那么只需将 'urn:xmpp:blocking' () {} 添加到列表中以激活此功能。

要确认您安装的 Tigase 是否支持此功能,您的服务器的快速 disco#info 应显示以下功能:

<feature var='urn:xmpp:blocking'/>

被阻止的用户以每个 JID 为基础存储在服务器上,因此一个用户可能只能看到他或她被阻止的 JIDs。被阻止的 JIDs 列表将作为带有 <item> 字段列表的 IQ 节返回。要检索阻止列表,发出以下命令:

<iq type='get' id='blockedjids'>
  <blocklist xmlns='urn:xmpp:blocking'/>
</iq>

服务器响应:

<iq type='result' id='blockedjids'>
  <blocklist xmlns='urn:xmpp:blocking'>
    <item jid='[email protected]'/>
    <item jid='[email protected]'/>
  </blocklist>
</iq>

要阻止 JID,将与上述类似的节发送到服务器,其中包含您希望添加的被阻止 JID 的项目:

<iq from='[email protected]' type='set' id='block'>
  <block xmlns='urn:xmpp:blocking'>
    <item jid='[email protected]'/>
  </block>
</iq>

然后,服务器会将不可用的状态推送给被阻止的联系人。被阻止的联系人与阻止它的实体之间的通信将导致 <not-acceptable> 错误:

<message type='error' from='[email protected]' to='[email protected]'>
  <body>Hello, are you online?</body>
  <error type='cancel'>
    <not-acceptable xmlns='urn:ietf:params:xml:ns:xmpp-stanzas'/>
    <blocked xmlns='urn:xmpp:blocking:errors'/>
  </error>
</message>

取消阻止联系人就像阻止一样简单,向服务器发送取消阻止节:

<iq from='[email protected]' type='set' id='unblock'>
  <unblock xmlns='urn:xmpp:blocking'>
    <item jid='[email protected]'/>
  </unblock>
</iq>

只要权限没有改变,服务器就会开始向未阻止的联系人和资源推送存在信息。

您也可以选择取消阻止所有联系人,并使用以下命令从根本上清除您的阻止列表:

<iq type='set' id='unblockall'>
  <unblock xmlns='urn:xmpp:blocking'/>
</iq>

8.2. 帐户注册限制

为了保护 Tigase 服务器免受 DOS 攻击,已经限制了每秒帐户的注册数量。这可以通过在 config.tdsl 文件中添加以下行来配置:

'registration-throttling' () {
    limit = 10

此设置允许每秒从单个 IP 进行 10 次注册。如果超出限制,将返回 NOT_ALLOWED 错误。

也可以创建两个单独的计数器:

'registration-throttling' () {
    limit = 10
}
c2s {
    'registration-throttling' (class: tigase.server.xmppclient.RegistrationThrottling) {
        limit = 3
    }
}

在这里,我们有一个用于 c2s 的计数器其限制为 3,而另外一个用于所有其他连接管理器的全局设置为 10。

您还可以设置单个组件限制:

ws2s {
    'registration-throttling' (class: tigase.server.xmppclient.RegistrationThrottling) {
        limit = 7
    }
}

8.3. 暴力攻击预防

暴力预防旨在保护 Tigase 服务器不会被猜测的用户密码破解。它计算无效的登录尝试,当它超过限制时,它会锁定特定时间的登录能力(软禁令)。当无效登录计数器达到第二级时,帐户将被永久禁用。

8.3.1. 配置

暴力防护由 VHost 配置。有以下配置参数列表:

brute-force-lock-enabled

boolean

启用暴力预防

brute-force-lock-after-fails

long

允许的无效登录次数

brute-force-period-time

long

计算失败登录尝试的时间 [秒]

brute-force-disable-after-fails

long

帐户将被永久禁用的阈值

brute-force-lock-time

long

软禁令的时间[秒](第一个阈值)

brute-force-mode

string

工作模式(参见 工作模式

详细统计

默认情况下,为了不污染统计数据,Brute-Force locker 将仅提供有关 locker IP 和 JID 数量(以及锁定尝试总数)的详细信息。为了获得相关已锁定在统计信息中的 IP 和 JID 的详细信息,您应该使用以下配置:

'sess-man' () {
    'brute-force-locker' () {
        detailedStatistics = false
    }
}

工作模式

共有三种工作模式:

  • Ip - 它计算来自 IP 的无效登录尝试,并锁定达到阈值的 IP 的登录(软禁令)

  • IpJid - 它计算从 IP 到特定用户帐户的尝试。软禁令锁定从特定 IP 登录特定 JID 的能力。

  • Jid- 类似于 IpJid 但只检查 JID。软禁令锁定从所有 IP 登录到特定 JID 的能力。

永久禁令

JidIpJid 模式下,当无效登录计数器达到 brute-force-disable-after-fails 阈值时,帐户状态将设置为 disabled。要再次启用它,您应该使用 Re-Enable User Ad-hoc 命令。

8.4. 服务器证书

8.4.1. 在 pem 文件中创建和加载服务器证书

服务器证书

使用安全套接字连接时需要服务器证书 - SSL/TLS。

对于安全套接字连接,需要适当的证书。您可以生成自己的自签名证书或从受信任的第三方组织获取证书。

以下是如何从受信任的组织获取证书的步骤。

生成您自己的证书

在 Linux 系统上可以轻松生成自签名证书。尽管它可能不被视为’信任的’证书颁发机构,但它对测试服务器安装很有用。 我们不建议经常使用自签名证书

备注

Tigase v5.0 及更高版本可以在需要时自动创建自签名 PEM 文件。但是,我们将介绍手动如何执行此过程。

本教程假设您正在运行基于 Linux 的操作系统,可以访问命令 shell,并且系统上安装了 ‘Openssl’ 包。

该过程采取以下步骤:
1. Create a local private key. This file ends with .key extension. It is recommended to create a new private key for the process.
2. Generate a certificate request. This file ends with the .csr extension and is the file sent to the Certificate Authority to be signed.
3. CA signs private key. This can be done by your own computer, but can also be done by private CAs for a fee.
4. Results are obtained from the CA. This is a .crt file which contains a separate public certificate.
5. Combine the .csr and .crt file into a unified .pem file. Tigase requires keys to be non-password protected PEM files.

生成本地私钥。

openssl genrsa -out [domain.com.key] 1024

此命令使用 1024 位 RSA 算法生成私钥。 -out 指定文件的名称,在这种情况下它将是 domain.com.key。确切的名称并不重要,文件将在您当前所在的任何目录中创建。

生成证书请求:

openssl req -nodes -key domain.com.key -out domain.com.csr

该命令使用 -key 之后指定的文件生成证书请求,结果文件将是 domain.com.csr。您将被问到一系列问题以生成请求。

Country Name (2 letter code) [AU]:AU
State or Province Name (full name) [Some-State]:Somestate
Locality Name (eg, city) []:Your city name
Organization Name (eg, company) [Internet Widgits Pty Ltd]:Company name
Organizational Unit Name (eg, section) []:Department or any unit
Common Name (eg, YOUR name) []:*.yourdomain.com
Email Address []:[email protected]

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:
An optional company name []:

签署证书请求:

现在 .csr 文件将由证书颁发机构签名。在本教程中,我们将自签名我们的证书。但是,通常不建议采用这种做法,并且您会收到有关您的证书不受信任的通知。公司提供商业报价以从受信任的来源签署您的证书。有关更多信息,请参阅 来自其他提供商的证书 部分。

openssl x509 -req -days 365 -in domain.com.csr -signkey domain.com.key -out domain.com.crt

此命令证书签名 365 天并生成 domain.com.crt 文件。当然,您可以使用任意天数。

生成 PEM 文件。

您现在应该在工作目录中有以下文件:..\ domain.com.key domain.com.csr domain.com.crt

cat yourdomain.com.cert.pem intermediate.cert.pem root.cert.pem > yourdomain.com.pem

如果证书是由第三方机构颁发的,您必须附加证书链,即生成您的证书的机构的证书。您通常需要从生成您的证书的机构获取您的链的证书。

结果文件应类似于:

-----BEGIN CERTIFICATE-----
MIIG/TCCBeWgAwIBAgIDAOwZMA0GCSqGSIb3DQEBBQUAMIGMMQswCQYDVQQGEwJJ
.
.
.
pSLqw/PmSLSmUNIr8yQnhy4=
-----END CERTIFICATE-----
-----BEGIN RSA PRIVATE KEY-----
WW91J3JlIGtpZGRpbmchISEKSSBkb24ndCBzaG93IHlvdSBvdXIgcHJpdmF0ZSBr
.
.
.
ZXkhISEhCkNyZWF0ZSB5b3VyIG93biA7KSA7KSA7KQo=
-----END RSA PRIVATE KEY-----
-----BEGIN CERTIFICATE-----
MIIHyTCCBbGgAwIBAgIBATANBgkqhkiG9w0BAQUFADB9MQswCQYDVQQGEwJJTDEW
.
.
.
xV/stleh
-----END CERTIFICATE-----

对于 Tigase 服务器以及许多其他服务器(Apache 2.x),顺序如下;您的域证书,您的私钥,颁发证书的机构,根证书。

备注

Tigase 需要 PEM 文件中的完整证书链(如上所述)!不同的应用程序可能需要具有不同顺序的证书和私钥的 pem 文件。因此,Web 服务器或电子邮件服务器等其他服务不一定会使用相同的文件。目前,Tigase 可以在加载 PEM 文件时自动对证书进行排序。

将证书安装/加载到 Tigase 服务器

安装和加载证书非常容易。服务器可以直接从 pem 文件加载所有证书。您只需为每个虚拟域创建一个单独的 pem 文件,并将该文件放在服务器可访问的目录中。 Tigase 服务器可以自动加载在给定目录中找到的所有 pem 文件。默认情况下,为了方便起见,我们推荐使用 Tigase/certs 目录。

也可以使用:* Admin ad-hoc 命令通过 XMPP 客户端 - 您应该访问到服务器的服务发现并在 VHost Manager 组件的命令列表中选择 Add SSL Certificate,然后按照说明* Admin WebUI - 打开 http://<host>/admin,访问 Other``类别并在其中选择 ``Add SSL Certificate,然后按照说明* REST API -使用包含您的证书的有效负载向 http://localhost:8080/rest/adhoc/vhost-man@domain.com 发出 POST 请求;为获取所需的表单字段,请向同一端点发出 GET 请求

来自其他提供商的证书

有许多证书提供商免费或有偿提供证书。您可以使用其中的任何一个,但是您必须注意,有时证书可能无法被所有 XMPP 服务器识别,特别是如果它是来自新提供商的证书。以下是提供商的示例列表:

  • LetsEncrypt - 有关详细信息,请参阅 在 Linux 系统中安装 LetsEncrypt 证书

  • CAcert - 带有 Web GUI 的免费证书。(警告:它没有被广泛接受)

  • Verisign - 与上述提供的证书相比,此证书非常昂贵,但此证书的提供者得到了所有人的认可。如果您拥有来自 Verisign 的证书,则可以确定此为有效证书。

  • Comodo 证书颁发机构 提供不同类型的商业证书

要从第三方机构获取证书,您必须访问其网站并使用上面生成的证书请求来请求证书。我无法为此提供任何说明,因为列出的每个提供商都有不同的要求和接口。

我们 强烈 建议使用 LetsEncrypt 密钥进行自签名并保护您的域。说明在 下一节

对多个域使用一个证书

备注

Tigase 尝试变得 智能,并自动检测通配符域和备用域,因此无需在多个文件中复制相同的证书以匹配域 - 相同的文件将被加载并使其可用于证书中可用的所有域 (CNames)。

8.4.2. 在 Linux 系统中安装 LetsEncrypt 证书

LetsEncrypt 是一个可信任的 CA,提供免费的安全证书。与以前的自签名证书不同,我们可以使用 LetsEncrypt 证书从受信任的来源认证您的域。

请参考官方 certbot用户指南 了解如何安装和操作该工具,选择所需的域认证方法(DNS或网络服务器)。成功执行后,所有相关文件的证书将存储在 /etc/letsencrypt/live/$domain

$ sudo ls  /etc/letsencrypt/live/$domain
cert.pem  chain.pem  fullchain.pem  privkey.pem  README

在该目录中,您将找到四个文件:

  • privkey.pem - 证书的私钥

  • cert.pem - 本身包含服务器证书

  • chain.pem - 包含额外的中间证书或证书

  • fullchain.pem - 所有证书,包括服务器证书(又名叶子证书或最终实体证书)。服务器证书是此文件中的第一个证书,然后是任何中间证书。

对于 Tigase XMPP 服务器,我们只关心 privkey.pemfullchain.pem (或 chain.pem - 请考虑实际的颁发者和认证链!)。

此时我们需要获取根证书和中间证书,这可以通过从 LetsEncrypt Chain of Trust website 下载这些证书来完成。

备注

请高度关注实际的证书颁发者,并确保维护证书链!

在撰写本文时,LetsEncrypt 提供由 R3 CertificateAuthorigy (CA) 颁发的域证书。为了向根 CA 提供完整的链,您应该获得 Let’s Encrypt R3 (RSA 2048, O = Let's Encrypt, CN = R3) 证书。根据所需的证书链,您有两个选择:1)(默认和推荐)使用自己的 LetsEncrypt CA:a)由 ISRG 根 X1 签名的 R3 证书:https://letsencrypt.org/certs/lets-encrypt-r3.pem b) ISRG Root X1 根证书:https://letsencrypt.org/certs/isrgrootx1.pem 2)(旧版,与旧系统更兼容的选项):IdenTrust 的交叉签名证书:a)由 IdenTrust 交叉签名的 R3 证书:https://letsencrypt.org/certs/lets-encrypt-r3-cross-signed.pem b) 来自 IdenTrust 的 TrustID X3 Roothttps://letsencrypt.org/certs/trustid-x3-root.pem.txt

考虑到第一个(推荐)选项,您可以使用 wget 获取它们:

wget https://letsencrypt.org/certs/isrgrootx1.pem
wget https://letsencrypt.org/certs/lets-encrypt-r3.pem

这些是根证书,以及由根证书签名的中间证书。

备注

IdenTrust 交叉签名证书以后将无法正常运行!

获取您的 privkey.pem 证书的内容,并将它们与 isrgrootx1.pemlets-encrypt-r3.pem 的内容组合成一个单独的pem证书。

根据您的配置,您或者需要在您的域之后命名文件,例如 mydomain.com.pem 并将其放在 Tigase XMPP 服务器安装的 certs/ 子目录下,或者使用管理员 ad-hoc 更新它(请参阅 存储和管理证书)

如果您将所有证书移动到单个目录,您可以在 *nix 操作系统下使用以下命令将它们组合起来:

cat ./cert.pem ./privkey.pem ./lets-encrypt-r3.pem ./isrgrootx1.pem > mydomain.com.pem

备注

如果你使用的是 isrgrootx1 根确保你使用 cert.pem 文件而不是 fullchain.pem,若使用不同的中间证书(Let’s Encrypt Authority X3 (IdenTrust cross-signed) ),你将不得不使用 DST Root CA X3 证书!

您的证书应如下所示:

警告

LetsEncrypt 证书在颁发后 90 天到期,需要更新才能保持有效!

您可以使用实用程序类检查您的证书:

java -cp <path_to_tigase-server_installation>/jars/tigase-utils.jar tigase.cert.CertificateUtil -lc mydomain.com.pem -simple

让我们加密和DNS验证

获得通配符(*.domain.com)证书的唯一方法是通过 DNS 验证。 Certbot 支持许多 DNS 运营商 - 您可以通过执行 $ certbot plugins 来检查您的 DNS 提供商是否在列表中

AWS Route53

如果您想将它与 Amazon Cloud 一起使用,您应该为 AWS 安装插件:

pip install certbot-dns-route53

备注

如果您在 macOS 下使用 certbot 并通过 brew 安装它,那么您应该使用:$( brew --prefix certbot )/libexec/bin/pip install certbot-dns-route53

您应该将您的凭据存储在 ~/.aws/credentials 中(您可能希望创建用于更新 DNS 的专用策略,如 plugin’s documentation 所描述:

[default]
aws_access_key_id = <key_id>
aws_secret_access_key = <key>

之后你应该使用 --dns-route53 参数执行 certbot

Certbot 更新钩子和 Tigase API

为了实现更高的自动化,可以自动更新通过 Tigase XMPP 服务器中的 certbot 获得的证书。您应该使用以下部署挂钩 - 或将其添加到 /etc/letsencrypt/renewal-hooks/deploy/ 或直接在带有 --deploy-hook 参数的 certboot 命令行中使用它(在后一种情况下,它将被添加到特定的域配置中,因此没有必要指定 UPDATE_DOMAINS)。

备注

请调整用于部署的帐户凭据(USER, PASS, DOMAIN)以及 Let’s Encrypt 证书的路径(ISRG Root X1 名为 isrgrootx1.pemLet’s Encrypt Authority X3 名为 letsencryptauthorityx3.pem

#!/bin/bash

set -e

## Configuration START

USER="admin_username"
PASS="admin_password"
DOMAIN="my_domain.tld"
HOST=${DOMAIN}
#UPDATE_DOMAINS=(${DOMAIN})
# PORT=":8080"
# APIKEY="?api-key=mySecretKey"
LE_CERTS_PATH="/path/to/letsencrypt/CA/certificates/"

## Configuration END

fail_count=0

for domain in ${RENEWED_DOMAINS[@]}; do
    if [[ $domain == "*."* ]]; then
        CERT_DOMAIN=${domain#*\*.}
    else
        CERT_DOMAIN=${domain}
    fi

    if [[ ! -z "${UPDATE_DOMAINS}" ]] ; then
        match=0
        for dn in "${UPDATE_DOMAINS[@]}"; do
            if [[ $dn = "$CERT_DOMAIN" ]]; then
                match=1
                break
            fi
        done
        if [[ $match = 0 ]]; then
            echo "Skipping updating ${domain} because it's not in the list of supported domains: ${UPDATE_DOMAINS[@]}"
            continue
        fi
    fi

    CERT=`cat "$RENEWED_LINEAGE/cert.pem" "$RENEWED_LINEAGE/privkey.pem" ${LE_CERTS_PATH}/isrgrootx1.pem ${LE_CERTS_PATH}/letsencryptauthorityx3.pem`

    REQUEST="
    <command>
      <node>ssl-certificate-add</node>
      <fields>
        <item>
          <var>Certificate in PEM format</var>
          <value>${CERT}</value>
        </item>
        <item>
          <var>command-marker</var>
          <value>command-marker</value>
        </item>
        <item>
          <var>VHost</var>
          <value>${CERT_DOMAIN}</value>
        </item>
        <item>
          <var>Save to disk</var>
          <value>true</value>
        </item>
      </fields>
    </command>"

    response=`curl -s -L -H "Content-Type: text/xml" -X POST  http://${USER}%40${DOMAIN}:${PASS}@${HOST}${PORT}/rest/adhoc/vhost-man@${DOMAIN}${APIKEY} -d "${REQUEST}"`

    if [[ ! ${response} = *"loaded successfully"* ]] ; then
        echo -e "Server returned error while updating   ${domain}   certificate:\n ${response}"
        fail_count=$((${fail_count}+1))
    else
        echo "Correctly updated ${domain} certificate"
    fi
done

exit ${fail_count}

备注

如果您没有使用通配符证书,则必须为主域提供证书以及为要公开的所有组件(muc, pubsub, push 等)的子域提供证书

8.4.3. 存储和管理证书

文件系统

默认情况下,Tigase 在 certs/ 子目录中加载和存储证书。每个 domain 证书都应该存储在一个文件中,此文件名由域名和 .pem 扩展名组成,即 <domain>.pem。例如对于域 tigase.net,它将是 certs/tigase.net.pem

备注

Tigase 尝试变得 智能,并自动检测通配符域和备用域,因此无需在多个文件中复制相同的证书来匹配域。

数据库存储库

或者,可以使用数据库作为证书的存储。启用它后,证书将不会被读取或存储到文件系统中。您可以通过将 repository () {} bean 添加到 TDSL 配置文件中的 'certificate-container' () {} 来启用它:

'certificate-container' () {
    repository () {}
}

如果您使用的是数据库存储库,那么您可以使用来自 VHost Manager 的临时命令 Add SSL certificate 或通过 HTTP REST API 来管理/更新证书。

8.5. 自定义身份验证连接器

本文介绍了管理员可用的配置选项,并描述了如何设置 Tigase 服务器以使用来自不同数据库的用户帐户数据。

首先要知道的是 Tigase 服务器总是打开 2 个独立的数据库连接。一个连接用于用户登录数据,另一个用于所有其他用户数据,如用户名册、vCard、私人数据存储、隐私列表等……​

在本文中,我们仍然假设 Tigase 服务器将用户数据保存在自己的数据库中,并且仅从外部数据库中检索登录数据。

目前 Tigase 提供以下身份验证连接器:

  • mysql, pgsql, derby - 标准身份验证连接器,其用于从 Tigase 服务器使用的主用户数据库加载用户登录数据。实际上,所有 JDBC 数据库都使用相同的物理实现。

  • drupal - 是用于将 Tigase 服务器与 Drupal CMS 集成的身份验证连接器。

  • tigase-custom - 是可用于任何数据库的身份验证连接器。与 ‘tigase-auth’ 连接器不同,它允许您在配置文件中定义 SQL 查询。这种实现的优点是您不必接触数据库。您可以使用简单的普通 SQL 查询或存储过程。此时配置更加困难,因为您必须在配置文件中仔细输入所有 SQL 查询,并且更改查询通常涉及重新启动服务器。有关此实现和所有配置参数的更多详细信息,请参阅 Tigase 自定义身份验证文档

  • tigase-auth (DEPRECATED) - 是可用于任何数据库的身份验证连接器。它执行存储过程以执行所有操作。因此,如果您不想暴露数据库结构,将服务器与外部数据库集成是一种非常方便的方法。您只需在数据库中提供一组存储过程。虽然实现服务器预期的所有存储过程可能需要做一些工作,但它允许您隐藏数据库结构并随时更改 SP 实现。您可以在用户登录/注销时添加更多操作而无需重新启动或触摸服务器。并且服务器端的配置非常简单。有关此实现的详细说明,请参阅 Tigase Auth 文档

与往常一样,配置服务器的最简单方法是通过 config.tdsl 文件。在描述此文件的文章中,您可以找到包含所有可用选项的长列表以及如何处理它的所有详细信息。但是,对于身份验证连接器设置,我们只需要 2 个选项:

dataSource {
    'default-auth' () {
        uri = 'database connection url'
    }
}
authRepository {
    default () {
        cls = 'connector'
        'data-source' = 'default-auth'
    }
}

例如,如果您将身份验证数据存储在 localhost 上的 drupal 数据库中,您的设置将是:

dataSource {
    'default-auth' () {
        uri = 'jdbc:mysql://localhost/drupal?user=user&password=passwd'
    }
}
authRepository {
    default () {
        'data-source' = 'default-auth'
    }
}

如果要附加自己的身份验证连接器,则必须使用类名。

默认为:

authRepository {
    default {
        cls = 'tigase.db.jdbc.TigaseAuth'
    }
}

以同样的方式,您可以为任何不同的数据库类型设置连接器。

例如,drupal 配置如下

authRepository {
    default {
        cls = 'tigase.db.jdbc.DrupalWPAuth'
    }
}

或 tigase-custom 身份验证连接器。

authRepository {
    default {
        cls = 'tigase.db.jdbc.TigaseCustomAuth'
    }
}

不同的 cls 或类是:

  • Drupal - tigase.db.jdbc.DrupalWPAuth

  • MySQL, Derby, PostgreSQL, MS SQL Server - tigase.db.jdbc.JDBCRepository

您通常可以跳过默认 Tigase 数据库格式的配置连接器:mysql, pgsqlderby, sqlserver ,因为如果缺少参数,它们会自动应用。

要知道的另一件重要的事情是,如果您使用自定义身份验证连接器,则必须修改 authRepository 。这是因为如果您从外部数据库检索用户登录数据,该外部数据库通常由外部系统管理。用户帐户在不通知 Tigase 服务器的情况下被添加。然后,当用户登录并尝试检索用户名册时,服务器在名册数据库中找不到这样的用户。

重要

要使用户帐户在身份验证数据库和主用户数据库之间保持同步,您必须在数据库连接 URL 的末尾添加以下选项:autoCreateUser=true

例如:

dataSource {
    default () {
        uri = 'jdbc:mysql://localhost/tigasedb?user=nobody&password=pass&autoCreateUser=true'
    }
}

如果您有兴趣通过编写自己的查询或存储过程来进一步自定义身份验证连接器,请查看以下指南:

8.5.1. Tigase 身份验证连接器(已弃用)

快捷方式名为 tigase-auth 的 Tigase Auth 连接器在类中实现:tigase.db.jdbc.TigaseAuth 。它允许您连接到任何外部数据库以执行用户身份验证。您可以在 Custom Authentication Connectors 指南中找到如何设置自定义连接器的更多详细信息。

要使此连接器正常工作,您必须准备数据库以提供一组存储过程供 Tigase 服务器执行所有身份验证操作。最好的描述是定义了所有存储过程的示例模式 - 请参阅 Tigase 存储库以获取模式定义文件(每个组件都有其专用的模式)。例如:

您必须实现的存储过程的绝对最小值是:

  • TigUserLoginPlainPw - 执行用户身份验证。当用户尝试登录 XMPP 服务器时,总是会调用该程序。这是唯一必须实施并且必须切实可行的程序。

  • TigUserLogout - 执行用户注销。当用户注销或与服务器断开连接时,始终调用该程序。这个程序必须执行,但它可以是空的并且什么也不做。它只需要存在,因为 Tigase 期望它存在并尝试调用它。

使用上述 2 个存储程序,您只能在外部数据库上执行用户登录/注销。您不能注册用户帐户,更改用户密码或删除用户。在许多情况下,这是可以的,因为所有用户管理都由外部系统处理。

但是,如果您想允许通过 XMPP 进行帐户管理,您还必须执行以下程序:

  • TigAddUserPlainPw - 添加新用户帐户

  • TigRemoveUser - 删除现有用户帐户

  • TigUpdatePasswordPlainPw - 更改现有帐户的用户密码

8.5.2. Tigase 自定义身份验证连接器

具有快捷方式名称的 Tigase 自定义身份验证连接器:tigase-custom 在类中实现:tigase.db.jdbc.TigaseCustomAuth。它允许您连接到任何外部数据库来执行用户身份验证并对所有操作使用自定义查询。

您可以在自定义身份验证连接器指南中找到有关如何设置自定义连接器的更多详细信息。

基本配置非常简单:

authRepository {
    default () {
        cls = 'tigase.db.jdbc.TigaseCustomAuth'
        'data-source' = 'default-auth'
    }
}

就这些

连接器正确加载并使用预定义的默认查询列表开始工作。在大多数情况下,您可能还想在配置文件中定义自己的查询。最短的可能描述是来自 config.tdsl 文件中的以下内容示例:

此查询用于检查与数据库的连接是否还持活

authRepository {
    default () {
        'conn-valid-query' = 'select 1'
    }
}

这是数据库初始化查询,一般我们不用,尤其是集群环境

authRepository {
    default () {
        'init-db-query' = 'update tig_users set online_status = 0'
    }
}

备注

online_status 列不存在,需要添加该查询才能工作。

下面的查询在数据库级别执行用户身份验证。 Tigase 服务器不需要知道身份验证算法或密码编码类型,它只需将从客户端接收到的用户 ID (BareJID) 和密码传递给存储过程。如果身份验证成功,则该过程返回用户裸 JID,否则返回 null。 Tigase 检查从查询返回的 JID 是否与作为参数传递的 JID 匹配。如果它们匹配,则认证成功。

authRepository {
    default () {
        'user-login-query' = '{ call TigUserLoginPlainPw(?, ?) }'
    }
}

备注

TigUserLoginPlainPw 不再是 Tigase XMPP 服务器数据库模式的一部分,需要创建。

下面的查询返回数据库中用户帐户的数量,这主要用于服务器指标和监控组件。

authRepository {
    default () {
      'users-count-query' = '{ call TigAllUsersCount() }'
    }
}

下面的查询用于向数据库添加新的用户帐户。

authRepository {
    default () {
        'add-user-query' = '{call TigAddUserPlainPw(?, ?) }'
    }
}

下面的查询用于从数据库中删除包含所有用户数据的现有帐户。

authRepository {
    default () {
        'del-user-query' = '{ call TigRemoveUser(?) }'
    }
}

如果未定义 user-login-query,则此查询用于用户身份验证,即没有可用的数据库级用户身份验证算法。在这种情况下,Tigase 服务器从数据库中加载用户密码,并将其与从客户端接收到的数据进行比较。

authRepository {
    default () {
        'get-password-query' = 'select user_pw from tig_users where user_id = ?'
    }
}

以下查询用于用户密码更新,以防用户决定更改密码。

authRepository {
    default () {
        'update-password-query' = 'update tig_users set user_pw = ? where user_id = ?'
    }
}

此查询在用户注销时被调用。通常我们使用一个存储过程来记录用户注销时间并在数据库中将用户标记为离线。

authRepository {
    default () {
        'update-logout-query' = 'update tig_users, set online_status = online_status - 1 where user_id = ?'
    }
}

备注

online_status 列不存在,需要添加该查询才能工作。

此配置指定向客户端公开哪些非 SASL 身份验证机制

authRepository {
    default () {
        'non-sasl-mechs' = [ 'password', 'digest' ]
    }
}

此设置指定向客户端公开哪些 sasl 身份验证机制

authRepository {
    default () {
        'sasl-mechs' = 'PLAIN,DIGEST-MD5'
    }
}

查询在配置文件中定义,它们可以是普通的 SQL 查询或存储过程。如果查询以字符 { call 开头, 则服务器假定这是一个存储过程的调用,否则它作为普通 SQL 查询执行。在处理之前,每个配置值都从两端的白色字符中去除。

请不要在查询末尾使用分号 ;,因为许多 JDBC 驱动程序会混淆,查询可能无法正常工作。

一些查询可以带参数。参数在查询中用问号 ? 标记。有关每个查询中预期的参数的更多详细信息,请参阅配置参数说明。

此示例说明如何使用存储过程将用户添加为具有 2 个必需参数(用户名和密码)的查询。

authRepository {
    default () {
        'add-user-query' = '{call TigAddUserPlainPw(?, ?) }'
    }
}

使用普通 SQL 参数的相同查询:

'add-user-query' = 'insert into users (user_id, password) values (?, ?)'

查询参数的顺序很重要,并且必须与每个参数的规范中描述的完全相同。

查询名称

描述

参数

示例查询

conn-valid-query

定期执行查询以确保与数据库保持连接。

不接受任何参数。

select 1

init-db-query

服务器启动后运行的数据库初始化查询。

不接受任何参数。

update tig_users set online_status = 0

add-user-query

向数据库添加新用户查询。

接受 2 个参数: (user_id (JID), password)

insert into tig_users (user_id, user_pw) values (?, ?)

del-user-query

从数据库中删除用户。

接受 1 个参数: (user_id (JID))

delete from tig_users where user_id = ?

get-password-query

从数据库中找回给定 user_id (JID) 的用户密码。

接受 1 个参数: (user_id (JID))

select user_pw from tig_users where user_id = ?

update-password-query

更新(更改)给定 user_id (JID) 的密码。

接受 2 个参数: (password, user_id (JID))

update tig_users set user_pw = ? where user_id = ?

user-login-query

执行用户登录。通常在有用于此目的的特殊 SP 时使用。这是需要找回用户密码的替代方法。因此,必须至少定义其中一个查询:user-login-queryget-password-query。如果定义了两个查询,则使用 user-login-query。通常,此方法应仅与纯文本密码身份验证或 sasl-plain 一起使用。如果登录成功,Tigase 期望从查询返回一个带有 user_id 的结果集,如果登录不成功,则返回空结果集。

接受 2 个参数: (user_id (JID), password)

select user_id from tig_users where (user_id = ?) AND (user_pw = ?)

user-logout-query

当用户注销或断开连接时调用此查询。它可以在数据库中记录该事件。

接受 1 个参数: (user_id (JID))

update tig_users, set online_status = online_status - 1 where user_id = ?

non-sasl-mechs

逗号分隔的非 SASL 身份验证机制列表。可能的机制是:passworddigest。摘要机制只能在 get-password-query 激活且密码以纯文本格式存储在数据库中时起作用。

sasl-mechs

逗号分隔的 SASL 身份验证机制列表。可能的机制都是 Java 实现支持的机制。最常见的是:PLAIN, DIGEST-MD5, CRAM-MD5。”Non-PLAIN” 机制仅在 get-password-query 激活且密码以纯文本格式存储在数据库中时才有效。

8.5.3. Drupal 身份验证

目前,我们目前只能针对 Drupal 数据库检查身份验证。完整的 Drupal 身份验证尚未被实现。

由于 Drupal 将加密密码保存在数据库中,唯一可能的授权协议是那些基于 PLAIN 密码的协议。

为了保护您的密码 Tigase 服务器必须使用 SSL 或 TLS 加密。

Drupal 基于数据库的授权的实现位于 tigase.db.jdbc.DrupalAuth 类中。尽管此类能够向存储库添加新用户,但由于 Drupal 中的缓存问题,我建议关闭带内注册。数据库中的更改尚未与 Drupal 同步。添加新用户的功能仅用于简化从早期 Tigase 服务器安装的不同存储库类型迁移用户帐户。

该实现的目的是允许来自 Drupal 的所有帐户管理任务,例如:帐户创建,所有帐户设置,比如电子邮件,全名,密码更改等。

Tigase 服务器使用来自 Drupal 数据库的以下字段:name(用户帐户名),pass(用户帐户密码),status(帐户状态)。服务器立即获取所有更改。如果用户状态不是 1,那么即使用户提供了有效的密码,服务器也不会允许用户通过 XMPP 登录。

Drupal 中还没有 Roster 管理。所以名册管理必须从 XMPP 客户端完成。

8.5.4. LDAP 身份验证连接器

Tigase XMPP 服务器支持在 Bind Authentication 模式下针对 LDAP 服务器对用户进行身份验证。

LDAP 支持的配置非常简单,您只需在 config.tdsl 文件中添加几行即可。

authRepository {
    default () {
        cls = 'tigase.db.ldap.LdapAuthProvider'
        uri = 'ldap://ldap.tigase.com:389'
        'user-dn-pattern' = 'cn=USER_ID,ou=people,dc=tigase,dc=org'
    }
}

请注意 USER_ID 元素,这是用于验证特定用户配置的特殊元素。 Tigase LDAP 连接器在身份验证期间将其替换为适当的数据。您可以控制 Tigase 应该在这部分中添加什么内容。在您的配置中,您必须将此字符串替换为以下之一:

  1. %1$s - 仅使用用户名进行身份验证(JabberID 的本地部分)

  2. %2$s - 仅使用域名进行身份验证(JabberID 的域部分)

  3. %3$s - 使用整个 Jabber ID (JID) 进行身份验证

重要

请确保您在主数据源(UserRepository 和 不是 以上 AuthRepository)中包含 autoCreateUser=true,如 [autoCreateUser] - 否则您可能会遇到数据访问问题。

8.5.5. SASL 外部配置

为了启用 SASL 外部设置 “Client Certificate CA” (client-trust-extension-ca-cert-path) 到包含 VHost(域)配置中的证书颁发机构 (CA) 证书的路径,例如 /path/to/cacert.pem

文件 cacert.pem 包含用于签署客户端证书的证书颁发机构证书。

客户端证书必须在 subjectAltName 中包含用户作为 XmppAddr 的 Jabber ID :

正如 RFC 3920 中指定和在 RFC 6120 中更新的那样,在流协商过程中,XMPP 客户端可以提供证书(“client certificate”)。如果 JabberID 包含在客户端证书中,则将其封装为 id-on-xmppAddr 对象标识符(“xmppAddr”),即 otherName 类型的 subjectAltName 条目,其 ASN.1 对象标识符为“id-on-xmppAddr”,正如 RFC 6120 的第 13.7.1.4 节,XEP-0178 中所述。

可以使制作客户端证书 必需 使用相同的 VHost 配置并启用选项 Client Certificate Required (client-trust-extension-cert-required)。

如果启用此选项,则客户端 必须提供 证书。该证书将根据 clientCertCA 进行验证。如果客户端不提供证书或证书无效,TLS 握手将被中断并将客户端连接断开

使用此选项不会强制客户端使用 SASL EXTERNAL。客户端仍然可以使用其他 SASL 机制进行身份验证。

8.6. SASL 机制

XMPP 协议支持多种身份验证方式,但大多用作 SASL 机制。 Tigase XMPP Server 提供了许多基于 SASL 的身份验证机制,例如:

  • PLAIN (启用)

  • ANONYMOUS

  • EXTERNAL

  • SCRAM-SHA-1 (启用)

  • SCRAM-SHA-256 (启用)

  • SCRAM-SHA-512

它们中的大多数在默认的 Tigase XMPP 服务器安装中默认启用。

8.6.1. 启用和禁用 SASL 机制(凭证编码器/解码器)

如果您想启用或禁用基于密码的身份验证机制之一,例如 SCRAM-SHA-1, SCRAM-SHA-256SCRAM-SHA-512,您可以通过启用或禁用安装中使用的编码器和解码器。通过启用编码器/解码器,您可以决定密码以何种形式存储在数据库中。这些更改可能(并且在大多数情况下)会影响哪些 SASL 机制允许在您的安装中使用。

备注

在大多数情况下,您应该同时启用或禁用这两种相同类型(凭证编码器和解码器)。此规则的唯一例外是当您更改那些已经工作的安装时。在这种情况下,您应该只启用您想要启用的类型的编码器并要求用户更改他们的密码。在用户更改密码后,您应该重新配置服务器以启用特定类型的解码器。 (在其他情况下,用户可能无法登录到您的安装,因为系统将拒绝他们的凭据,因为它可能没有与特定 SASL 机制匹配的凭据)

启用 SCRAM-SHA-512 编码器

authRepository () {
    default () {
        credentialEncoders () {
            'SCRAM-SHA-512' () {}
        }
    }
}

禁用 SCRAM-SHA-1 解码器

authRepository () {
    default () {
        credentialDecoders () {
            'SCRAM-SHA-1' (active: false) {}
        }
    }
}

警告

如果您启用了相同类型的解码器,强烈建议不要禁用编码器,因为如果客户端尝试使用不可用的机制,可能会导致身份验证问题。

8.7. 应用程序密码

在最新版本的 Tigase XMPP 服务器中,可以创建和使用多个用户名和密码对来授权连接到单个 XMPP 帐户。

有了这个,现在可以为访问同一帐户的多个客户端设置多个密码,这可用于提高帐户的安全性,因为即使一个密码被泄露,您仍然可以登录并阻止丢失或受损的设备。

8.7.1. 添加应用程序密码

要添加新的用户名-密码对,您需要在登录XMPP 帐户并为其添加新应用程序密码时执行 Add user credentials 临时命令( sess-man 的命令节点 auth-credentials-delete)。

在执行命令期间,您将获得一个表格,用于填写以下字段:

  • 帐户的 Jabber ID (jid) - 您帐户的裸 JID

  • 凭据 ID (credentialId) - 新应用程序密码的用户名

  • 密码 (password) - 新密码

提交此表格后,将添加新的凭据。

8.7.2. 使用应用程序密码登录

要使用新密码登录,XMPP 客户端可以使用任何 SASL 机制,但需要提供(在 SASL 消息中):

  • authzid - 帐号 JID

  • authcid - 应用程序密码的用户名

  • passwd - 申请密码

使用正确的值,您的应用程序将能够用应用程序密码登录。

8.7.3. 删除应用程序密码

如果您的设备被盗用或丢失并且您想删除应用程序密码,您需要使用其他不同设备并登录您的 XMPP 帐户。然后你需要执行 Delete user credentials 临时命令(sess-man 的命令节点 auth-credentials-delete)。

在执行命令期间,您将获得一个表格,用于填写以下字段:

  • 帐户的 Jabber ID (jid) - 您帐户的裸 JID

  • 凭据 ID (credentialId) - 要删除的应用程序密码的用户名

提交此表格后,证书将被删除。

8.8. 包过滤

Tigase 提供了不同的方法来过滤通过服务器的 XMPP 数据包。包过滤最常见的用途是根据发送者或接收地址限制用户发送或接收数据包。

还有不同的可能场景:基于时间的过滤,内容过滤,音量过滤等。

本节中的所有页面都描述了不同的过滤策略。

8.8.1. 基于域的包过滤

基于域的数据包过滤是一个简单的过滤器,其允许根据源/目标域名限制用户通信。如果我们希望仅在单个自己的域或域列表中限制用户通信,这将特别有用。

公司可能不希望雇主在工作时间与世界上任何人聊天。一家公司也可能有几个不同的域被不同的分支机构或部门使用。管理员可以将通信限制为域列表。

介绍

限制是基于每个用户的。因此管理员可以为每个用户设置不同的过滤规则。还有一个按域配置和全局安装设置(从最一般到最具体的应用,即从安装到用户)。

普通用户无法更改设置。所以这不像用户控制过滤器的隐私列表。域过滤器不能由用户更改或控制。系统管理员可以根据公司政策更改设置。

包过滤有预定义的规则:

  1. ALL - 用户可以发送和接收来自任何人的数据包。

  2. LOCAL - 用户只能在服务器安装及其所有虚拟域内发送和接收数据包。

  3. OWN - 用户只能在自己的域内发送和接收数据包

  4. BLOCK - 用户无法与任何人交流。这可以用作暂时禁用帐户或域的一种手段。

  5. LIST - 用户只能在列出的域内发送和接收数据包(即 白名单)。

  6. BLACKLIST - 用户可以与所有人(如 ALL)通信,除了列出域上的联系人。

  7. CUSTOM - 用户只能在自定义创建的规则集中进行通信。

白名单 ( LIST) 和黑名单 ( BLACKLIST) 设置是互斥的,即在任何给定时间点,只能使用其中一个。

那些适用于特定用户的规则存储在用户存储库中,并为每个用户会话加载。如果没有为特定用户存储规则,则服务器尝试为特定用户的 VHost 应用规则,并且如果没有 VHost 过滤策略,服务器使用全局服务器配置。如果完全没有过滤策略,服务器将根据以下条件应用默认值:

  1. 如果这是 Anonymous 用户,则应用 LOCAL 规则

  2. 对于所有 other 用户,应用 ALL 规则。

配置

过滤由必须在启动时加载的域过滤器插件执行。如果配置文件中未设置插件列表,则默认加载。但是,如果您在配置文件中有加载插件的列表,请确保 domain-filter 在列表中。

该插件无需其他配置即可工作。

行政,规则管理

尽管可以为每个用户单独控制域过滤规则,但对于大型安装来说并不实用。在大多数情况下,用户存储在数据库中,第三方系统保存所有用户信息。

要更改单个用户的规则,您可以使用可加载的管理脚本功能并加载 UserDomainFilter.groovy 脚本。它可以修改给定用户 JID 的规则。

执行

如果您有一个保存和管理所有用户信息的第三方系统,那么您可能拥有自己的 UserRepository 实现,它允许 Tigase 服务器访问用户数据。使用以下命令从用户存储库加载过滤规则:

repo.getData(user_id, null, DomainFilter.ALLOWED_DOMAINS_KEY, null);
repo.getData(user_id, null, DomainFilter.ALLOWED_DOMAINS_LIST_KEY, null);

其中 user_id 是没有资源部分的用户 Jabber ID,DomainFilter.ALLOWED_DOMAINS_KEY 是属性键:allowed-domains。用户存储库必须仅返回以下之一:

  1. ALL - 如果允许用户与任何人通信

  2. LOCAL - 如果允许用户与同一服务器安装上的用户进行通信。

  3. OWN - 如果只允许用户与他自己域内的用户进行通信。

  4. LIST - 允许用户与其他用户通信的域列表。不支持通配符。用户自己的域也应该包括在内。

  5. BLACKLIST - 不允许用户与其他用户通信的域列表。不支持通配符。不应包含用户自己的域。

  6. CUSTOM - 定义自定义通信权限的规则列表(服务器根据第一个匹配的规则处理节,类似于 XEP-0016),格式如下:

ruleSet = rule1;rule2;ruleX;

rule = order_number|policy|UID_type[|UID]

order_number = any integer;
policy = (allow|deny);
UID_type = [jid|domain|all];
UID = user JID or domain, for example pubsub@test.com; if UID_type is ALL then this is ignored.

例如:

1|allow|self;
2|allow|jid|admin@test2.com;
3|allow|jid|pubsub@test.com;
4|deny|all;
  1. null - 如果用户没有设置,则返回 java null。

LISTBLACKLIST 过滤选项的情况下,为白名单/黑名单提供域列表是必不可少的。 DomainFilter.ALLOWED_DOMAINS_LIST_KEY 是一个属性键:“allowed-domains-list”。用户存储库必须返回分号分隔的域列表:domain1.com;domain2.com,domain3.org

过滤由 tigase.xmpp.impl.DomainFilter 插件实现。更多实现细节请参考源代码。

8.9. Tigase 中的访问控制列表

Tigase 提供对 访问控制列表 (ACL) 的支持,以允许对服务器上的管理命令进行细粒度访问。

默认情况下,所有管理命令只能由服务管理员访问(通过服务发现可见并且可以执行)。服务管理员是在 admins = [] 下的 config.tdsl 文件中列出的具有 JID (BareJIDs) 的现有帐户(有关详细信息,请参阅 admins)。

此外,可以为其他 XMPP 用户和实体分配权限以使用 Tigase 的 ACL 功能执行一个或多个命令。

以下是管理员命令可访问的可能的 ACL 修饰符列表:

  • ALL - 每个人都可以执行该命令,即使是来自不同联合服务器的用户。

  • ADMIN - 本地服务器管理员可以执行命令,如果没有为命令设置 ACL,此为默认设置。

  • LOCAL - 在本地服务器上拥有帐户的所有用户都可以执行该命令。来自其他联合服务器的用户将无法执行该命令。

  • NONE - 不允许任何人执行此命令

  • DOMAIN_OWNER - 只有作为正在操作项目的域的所有者的用户才被允许执行评论。如果脚本没有检查被操作项的权限,则此值的行为方式与 LOCAL 相同。

  • DOMAIN_ADMIN - 只有作为域管理员之一的用户才能执行操作与域相关的项目的命令。如果脚本没有检查被操作项的权限,则此值的行为方式与 LOCAL 相同。

  • example.com - 只有在所选域中拥有帐户的用户才能执行该命令。专门为管理员帐户设置域可能很有用,并且该域中的所有用户都将能够自动运行该命令。

  • user@example.com - 可以执行命令的用户的 JID 的逗号分隔列表。

在任何情况下,无论 ACL 设置如何,任何命令都可以由指定的服务范围管理员执行和访问,即在 config.tdsl 文件中列为管理员的帐户。

多个 ACL 修饰符可以组合并应用于任何命令。这可能并不总是有意义的。例如 ALL 取代所有其他设置,因此将其与任何其他修饰符结合使用是没有意义的。但是,大多数其他修饰符可以与 JID 结合以扩大对特定帐户的访问。

在 Tigase 服务器上,检查访问控制列表中的第一个匹配修饰符。因此,如果您将 ALL 与任何其他修饰符结合使用,则无论添加了哪些其他修饰符,本地或远程服务中的任何人都将始终能够执行该命令。

请注意,ACL 列表在命令框架级别上工作。在实际执行命令之前验证访问。命令本身可能存在其他访问限制。在许多情况下,即使允许所有本地用户执行命令(LOCAL 修饰符),某些命令也只允许由域所有者或域管理员(当然也包括服务范围的管理员)执行。所有与用户管理相关的命令,例如添加新用户,删除用户,更改密码等……都属于此类别。进行域 (vhost) 管理时,任何本地用户都可以创建/注册新域(如果设置了 LOCAL ACL 修饰符),但随后的所有域管理任务,例如删除 vhost、更新其配置、设置 SSL 证书只能由域所有者或管理员完成。

ACL 列表是为特定 Tigase 组件和特定命令设置的。因此配置属性必须指定所有细节。所以为命令配置 ACL 的一般格式是这样的:

comp-id () {
    commands {
        'command-id' = [ 'ACL_modifier', 'ACL_modifier', 'ACL_modifier' ]
    }
}

细分是这样的:

  • comp-id 是 Tigase 服务器组件 ID 如:sess-man、vhost-man、c2s 等。

  • commands 是一个静态文本,以表示该属性用于组件的命令设置。

  • command-id 是我们为其设置 ACL 的命令 ID,例如 query-dns、http://jabber.org/protocol/admin#add-user、user-roster-management 等……

这里有一些例子:

允许本地用户创建和管理自己的域

'vhost-man' () {
    commands {
        'comp-repo-item-add' = 'LOCAL'
        'comp-repo-item-remove' = 'LOCAL'
        'comp-repo-item-update' = 'LOCAL'
        'ssl-certificate-add' = 'LOCAL'
    }
}

事实上,除了 item-add 之外的所有命令都可以由域所有者或管理员执行。

允许本地用户执行用户管理命令:

'sess-man' () {
    'commands' {
        'http://jabber.org/protocol/admin#add-user' = 'LOCAL'
        'http://jabber.org/protocol/admin#change-user-password' = 'LOCAL'
        'http://jabber.org/protocol/admin#delete-user' = 'LOCAL'
        'http://jabber.org/protocol/admin#get-online-users-list' = 'LOCAL'
        'http://jabber.org/protocol/admin#get-registered-user-list' = 'LOCAL'
        'http://jabber.org/protocol/admin#user-stats' = 'LOCAL'
        'http://jabber.org/protocol/admin#get-online-users-list' = 'LOCAL'
    }
}

与前面的示例一样,这些命令将仅由作为特定域管理员的本地用户执行。

允许来自特定域的用户执行 query-dns 以及来自其他域的给定 JID 的其他一些用户:

'vhost-man' () {
    'commands' {
        'query-dns' = [ 'tigase.com', '[email protected]', '[email protected]' ]
    }
}

为了能够设置正确的 ACL 属性,您需要知道组件名称和命令 ID。组件 ID 可以在正在运行的服务器上的服务发现信息或启动期间的服务器日志中找到。可以在命令脚本源代码中找到命令 ID。每个脚本在其代码的开头都包含一个元数据列表。其中之一是 AS:CommandId ,这是您必须用于 ACL 设置的内容。

8.10. TLS/SSL 加密功能配置

Tigase 允许调整在建立 TLS 连接时使用的最重要的参数 - 在连接协商期间将使用的一组协议和密码。最重要的一个是 hardened-mode - 它是最通用的配置,其提供了三步调整设置 - 详情请参阅 hardened-modehardened-mode 可以通过 TDSL 配置文件(在 root 级别或对于特定连接管理器的 sslContextContainer)或 VHost 级别进行配置。

如果你想禁用某些协议或密码,你可以使用两个选项:分别是 tls-disabled-protocolstls-disabled-ciphers。顾名思义,它们允许禁用默认集中的某些项目。他们都接受一个字符串数组,从列表中删除哪十个。

假设您想删除对 SSL, SSLv2SSLv3 协议的支持。您应该简单地使用以下配置:'tls-disabled-protocols' = ['SSL', 'SSLv2', 'SSLv3']。协议的完整列表取决于您使用的特定 Java 版本 - 请参阅文档了解详细信息。例如对于默认的 Java11 列表,您可以查看 SSLContext Algorithms

tls-disabled-ciphers 遵循相同的格式并使用 JSSE Cipher Suite Names 中定义的名称。也可以使用正则表达式来快速消除密码组。

如果您只想启用特定的协议或密码,而不考虑 hardened-mode 或以上禁用选项,您可以使用 tls-enabled-protocolstls-enabled-ciphers - 这两个选项也接受数组,它们将会配置Tigase 以仅使用提供的那些协议或密码(不支持正则表达式)。因此,如果您使用 'tls-enabled-protocols' = [ 'TLSv1.2' ] 配置 Tigase,那么 Tigase 将 支持 TLSv1.2

您可能有兴趣调整的最后一个选项是 ephemeral-key-size - 它遵循 Customizing Size of Ephemeral Diffie-Hellman Keys 中概述的 Java 配置功能 。Tigase 默认 Diffie-Hellman 密钥为 4096 位元。

重要

我们尝试提供最佳的默认选项集,因此 建议使用 Tigase 提供的默认值。如果你想让你的系统非常安全(考虑到安装可能不太安全的连接问题),那么你应该只调整 hardened-mode 设置(并将其切换为 strict)。

8.10.1. 测试主机 TLS 功能

如果您遇到 TLS 连接问题,比较两个安装是否支持相同的协议和密码集会很有帮助。最通用和最有用的工具之一是 Mozilla’s CipherScan。例如,对于我们的安装 tigase.im 结果将如下所示:

$ ./cipherscan --curves -starttls xmpp -servername tigase.im tigase.me:5222
.......................................................................
Target: tigase.me:5222

prio  ciphersuite                  protocols              pfs                 curves
1     ECDHE-RSA-AES256-GCM-SHA384  TLSv1.2                ECDH,B-571,570bits  sect283k1,sect283r1,sect409k1,sect409r1,sect571k1,sect571r1,secp256k1,prime256v1,secp384r1,secp521r1
2     ECDHE-RSA-AES256-SHA384      TLSv1.2                ECDH,B-571,570bits  sect283k1,sect283r1,sect409k1,sect409r1,sect571k1,sect571r1,secp256k1,prime256v1,secp384r1,secp521r1
3     ECDHE-RSA-AES256-SHA         TLSv1,TLSv1.1,TLSv1.2  ECDH,B-571,570bits  sect283k1,sect283r1,sect409k1,sect409r1,sect571k1,sect571r1,secp256k1,prime256v1,secp384r1,secp521r1
4     DHE-RSA-AES256-GCM-SHA384    TLSv1.2                DH,4096bits         None
5     DHE-RSA-AES256-SHA256        TLSv1.2                DH,4096bits         None
6     DHE-RSA-AES256-SHA           TLSv1,TLSv1.1,TLSv1.2  DH,4096bits         None
7     ECDHE-RSA-AES128-GCM-SHA256  TLSv1.2                ECDH,B-571,570bits  sect283k1,sect283r1,sect409k1,sect409r1,sect571k1,sect571r1,secp256k1,prime256v1
8     ECDHE-RSA-AES128-SHA256      TLSv1.2                ECDH,B-571,570bits  sect283k1,sect283r1,sect409k1,sect409r1,sect571k1,sect571r1,secp256k1,prime256v1,secp384r1,secp521r1
9     ECDHE-RSA-AES128-SHA         TLSv1,TLSv1.1,TLSv1.2  ECDH,B-571,570bits  sect283k1,sect283r1,sect409k1,sect409r1,sect571k1,sect571r1,secp256k1,prime256v1,secp384r1,secp521r1
10    DHE-RSA-AES128-GCM-SHA256    TLSv1.2                DH,4096bits         None
11    DHE-RSA-AES128-SHA256        TLSv1.2                DH,4096bits         None
12    DHE-RSA-AES128-SHA           TLSv1,TLSv1.1,TLSv1.2  DH,4096bits         None

Certificate: trusted, 2048 bits, sha256WithRSAEncryption signature
TLS ticket lifetime hint: None
NPN protocols: None
OCSP stapling: not supported
Cipher ordering: client
Curves ordering: client - fallback: no
Server supports secure renegotiation
Server supported compression methods: NONE
TLS Tolerance: yes

8.10.2. TLS 1.3 兼容性

由于兼容性问题,目前默认禁用 TLS 1.3(版本 8.1.x)。可以通过将 sslContextContainer bean 的属性 tls-disable-tls13 设置为 false 来启用它:

sslContextContainer () {
    'tls-disable-tls13' = false
}