认证 / 授权从 EMQX 4.4 到 EMQX 5.1 的不兼容变更
本页介绍了认证和授权功能的配置在 EMQX 4.4 升级到 EMQX 5.1 之后的兼容性。
通用不兼容变更
SSL选项
EMQX 5.1 提供了当需要访问外部资源时可以启用 TLS 的选项,例如连接到数据库(MySQL、PostgreSQL、MongoDB、Redis)进行身份验证,或者通过 HTTPS 访问 Web 服务器进行基于密码的身份验证。更多信息,请参阅启用 TLS 加密访问外部资源。
占位符
现在支持某种数据插值的后端(例如:MySQL、PostgreSQL、MongoDB、Redis、用于外部请求的 HTTP、用于数据插值的 JWT)使用 ${variable}
占位符代替 %X
。
认证配置的不兼容变更
通用变更 (针对所有认证数据源)
密码散列
所有使用密码认证的数据源(内置数据库、MySQL、PostgreSQL、MongoDB、Redis)现在都具有相同的 password_hash
选项,并以相同的方式配置。详情请参阅密码散列。
监听器认证
与 4.4 版本不同,EMQX 5.1 中的每个 MQTT 监听器可以有自己的身份认证配置。此外,提供了 enable_authn
监听器选项:
enable_authn=true
是默认值,将身份认证委托给身份认证链。enable_authn=false
完全禁用监听器的身份认证。enable_authn=quick_deny_anonymous
类似于true
,但还会立即拒绝没有凭证的连接客户端。
移除匿名认证机制
EMQX 5.1 不再有显式的 allow_anonymous
设置。所有客户端默认允许连接。如果添加并启用任何身份验证器,EMQX 将尝试对客户端进行身份验证。要允许匿名访问,请移除或禁用全局或特定监听器链中的所有身份认证器。
在遍历配置的身份认证链后,如果链中没有身份认证器决定允许此客户端连接,则拒绝连接。
同时也删除了bypass_auth_plugins
配置。当希望允许所有客户端在没有身份认证的情况下连接时,可以设置 listeners.{type}.{name}.enable_authn = false
。
内置数据库(Mnesia)
- Mnesia 现在称为"内置"数据库;不在配置中保留用户记录。
- 将
password_hash
更改为password_hash_algorithm
:{name = Algo, salt_position = prefix}。有关详情,请参阅密码散列。 user_id_type
用于标识是使用clientid
还是username
作为 MQTT 用户标识符。不允许混合类型的记录。- 用于管理身份认证数据记录的 REST API 已更改。有关更多信息,请参阅
POST /authentication/{id}/users
的API文档。 - 用户可以使用数据导入 API 将数据从旧版本导入到 EMQX 5.x,请参阅
POST /authentication/{id}/import_users
了解详情。
示例
EMQX 4.4
auth.mnesia.password_hash = sha256
EMQX 5.1
authentication {
backend = built_in_database
mechanism = password_based
password_hash_algorithm {
name = sha256
salt_position = prefix
}
user_id_type = username
enable = true
}
内置数据库 (增强认证)
- EMQX 4.4 中使用的 SHA1哈希支持已不再可用。现在可以使用
algorithm
参数来选择sha512
和sha256
算法。 - 现在可以通过配置迭代次数选项
iteration_count
指定散列次数(在 EMQX 4.4 中隐式使用了4096)。
示例
EMQX 4.4
# No configuration
EMQX 5.1
{
mechanism = scram
backend = built_in_database
enable = true
algorithm = sha512
iteration_count = 4096
}
Redis
mechanism = password_based
backend = redis
type
已更改为redis_type
。- 对于类型为
single
,server
已更改为servers
。 - 对于类型为
sentinel
,server
已更改为servers
。 - 对于类型为
cluster
,database
选项不再可用。
- 对于类型为
database
仍为database
(对于cluster
类型除外);此选项不再适用于集群。pool
已更改为pool_size
。password
仍为password
。query_timeout
不再使用。ssl.*
选项已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。auth_cmd
已更改为cmd
。仅支持 Redis Hashes 数据结构和HGET
和HMGET
查询命令。在命令中使用${var}
样式的占位符。命令应至少获取password
(与 4.x 兼容)或password_hash
字段,以及可选的salt
和is_superuser
字段。不再使用
super_cmd
。请在cmd
中提供is_superuser
字段。如果需要给客户端提供超级用户权限,请将is_superuser
字段添加到 Redis 查询命令中。Details
shell# bad GET emqx_user:${username} # bad HMGET emqx_user:${username} passwd # good HMGET emqx_user:${username} password_hash # good HMGET emqx_user:${username} password_hash is_superuser
password_hash
现在使用通用的password_hash_algorithm
参数。当与数据库连接失败时,您可以使用
auto_reconnect
配置来自动重连。
示例
EMQX 4.4
auth.redis.type = single
auth.redis.server = 127.0.0.1:6379
auth.redis.pool = 8
auth.redis.database = 0
auth.redis.password = pass
assword salt
auth.redis.auth_cmd = HMGET mqtt_user:%u password salt
auth.redis.password_hash = salt,sha256
auth.redis.ssl = on
auth.redis.ssl.cacertfile = path/to/your/cafile.pem
auth.redis.ssl.certfile = path/to/your/certfile
auth.redis.ssl.keyfile = path/to/your/keyfile
auth.redis.ssl.verify = true
auth.redis.ssl.server_name_indication = myredis
EMQX 5.1
authentication {
mechanism = password_based
backend = redis
enable = true
redis_type = single
server = "127.0.0.1:6379"
password_hash_algorithm {
name = sha256
salt_position = prefix
}
cmd = "HMGET mqtt_user:${username} password salt"
database = 0
password = "pass"
auto_reconnect = true
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = myredis
}
}
MySQL
backend = mysql
mechanism = password_based
server
、username
、password
、database
、query_timeout
保持不变。pool
已更改为pool_size
。ssl.*
选项已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。password_hash
已更改为common password_hash_algorithm
参数。auth_query
已更改为query
。应使用${var}
样式的占位符。查询应至少获取password
或password_hash
列,并可选地获取salt
和is_superuser
列。不再使用
,请在查询中提供
is_superuser
列。如果需要给客户端提供超级用户权限,请确保认证 SQL 结果包含is_superuser
字段。sqlSELECT password as password_hash, salt, is_superuser FROM mqtt_user where username = ${username} LIMIT 1
当与数据库连接失败时,您可以使用
auto_reconnect
配置来自动重连。
示例
EMQX 4.4
auth.mysql.server = 127.0.0.1:3306
auth.mysql.pool = 8
auth.mysql.username = dbuser
auth.mysql.database = mqtt
auth.mysql.query_timeout = 5s
auth.mysql.auth_query = select password_hash as password from mqtt where username = '%u' limit 1
auth.mysql.super_query = select is_superuser from mqtt where username = '%u' limit 1
auth.mysql.ssl = on
auth.mysql.ssl.cacertfile = path/to/your/cafile.pem
auth.mysql.ssl.certfile = path/to/your/certfile
auth.mysql.ssl.keyfile = path/to/your/keyfile
auth.mysql.ssl.verify = true
auth.mysql.ssl.server_name_indication = mymysql
EMQX 5.1
authentication {
backend = mysql
mechanism = password_based
enable = true
server = "127.0.0.1:3306"
username = "dbuser"
database = "mqtt"
password = "dbpass"
pool_size = 8
password_hash_algorithm {
name = sha256
salt_position = prefix
}
query = "SELECT password_hash, salt, is_superuser FROM mqtt where username = ${username} LIMIT 1"
query_timeout = "5s"
auto_reconnect = true
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = mymysql
}
}
PostgreSQL
mechanism = password_based
backend = postgresql
server
、username
、password
、database
保持不变。不再使用
query_timeout
。不再使用
encoding
。pool
已更改为pool_size
。ssl.*
已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。password_hash
已更改为通用的password_hash_algorithm
参数。auth_query
已更改为query
。应使用${var}
样式的占位符。查询应至少获取password
或password_hash
列,并可选地获取salt
和is_superuser
列。不再使用
super_query
,请在查询中提供is_superuser
列。如果需要给客户端提供超级用户权限,请确保认证 SQL 结果包含is_superuser
字段。sqlSELECT password as password_hash, salt, is_superuser FROM mqtt_user where username = ${username} LIMIT 1
示例
EMQX 4.4
auth.pgsql.server = 127.0.0.1:5432
auth.pgsql.pool = 8
auth.pgsql.username = root
auth.pgsql.password = dbpass
auth.pgsql.database = mqtt
auth.pgsql.encoding = utf8
auth.pgsql.auth_query = select password, salt from mqtt_user where username = '%u' limit 1
auth.pgsql.password_hash = salt,sha256
auth.pgsql.super_query = select is_superuser from mqtt_user where username = '%u' limit 1
auth.pgsql.ssl = on
auth.pgsql.ssl.cacertfile = path/to/your/cafile.pem
auth.pgsql.ssl.certfile = path/to/your/certfile
auth.pgsql.ssl.keyfile = path/to/your/keyfile
auth.pgsql.ssl.verify = true
auth.pgsql.ssl.server_name_indication = mypgsql
EMQX 5.1
authentication {
backend = postgresql
mechanism = password_based
enable = true
server = "127.0.0.1:5432"
username = "root"
database = "mqtt"
password = "dbpass"
pool_size = 8
password_hash_algorithm {
name = sha256
salt_position = prefix
}
query = "SELECT password_hash, salt, is_superuser FROM mqtt_user where username = ${username} LIMIT 1"
auto_reconnect = true
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = mypgsql
}
}
MongoDB
mechanism = password_based
backend = mongodb
type
已更改为mongo_type
字段。可能的值为single
、rs
、sharded
。不再支持未知值。server
- 对于
rs
、sharded
类型,更改为servers
- 对于
single
类型,更改为server
- 对于
srv_record
,username
,password
,auth_source
,database
,w_mode
,topology
,collection
保持不变。r_mode
仅适用于rs
类型。pool
更改为pool_size
.ssl.*
已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。auth_query.selector
更改为filter
。查询 Filter 应该不再是一个字符串,而是整个 selector 数据结构。在 selector 值中可使用${var}
格式的占位符。auth_query.salt_field
更改为salt_field
。auth_query.super_field
更改为is_superuser_field
。super_query
不再使用。 在使用filter
获取的文档中提供is_superuser_field
字段,同时设置is_superuser_field
。Details
shellauthentication = [ { ... mechanism = "password_based" backend = "mongodb" # is_superuser_field = "is_superuser" } ]
password_hash
更改为common password_hash_algorithm
参数。query_timeout
不再使用。
示例
EMQX 4.4
auth.mongo.type = single
auth.mongo.srv_record = false
auth.mongo.server = 127.0.0.1:27017
auth.mongo.pool = 8
auth.mongo.username = user
auth.mongo.password = pass
auth.mongo.auth_source = admin
auth.mongo.database = mqtt
auth.mongo.query_timeout = 5s
auth.mongo.ssl = on
auth.mongo.ssl.cacertfile = path/to/your/cafile.pem
auth.mongo.ssl.certfile = path/to/your/certfile
auth.mongo.ssl.keyfile = path/to/your/keyfile
auth.mongo.ssl.verify = true
auth.mongo.ssl.server_name_indication = mymongo
auth.mongo.w_mode = unsafe
auth.mongo.topology.pool_size = 1
auth.mongo.topology.max_overflow = 0
## auth.mongo.auth_query.password_hash = salt,sha256
auth.mongo.auth_query.collection = mqtt_user
auth.mongo.auth_query.password_field = password_hash
auth.mongo.auth_query.selector = username=%u, clientid=%c
auth.mongo.super_query.collection = mqtt_user
auth.mongo.super_query.super_field = is_superuser
auth.mongo.super_query.selector = username=%u, clientid=%c
EMQX 5.1
authentication {
mechanism = password_based
backend = mongodb
enable = true
password_hash_algorithm {
name = sha256
salt_position = prefix
}
collection = "mqtt_user"
filter { username = "${username}", clientid = "${clientid}" }
password_hash_field = "password_hash"
salt_field = "salt"
is_superuser_field = "is_superuser"
mongo_type = single
server = "127.0.0.1:27017"
database = "mqtt"
username = "emqx"
password = "pass"
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = mymongo
}
topology {
pool_size = 1
max_overflow = 0
}
}
JWT
mechanism = jwt
secret
、from
、verify_claims
、acl_claim_name
和refresh_interval
保持不变。pubkey
更改为public_key
。jwks
更改为endpoint
。signature_format
已删除。
在 verifiy_claims
配置中,在 selector 值中应使用 ${var}
格式的占位符 (${username}
和 ${clientid}
) 而不是 %X
。
更多参数:
use_jwks
:是否从 JWKS 获取 keyalgorithm
:使用哪种签名来验证public-key|hmac-based
secret_base64_encoded
: 指定密钥格式pool_size
: 连接到 JWKS 服务器的客户端连接个数ssl
:用于连接 JWKS 服务器的 SSL 选项
注意:不是所有参数集都被允许。
EMQX 4.x 同时支持 public key
、hmac secret
算法以及 jwks
。与 EMQX 4.4 不同,(secret
, secret_base64_encoded
, public_key
, endpoint
, pool_size
, refresh_interval
, ssl
) 参数的所有组合并非都被允许。EMQX 5.1 只能一次使用一种算法,并且在全局配置中设置。use_jwks
和 algorithm
标识了可用的参数集:
使用 use_jwks=true
和 algorithm=public-key
:endpoint
、pool_size
、refresh_interval
、ssl
使用 use_jwks=false
和 algorithm=public-key
:public_key
使用 use_jwks=false
和 algorithm=hmac-based
:secret
、secret_base64_encoded
use_jwks=true
和 algorithm=hmac-based
的组合是无效的。
示例
EMQX 4.4
auth.jwt.jwks = https://127.0.0.1:8080/jwks
auth.jwt.jwks.refresh_interval = 5m
auth.jwt.from = password
auth.jwt.verify_claims = on
auth.jwt.verify_claims.username = %u
auth.jwt.acl_claim_name = acl
EMQX 5.1
{
mechanism = jwt
from = password,
acl_claim_name = acl
use_jwks = true
algorithm = "public-key"
verify_claims = {
username = "${username}
}
ssl {
enable = true
}
endpoint = "https://127.0.0.1:8080/jwks"
}
HTTP
mechanism = password_based
backend = http
method
、pool_size
、connect_timeout
和enable_pipelining
保持不变。auth_req.url
已更改为url
。auth_req.headers
已更改为headers
。auth_req.params
已更改为body
。timeout
已更改为request_timeout
。ssl.*
已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。super_req
不再可用。客户端的超级用户身份通过认证响应中的 body 设置,需要在服务响应中提供is_superuser
字段。
与 4.4 版本不同,url
、headers
和 body
参数允许使用占位符。在 5.1 版本中,body
不再是一个字符串,而是一个映射。它将使用 JSON 或 X-WWW-Form-Urlencoded 格式进行序列化(用于 POST 请求),或作为查询参数(用于 GET 请求)。
与 4.4 版本不同,在 5.1 版本中,认证结果现在通过响应 body 内的 JSON 字段来确定,而不再使用 HTTP 响应状态码。HTTP 认证仅会关注返回成功的 HTTP 状态码(2XX),并从响应 body 中提取 result
字段作为解析依据。
Details
成功响应状态码:
200 or 204
如果请求失败或返回其他状态码,认证器将被忽略。
成功响应 body (JSON):
名称 | 类型 | 是否必须 | 描述 |
---|---|---|---|
result | Enum | 是 | `allow |
is_supseruser | Boolean | 否 | 默认为 false |
{
"result": "allow",
"is_supseruser": true
}
示例
EMQX 4.4
auth.http.auth_req.url = http://127.0.0.1:80/mqtt/auth
auth.http.auth_req.method = post
auth.http.auth_req.headers.content_type = application/x-www-form-urlencoded
auth.http.auth_req.params = clientid=%c,username=%u,password=%P
auth.http.timeout = 5s
auth.http.connect_timeout = 5s
auth.http.pool_size = 32
auth.http.enable_pipelining = 100
auth.http.ssl = on
auth.http.ssl.cacertfile = path/to/your/cafile.pem
auth.http.ssl.certfile = path/to/your/certfile
auth.http.ssl.keyfile = path/to/your/keyfile
auth.http.ssl.verify = true
auth.http.ssl.server_name_indication = myhttp
EMQX 5.1
{
mechanism = password_based
backend = http
enable = true
method = post
url = "http://127.0.0.1:80/mqtt/auth"
body {
username = "${username}"
clientid = "${clientid}"
password = "${password}"
}
headers {
"Content-Type" = "application/x-www-form-urlencoded"
}
request_timeout = "5s"
connect_timeout = "5s"
pool_size = 32
enable_pipelining = 100
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = myhttp
}
}
授权配置的不兼容变更
ACL 文件
- 移除了
acl_file
配置。基于文件的 ACL(acl.conf)将作为授权检查数据源之一,并默认添加到 EMQX 中。 acl.conf
数据文件的语法已经发生了变化。- 在 dsl 中,
pubsub
被重命名为all
。
4.x | 5.1 | 兼容性 |
---|---|---|
user | username | 是 |
client | clientid | 是 |
pubsub | all | 否 |
示例
EMQX 4.3
{allow, {user, "dashboard"}, subscribe, ["$SYS/#"]}.
{allow, {ipaddr, "127.0.0.1"}, pubsub, ["$SYS/#", "#"]}.
{deny, all, subscribe, ["$SYS/#", {eq, "#"}]}.
{allow, all}.
EMQX 5.1
{allow, {user, "dashboard"}, subscribe, ["$SYS/#"]}.
{allow, {ipaddr, "127.0.0.1"}, all, ["$SYS/#", "#"]}.
{deny, all, subscribe, ["$SYS/#", {eq, "#"}]}.
{allow, all}.
内置数据库(Mnesia)
- 为方便理解,该数据源由 Mnesia 更名为内置数据库 (Built-in Database)。
- 数据格式与数据操作 REST API 有变动,4.x 版本中的 ACL 数据可以通过
./bin/emqx_ctl data export
命令导出。用户可以将数据转换为符合 5.1 版本的格式,并通过相应的 REST API 导入。新的 API 是/authorization/sources/built_in_database/rules{/clients,/users}
。
示例
EMQX 4.4
# No settings
EMQX 5.1
{
type = built_in_database
enable = true
}
JWT
这是隐式的 ACL,基于 JWT 认证期间提取的声明 。在 ACL 声明中,应使用 ${variable}
占位符,而不是 %X
占位符。
HTTP
type = http
method
、pool_size
、connect_timeout
和enable_pipelining
参数保留不变。acl_req.url
已更改为url
。acl_req.headers
已更改为headers
。acl_req.params
已更改为body
。timeout
已更改为request_timeout
。ssl.*
已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。
与 4.4 版本不同,url
、headers
和 body
参数允许使用占位符。
在 5.1 版本中,body
不再是一个字符串,而是一个映射。它将使用 JSON 或 X-WWW-Form-Urlencoded 格式进行序列化(用于 POST 请求),或作为查询参数(用于 GET 请求)。
与 4.4 版本不同,授权结果现在通过响应 body 内的 JSON 字段来确定,而不再使用 HTTP 响应状态码。HTTP 授权仅关注返回成功的 HTTP 状态码(2XX),并从响应 body 中提取 result
字段作为解析依据。
Details
成功响应状态码
200 or 204
如果请求失败或返回其他状态码,授权检查器将被忽略。
成功响应 body (JSON):
Name | 类型 | 是否必须 | 描述 |
---|---|---|---|
result | Enum | 是 | `allow |
{
"result": "deny"
}
示例
EMQX 4.4
auth.http.acl_req.url = http://127.0.0.1:80/mqtt/acl
auth.http.acl_req.method = post
auth.http.acl_req.headers.content_type = application/x-www-form-urlencoded
auth.http.acl_req.params = clientid=%c,username=%u,password=%P
auth.http.timeout = 5s
auth.http.connect_timeout = 5s
auth.http.pool_size = 32
auth.http.enable_pipelining = 100
auth.http.ssl = on
auth.http.ssl.cacertfile = path/to/your/cafile.pem
auth.http.ssl.certfile = path/to/your/certfile
auth.http.ssl.keyfile = path/to/your/keyfile
auth.http.ssl.verify = true
auth.http.ssl.server_name_indication = myhttp
EMQX 5.1
{
type = http
method = post
url = "http://127.0.0.1:80/mqtt/acl"
body {
username = "${username}"
clientid = "${clientid}"
password = "${password}"
}
headers {
"Content-Type" = "application/x-www-form-urlencoded"
}
request_timeout = "5s"
connect_timeout = "5s"
pool_size = 32
enable_pipelining = 100
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = myhttp
}
}
Redis
type = redis
- 当与数据库连接失败时,可以使用
auto_reconnect
配置进行自动重连。 type
已更改为redis_type
。- 对于类型
single
,server
已更改为servers
。 - 对于类型
sentinel
,server
已更改为servers
。 - 对于类型
cluster
,database
选项不再可用。
- 对于类型
database
仍为database
,但不包括cluster
类型;该选项不再适用于集群)。pool
已更改为pool_size
。password
仍为password
。- 不再使用
query_timeout
选项。 ssl.*
选项已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。auth_cmd
已更改为cmd
。应在命令中使用${var}
样式的占位符。- Redis 数据源仍然仅支持白名单模式,需要设置
acl_nomatch = deny
; access
字段名称更改为action
,数据由数字变为动作全称字符串,对应关系见下表。
如果您想继续使用 4.x 中的数据,请手动进行必要的迁移。
4.x 与 5.x 版本的数据对应关系
4.x | 5.x | 对应动作 |
---|---|---|
1 | subscribe | 订阅 |
2 | publish | 发布 |
3 | all | 发布订阅 |
5.1 版本中数据示例
HSET mqtt_acl:emqx_u t/# subscribe
HSET mqtt_acl:emqx_u # all
HSET mqtt_acl:emqx_u a/1 publish
示例
EMQX 4.4
auth.redis.type = single
auth.redis.server = 127.0.0.1:6379
auth.redis.pool = 8
auth.redis.database = 0
auth.redis.password = pass
assword salt
auth.redis.acl_cmd = HGETALL mqtt_user:%u
auth.redis.password_hash = salt,sha256
auth.redis.ssl = on
auth.redis.ssl.cacertfile = path/to/your/cafile.pem
auth.redis.ssl.certfile = path/to/your/certfile
auth.redis.ssl.keyfile = path/to/your/keyfile
auth.redis.ssl.verify = true
auth.redis.ssl.server_name_indication = myredis
EMQX 5.1
{
type = redis
enable = true
redis_type = single
server = "127.0.0.1:6379"
cmd = "HMGET mqtt_user:${username}"
database = 0
password = "pass"
auto_reconnect = true
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = myredis
}
}
MySQL
type = mysql
查询结果中不再需要
ipaddr/username/clientid
字段,需要调整查询 SQL。access
字段名变为action
,数据类型由整型变为字符或字符枚举,数值对应关系见下表。allow
字段名变为permission
,数据类型由整型变为字符或字符枚举,数值对应关系见下表。4.x 的整数值与 5.x 的字符/字符枚举值之间的对应关系
Access/action 字段数据类型映射
4.x (int) 5.x (varchar/enum) 对应动作 1 subscribe 订阅 2 publish 发布 3 all 发布订阅 Allow/permission 字段数据类型映射
4.x (int) 5.x (varchar/enum) 对应行为 0 deny 拒绝 1 allow 允许 server
、username
、password
、database
、query_timeout
参数保留不变。pool
已更改为pool_size
。ssl.*
选项已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。acl_query
已更改为query
。应使用${var}
样式的占位符。您可以使用
auto_reconnect
在 MySQL 连接失败时自动重新连接。
存储模式已更改。
在 EMQX 4.4 中,查询应准确按照 [Allow, IpAddr, Username, ClientId, Access, Topic]
列的顺序提取行,列名可以是任意名称。
在 EMQX 5.1 中,查询应该按照任意顺序提取具有 permission, action, topic
列的行,但列名必须是这些名称。 "who" 部分(IpAddr, Username, ClientId
)现在建议作为查询的一部分。
示例
EMQX 4.4
auth.mysql.server = 127.0.0.1:3306
auth.mysql.pool = 8
auth.mysql.username = dbuser
auth.mysql.database = mqtt
auth.mysql.query_timeout = 5s
auth.mysql.acl_query = select allow, ipaddr, username, clientid, access, topic from mqtt_acl where username = '%u'
auth.mysql.ssl = on
auth.mysql.ssl.cacertfile = path/to/your/cafile.pem
auth.mysql.ssl.certfile = path/to/your/certfile
auth.mysql.ssl.keyfile = path/to/your/keyfile
auth.mysql.ssl.verify = true
auth.mysql.ssl.server_name_indication = mymysql
EMQX 5.1
{
type = mysql
enable = true
server = "127.0.0.1:3306"
username = "dbuser"
database = "mqtt"
password = "dbpass"
pool_size = 8
query = "select allow as permission, access as action, topic from mqtt_acl where username = ${username} and ipaddr = ${peerhost} and clientid = ${clientid}"
query_timeout = "5s"
auto_reconnect = true
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = mymysql
}
}
PostgreSQL
type = postgresql
- 查询结果中不再需要
ipaddr/username/clientid
字段,需要调整查询 SQL。 access
字段名变为action
,数据类型由整型变为字符或字符枚举,数值对应关系见下表。allow
字段名变为permission
,数据类型由整型变为字符或字符枚举,数值对应关系见下表。
4.x 的整数值与 5.x 的字符/字符枚举值之间的对应关系
Access/action 字段数据类型映射
4.x (int) | 5.x (varchar/enum) | 对应动作 |
---|---|---|
1 | subscribe | 订阅 |
2 | publish | 发布 |
3 | all | 发布订阅 |
Allow/permission 字段数据类型映射
4.x (int) | 5.x (varchar/enum) | 对应行为 |
---|---|---|
0 | deny | 拒绝 |
1 | allow | 允许 |
server
、username
、password
、database
、query_timeout
参数保留不变。query_timeout
不再使用。encoding
不再使用。pool
已更改为pool_size
。ssl.*
选项已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。acl_query
已更改为query
。应使用${var}
样式的占位符。
存储模式已更改。
在 EMQX 4.4 中,查询应准确按照 [Allow, IpAddr, Username, ClientId, Access, Topic]
列的顺序提取行,列名可以是任意名称。
在 EMQX 5.1 中,查询应该按照任意顺序提取具有 permission, action, topic
列的行,但列名必须是这些名称。 "who" 部分(IpAddr, Username, ClientId
)现在建议作为查询的一部分。
示例
EMQX 4.4
auth.pgsql.server = 127.0.0.1:5432
auth.pgsql.pool = 8
auth.pgsql.username = root
auth.pgsql.password = dbpass
auth.pgsql.database = mqtt
auth.pgsql.encoding = utf8
auth.pgsql.acl_query = select allow, ipaddr, username, clientid, access, topic from mqtt_acl where username = '%u'
auth.pgsql.ssl = on
auth.pgsql.ssl.cacertfile = path/to/your/cafile.pem
auth.pgsql.ssl.certfile = path/to/your/certfile
auth.pgsql.ssl.keyfile = path/to/your/keyfile
auth.pgsql.ssl.verify = true
auth.pgsql.ssl.server_name_indication = mypgsql
EMQX 5.1
{
type = postgresql
enable = true
server = "127.0.0.1:5432"
username = "root"
database = "mqtt"
password = "dbpass"
pool_size = 8
query = "select allow as permission, access as action, topic from mqtt_acl where username = ${username} and ipaddr = ${peerhost} and clientid = ${clientid}"
auto_reconnect = true
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = mypgsql
}
}
MongoDB
type = mongodb
type
已更改为mongo_type
字段。可能的取值为single
、rs
和sharded
。不再允许未知的值。server
- 对于
rs
和sharded
类型,server
已更改为servers
。 - 对于
single
类型,server
已更改为server
。
- 对于
srv_record
、username
、password
、auth_source
、database
、w_mode
、topology
、collection
参数保留不变。r_mode
仅适用于rs
类型。pool
已更改为pool_size
。ssl.*
选项已更改为通用的 SSL 选项。请参阅启用 TLS 加密访问外部资源。auth_query.selector
已更改为filter
。过滤器不应该是一个字符串,而是整个选择器数据结构。应在选择器值中使用${var}
样式的占位符。- 不再使用
query_timeout
。
存储模式已更改。在 EMQX 4.4 中,生成的数据存储文档应该按照 action 键包含主题列表,类似于 Redis 或 JWT:
{
"publish": ["t1", "t2"],
"subscribe": ["t3", "t4"],
"pubsub": ["t5", "t6"]
}
在 EMQX 5.1 中, MongoDB 数据源可用于黑/白名单模式下,此前仅支持白名单模式,并要求设置 acl_nomatch = deny
。 MongoDB 数据存储文档中应包含 action
permission
topics
字段的单独规则,topic
字段应该是一个主题数组。具体使用方式详见 基于 MongoDB 进行授权。如需继续使用 4.x 中的数据,请手动迁移适配。
5.1 版本中数据示例
[
{
"username": "emqx_u",
"clientid": "emqx_c",
"ipaddress": "127.0.0.1",
"permission": "allow",
"action": "all",
"topics": ["#"]
}
]
示例
EMQX 4.4
auth.mongo.type = single
auth.mongo.srv_record = false
auth.mongo.server = 127.0.0.1:27017
auth.mongo.pool = 8
auth.mongo.username = user
auth.mongo.password = pass
auth.mongo.auth_source = admin
auth.mongo.database = mqtt
auth.mongo.query_timeout = 5s
auth.mongo.ssl = on
auth.mongo.ssl.cacertfile = path/to/your/cafile.pem
auth.mongo.ssl.certfile = path/to/your/certfile
auth.mongo.ssl.keyfile = path/to/your/keyfile
auth.mongo.ssl.verify = true
auth.mongo.ssl.server_name_indication = mymongo
auth.mongo.w_mode = unsafe
auth.mongo.topology.pool_size = 1
auth.mongo.topology.max_overflow = 0
auth.mongo.acl_query.collection = mqtt_user
auth.mongo.acl_query.selector = username=%u, clientid=%c
EMQX 5.1
{
type = mongodb
enable = true
collection = "mqtt_user"
filter { username = "${username}", clientid = "${clientid}" }
mongo_type = single
server = "127.0.0.1:27017"
database = "mqtt"
username = "emqx"
password = "pass"
ssl {
enable = true
verify = verify_peer
keyfile = path/to/your/keyfile
certfile = path/to/your/certfile
cacertfile = path/to/your/cafile.pem
server_name_indication = mymongo
}
topology {
pool_size = 1
max_overflow = 0
}
}