首页/新闻资讯/正文详情

EMQX 认证器前置条件(Authenticator Precondition):基于客户端信息的条件化认证调度

发布时间:2026/9/23 1:58:01 来源:云帆数科 栏目:资讯中心
EMQX 认证器前置条件(Authenticator Precondition):基于客户端信息的条件化认证调度
后端物联网消息队列通信【免费下载链接】emqxThe most scalable and reliable MQTT broker for AI, IoT, IIoT and connected vehicles项目地址https://gitcode.com/gh_mirrors/em/emqx点击查看免费下载导读EMQX 从 v5.x 起支持在认证链Authentication Chain中为每个认证器Authenticator配置前置条件Precondition表达式。本文基于 changes/ee/feat-14976.en.md 的变更记录展开介绍如何在认证器中通过 Variform 表达式按客户端信息如监听器、Zone、用户名等选择性调用认证器从而避免不必要的认证请求。读完本文你将掌握precondition配置项的语法、可用变量、真实配置示例以及它在源码中的编译、渲染与执行机制。功能背景与核心价值EMQX 的认证Authenticationauthn采用认证链机制多个认证器按顺序排列逐个尝试对客户端进行身份验证。在默认情况下链上的每个认证器都会被依次调用直到某个认证器返回成功或全部失败。引入 precondition前置条件后每个认证器可以附带一个 Variform 条件表达式。只有当该表达式求值为字符串true时对应的认证器才会被真正调用否则该认证器被跳过直接进入链上的下一个认证器。这带来了两个直接收益避免不必要的认证请求例如将 HTTP 认证器限定在tcp:default监听器将 PostgreSQL 认证器限定在ssl:default监听器从而减少跨网络的后端请求实现按场景分流同一认证链可以按客户端来源、TLS 属性、用户名/密码特征等维度路由到不同的认证后端。该能力由 EMQX 认证模块 apps/emqx_auth 实现涉及配置 Schema、认证链执行逻辑与 Variform 表达式引擎三部分。配置项说明precondition字段在认证器Authenticator配置中新增了可选字段precondition。它定义在认证链公共字段中见 apps/emqx_auth/src/emqx_authn/emqx_authn_schema.erl#L200-L213类型binary()字符串表达式默认值空字符串等价于未配置表示该认证器无条件被调用语义一个 Variform 表达式使用客户端信息作为预绑定变量求值表达式求值结果必须为字符串true认证器才会被调用求值为任何其他值则跳过该认证器。可用变量根据 rel/i18n/emqx_authn_schema.hocon#L168-L194 中的字段描述表达式可用的预绑定变量来源于客户端信息包括变量含义username客户端用户名password客户端密码clientid客户端 IDclient_attrs.*客户端属性cert_common_name客户端 TLS 证书的 subject 字段cert_subject客户端 TLS 证书的 CNCommon NamepeersniTLS 客户端发送的 SNIServer Name Indicationlistener监听器 ID例如tcp:defaultzone客户端关联的配置 Zone常用表达式示例文档 rel/i18n/emqx_authn_schema.hocon#L186-L192 给出的官方示例仅当客户端从监听器ssl:letsencrypt接入时才调用该认证器str_eq(listener, ssl:letsencrypt)当用户名为空时跳过该认证器not(is_empty_val(username))仅当密码存在且 Zone 为zone1时调用iif(is_empty_val(password), false, str_eq(zone, zone1))这些内置函数如str_eq、is_empty_val、iif、not的行为可在 Variform 表达式引擎的单元测试 apps/emqx_utils/test/emqx_variform_tests.erl#L247-L253 与 apps/emqx_utils/test/emqx_variform_tests.erl#L384-L386 中验证例如str_eq(a, a)求值为{ok, true}str_eq(a, b)求值为{ok, false}iif(str_eq(a,1),2,3)在a 1时求值为2否则为3。配置示例按监听器分流认证器变更记录 changes/ee/feat-14976.en.md 中给出了典型场景对通过tcp:default接入的客户端触发 HTTP 认证器对通过ssl:default接入的客户端触发 PostgreSQL 认证器。在 HOCON 配置文件中可以在认证链authentication下为每个认证器添加preconditionauthentication [ { mechanism password_based backend http method post url http://127.0.0.1:8080/auth precondition str_eq(listener, tcp:default) enable true }, { mechanism password_based backend postgresql server 127.0.0.1:5432 database mqtt username emqx password secret precondition str_eq(listener, ssl:default) enable true } ]运行效果通过tcp:default监听器接入的客户端HTTP 认证器前置条件满足 → 触发 HTTP 认证请求PostgreSQL 认证器前置条件不满足 → 被跳过不产生任何 PostgreSQL 查询通过ssl:default监听器接入的客户端行为相反仅 PostgreSQL 认证器被调用两个监听器的客户端共用同一个认证链但认证后端完全隔离。源码实现解析Schema 定义precondition作为认证器公共字段与enable并列注册见 apps/emqx_auth/src/emqx_authn/emqx_authn_schema.erl#L209-L213common_fields() - [ {enable, fun enable/1}, {precondition, precondition()} ].编译期表达式预编译创建认证器时配置中的 precondition 字符串会先经emqx_variform:compile/1编译为内部表达式预编译可提前发现语法错误编译失败时返回bad_precondition_expression错误apps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L1068-L1082 中的compile_precondition/1与do_compile_precondition/1undefined与空二进制都被视为无前置条件编译结果为undefined创建认证器的入口 apps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L1028-L1035 与更新认证器的 apps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L726-L752 都会执行编译并把编译结果存入#authenticator{precondition ...}记录。运行期条件检查与跳过语义认证链按顺序执行认证器时会先检查 preconditionapps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L923-L932 的check_precondition/2调用emqx_variform:render(Precondition, Credential)求值结果恰好为二进制true时返回{ok, true}apps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L934-L952 的authenticate_with_provider/2依据检查结果分三种情况处理{ok, true}调用do_authenticate_with_provider/2真正执行后端认证{error, _}表达式本身求值出错如引用了不存在的变量记为precondition_error并按后端失败处理{ok, Other}表达式求值成功但结果不是true记为precondition_not_met并返回ignoreapps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L903-L906ignore结果不会终止认证链而是继续尝试链上的下一个认证器{stop, _}则终止。因此precondition 不满足的认证器对认证链而言等价于未匹配nomatch 语义既不会触发后端请求也不会中断认证流程。安全基线Hardened Profile下的组合在加固安全基线hardened security profile下precondition 与ignore_backend_failures语义可以组合使用形成按条件跳过 后端失败忽略的弹性认证链。相关测试见 apps/emqx_auth/test/emqx_authn/emqx_authn_chains_SUITE.erl#L727-L762。实战验证JWT 与密码认证的混合链测试套件 apps/emqx_auth/test/emqx_authn/emqx_authn_chains_SUITE.erl#L842-L856 演示了一个典型用法在同一认证链中先创建带前置条件is_jwt(password)的 JWT 认证器再创建内置数据库built_in_database的密码认证器{ok, _} ?AUTHN:create_authenticator(ListenerID, #{ mechanism jwt, enable true, precondition is_jwt(password) }), {ok, _} ?AUTHN:create_authenticator(ListenerID, #{ mechanism password_based, backend built_in_database, enable true }).测试验证的行为apps/emqx_auth/test/emqx_authn/emqx_authn_chains_SUITE.erl#L735-L761当密码是 JWT 时前置条件满足 → 调用 JWT 认证器当密码不是 JWT 时前置条件不满足 → 跳过 JWT 认证器回落到密码认证器当完全没有密码时表达式求值为 false非错误→ 同样跳过继续后续认证器。这正体现了 precondition 的核心价值把是否适用的判断从认证逻辑中剥离出来交给可声明、可预编译的表达式让认证链更简洁、更高效。注意事项precondition表达式的求值结果是字符串true而非布尔值true编写表达式时需注意函数的返回值形态表达式求值失败如变量不存在会被视为认证失败而不是跳过与表达式结果为 false 时跳过语义不同参见 apps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl#L938-L944该配置同样适用于认证授权authz模块其 Schema 中也有precondition字段见 apps/emqx_auth/src/emqx_authz/emqx_authz_schema.erl实现思路一致通过 Dashboard / HTTP API 创建认证器时同样可以在请求体中携带precondition字段通过 Dashboard 界面配置时该项位于认证器的Precondition设置中。延伸阅读认证链核心实现apps/emqx_auth/src/emqx_authn/emqx_authn_chains.erl认证器配置 Schemaapps/emqx_auth/src/emqx_authn/emqx_authn_schema.erl字段说明与示例rel/i18n/emqx_authn_schema.hoconVariform 表达式引擎apps/emqx_utils/src/emqx_variform.erl 及其测试 apps/emqx_utils/test/emqx_variform_tests.erl功能变更记录changes/ee/feat-14976.en.md赞分享后端物联网消息队列通信【免费下载链接】emqxThe most scalable and reliable MQTT broker for AI, IoT, IIoT and connected vehicles项目地址https://gitcode.com/gh_mirrors/em/emqx点击查看免费下载相关推荐EMQX 的 is_jwt 前置条件函数在认证链中优雅分流 JWT 与传统凭据客户端EMQX 的 is_jwt 前置条件函数在认证链中优雅分流 JWT 与传统凭据客户端 导读 本文围绕 EMQX 6.2.3 新增的 is_jwt value后端物联网消息队列通信CephFS 挂载前置条件指南客户端选择、CephX 认证与配置文件准备CephFS 挂载前置条件指南客户端选择、CephX 认证与配置文件准备 本指南以 Ceph 官方文档 Mount CephFS: Prerequisites存储分布式文件系统对象存储后端高可用EMQX 授权源前置条件Precondition基于 Variform 表达式的动态鉴权路由EMQX 授权源前置条件Precondition基于 Variform 表达式的动态鉴权路由 导读 EMQX 的授权Authorization/ACL后端物联网消息队列通信创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

相关推荐

mu5344报错全解析:面试必问的Stack Trace排查心法
mu5344报错全解析:面试必问的Stack Trace排查心法

mu5344报错全解析:面试必问的Stack Trace排查心法 盯着屏幕上那串红色的英文字母,头都大了。报错信息长得像天书,Java 的 StackTrace 更是直接给你甩出几十行堆栈,光看 NullPointerException… · 2026/9/23 1:57:55

JavaWeb校园管理系统课设:从环境搭建到答辩拿高分
JavaWeb校园管理系统课设:从环境搭建到答辩拿高分

简介:这是一份面向Java课程设计/期末大作业的校园管理系统完整源码包,基于JavaWeb技术栈实现,前端页面、后端逻辑与数据库设计齐全,适合计算机相关专业学生直接参考运行或二次开发。包内共20个文件,主要包括XML配置、S… · 2026/9/23 1:57:55

深入解析 PHP-CS-Fixer 的 `no_short_bool_cast` 规则:用 `(bool)` 取代 `!!` 双重否定
深入解析 PHP-CS-Fixer 的 `no_short_bool_cast` 规则:用 `(bool)` 取代 `!!` 双重否定

深入解析 PHP-CS-Fixer 的 no_short_bool_cast 规则:用 (bool) 取代 !! 双重否定 【免费下载链接】PHP-CS-Fixer A tool to automatically fix PHP Coding Standards issues 项目地址: https://gitcode.com/gh_mirrors/ph/PHP-CS-Fixer 本篇技术指南围绕 PHP… · 2026/9/23 1:57:49

深入解析HttpServletRequest:Java Web开发核心接口
深入解析HttpServletRequest:Java Web开发核心接口

1. HttpServletRequest 核心概念解析HttpServletRequest 是 Java Servlet 规范中最重要的接口之一,它代表了客户端发起的 HTTP 请求。作为一个在 Web 开发领域摸爬滚打多年的老手,我见过太多开发者对这个基础组件理解不够深入而踩坑的情况。今天我们就来… · 2026/9/23 4:58:27

在4张A800上跑DeepSeek-V4-Flash-Vision系列[9]:视觉链路问题修复
在4张A800上跑DeepSeek-V4-Flash-Vision系列[9]:视觉链路问题修复

09 视觉链路:从"能读图"到"崩不了" SGLang v0.5.16 原生没有任何 DSV4 视觉支持,模型注册里只有纯文本的 DeepseekV4ForCausalLM,加载带视觉张量的 checkpoint 必然 KeyError: aligner.gate_up_proj.weight。所以视觉不… · 2026/9/23 4:58:27

OpenWiki 实践指南:用 Markdown 与 CLI 构建 AI Agent 知识底座
OpenWiki 实践指南:用 Markdown 与 CLI 构建 AI Agent 知识底座

1. 从命令行到知识库:OpenWiki 到底解决了什么问题第一次听到 OpenWiki 这个名字,很多人会下意识觉得它又是一个“维基百科的克隆”或者“文档站生成器”。但真正用过一段时间之后,你会发现它瞄准的痛点其实非常具体:团队和个人的… · 2026/9/23 4:58:27

EverOS 模块文档字符串规范:用「意图 + 契约」写透每个领域与基础设施模块
EverOS 模块文档字符串规范:用「意图 + 契约」写透每个领域与基础设施模块

人工智能AI AgentAgent 记忆RAG 【免费下载链接】EverOS One portable memory layer for every AI agent: local-first, Markdown-native, user-owned, and self-evolving across apps, tools, and workflows. 项目地址: https://gitcode.com/gh_mirrors/ev/EverOS … · 2026/9/23 4:58:20

Spring IoC容器与核心注解深度解析
Spring IoC容器与核心注解深度解析

1. Spring IoC 容器核心机制解析Spring框架最核心的特性莫过于IoC(控制反转)容器,它彻底改变了传统Java应用中对象创建和依赖管理的方式。在传统编程模式下,对象之间的依赖关系通常由调用方显式创建和维护,而Spring Io… · 2026/9/23 4:58:20

PaddleDetection 全场景高性能部署指南:基于 FastDeploy 的云边端推理实践
PaddleDetection 全场景高性能部署指南:基于 FastDeploy 的云边端推理实践

人工智能深度学习计算机视觉 【免费下载链接】PaddleDetection Object Detection toolkit based on PaddlePaddle. It supports object detection, instance segmentation, multiple object tracking and real-time multi-person keypoint detection. 项目地址: htt… · 2026/9/23 4:58:20

3招搞定手机怎么下载微信面试难题实战项目解析
3招搞定手机怎么下载微信面试难题实战项目解析

3招搞定手机怎么下载微信面试难题实战项目解析 面试被问“手机怎么下载微信”背后的原理,90%的人答不上来。别笑,这看似弱智的问题,实则是考察你对移动应用分发机制、安全校验及网络协议理解的试金石。我带过不少校招新人,他们背了八股文,却连一个A… · 2026/9/23 0:00:03

你有新短消息请注意查收:3个新手避坑指南搞定消息系统选型
你有新短消息请注意查收:3个新手避坑指南搞定消息系统选型

你有新短消息请注意查收:3个新手避坑指南搞定消息系统选型 面试被问“高并发下如何保证消息不丢失”,你张口就是“用Redis”,结果面试官追问“如果Redis宕机了怎么办”,你瞬间卡壳。这种场景太常见了,很多新手在背八股文时,只记住了技术名词… · 2026/9/23 0:00:29

Win7无线热点配置工具源码解析:解决API失效的3个实战技巧
Win7无线热点配置工具源码解析:解决API失效的3个实战技巧

Win7无线热点配置工具源码解析:解决API失效的3个实战技巧 Win7无线热点配置工具在Win10/11上跑不动?不是你的问题,是版本升级后 API 全变了。很多老项目里的 netsh wlan… · 2026/9/23 0:00:36

了解更多?预约专属演示

我们的顾问将为您一对一讲解产品与方案

企业微信二维码