消息选择器语法
IBM® MQ 消息选择器是具有基于 SQL92 条件表达式语法子集的语法的字符串。
消息选择器的求值顺序为同一优先顺序级别内从左到右。 可使用括号来更改这一顺序。 预定义选择器字面值和运算符名称在此处以大写写入;但是,这些文本和运算符不区分大小写。
如果通过 API 提供选择器,那么 IBM MQ 会在显示消息选择器时验证其语法正确性。 如果选择字符串的语法不正确或属性名无效,并且扩展消息选择提供程序不可用,那么会将 MQRC_SELECTION_NOT_AVAILABLE 返回到应用程序。 如果恢复预订时选择字符串的语法不正确或属性名称无效,将向应用程序返回 MQRC_SELECTOR_SYNTAX_ERROR。 如果设置属性时禁用了属性名称验证(设置 MQCMHO_NONE,而不是 MQCMHO_VALIDATE),而应用程序随后放入了具有无效属性名称的消息,那么不会选择此消息。
如果 IBM MQ 确定以管理方式定义的预订选择器正在使用扩展消息语法 (如具有值 EXTENDED的 DISPLAY
SUB 参数 SELTYPE 所指示) ,那么在提供选择器时不会返回任何错误。 在这种情况下,选择字符串的语法检查将延迟到发布时间 (请参阅 MQRC_SELECTION_NOT_AVAILABLE)。
- 字面值:
- 字符串字面值以单引号括起。 两个连续的单引号表示一个单引号。 例如,'literal' 和 'literal''s'。 与 Java 字符串字面值一样,这些字面值使用 Unicode 字符编码。 不能使用双引号括起字符串字面值。 单引号之间可以使用任何字节序列。
- 字节字符串是一对或多对十六进制字符,这些字符以双引号括起并带有前缀
0x。 示例为或0x2F1C
。 字节字符串的长度必须至少一个字节。 如果选择器字节字符串与0XD43A
MQTYPE_BYTE_STRING类型的消息属性匹配,那么不需要对前导零或后导零采取特殊操作。 这些字节将视为另外的字符。 同时不考虑字节顺序。 选择器和属性字节字符串的长度必须相等,且字节的顺序必须相同。下面是匹配的字节字符串选择示例(假设 myBytes =0AFC23):myBytes =
= TRUE0x0AFC23
(因为字节数量不是 2 的倍数)myBytes =
= MQRC_SELECTOR_SYNTAX_ERROR0xAFC23
(因为相较之下,后导零非常重要)myBytes =
= FALSE0x0AFC2300
(因为相较之下,前导零非常重要)myBytes =
= FALSE0x000AFC23
(因为不考虑字节顺序)myBytes =
= FALSE0x23FC0A
- 十六进制数字以 0 开头,后跟大写或小写
x。 文字的其余部分包含一个或多个有效十六进制字符。 例如,0xA、0xAF和0X2020。 - 后跟一个或多个 0-7 范围内数字的前导零将始终认为是八进制数字的开头。 不能像以下示例这样表示以零为前缀的小数,例如,
09将返回语法错误,因为 9 不是有效的八进制数字。 八进制数字的示例有0177、0713。 - 准确的数字字面值为不带小数点的数字值,例如
57、-957和+62。 准确的数字字面值结尾可以有大写或小写的 L;这不会影响数字的存储方式和理解方式。 IBM MQ 支持范围在-9,223,372,036,854,775,808到9,223,372,036,854,775,807之间的精确数字。 - 近似数字字面值是科学记数法格式的数字值,如
7E3或-57.9E2,或带有小数点的数字值,如7.、-95.7或+6.2。 IBM MQ 支持-1.797693134862315E+308到1.797693134862315E+308范围内的数字。有效数字应跟在可选符号字符(
+或-)后。 有效数字应为整数或小数。 有效数字的小数部分不需要前导数字。大写或小写的
E表示可选指数的开头。 指数有十进制基数,指数的数字部分可以加上可选符号字符前缀。近似数字字面值可以以
F或D字符(不区分大小写)结尾。 此语法的存在用于支持跨语言标记单精度或双精度数字的方式。 这些字符为可选字符,不会影响近似数字字面值的存储和处理方式。 始终会使用双精度存储和处理这些数字。 - 布尔文字
TRUE和FALSE。
注: 在选择字符串中不支持非有限 IEEE-754 表示,例如NaN,+Infinity和-Infinity。 因此不能使用这些值作为表达式中的操作数。 对于数学运算而言,负零将视为与正零相同。 - 标识符:
标识符是长度可变的字符顺序,必须以有效的标识符起始符开头,后跟零个或更多有效标识符组成字符。 标识符名称的规则与报文属性名称的规则相同,更多信息请参阅 Property names 和 Property name restrictions 。
注: 仅当扩展消息选择提供程序可用时,才能对消息有效内容执行选择。标识为头字段引用或属性引用。 尽管会尽量执行数字提升,但消息选择器内属性值的类型必须与用于设置属性的类型对应。 如果出现类型不匹配,表达式的结果将为
FALSE。 如果引用了消息中不存在的属性,其值将为NULL。当属性用在消息选择器表达式中时,适用于属性获取方法的类型转换不适用。 例如,如果您将属性设置为字符串值,然后使用选择器按照数字值查询此属性,表达式将返回
FALSE。映射到属性名称或 MQMD 字段名称的 JMS 字段和属性名称也是选择字符串中的有效标识。 IBM MQ 将识别的 JMS 字段和属性名称映射到消息属性值。 有关详细信息,请参阅 JMS 中的消息选择器。 例如,选择字符串
在当前消息的 jms 文件夹中的 Pri 属性上选择。JMSPriority >=
- 溢出/下溢:对于十进制和近似数字,未定义以下条件:
- 指定不在定义范围内的数字
- 指定将导致溢出或下溢的算术表达式
- 空格:定义为空格、换页符、换行符、回车符、横向制表符或纵向制表符。 以下 Unicode 字符将识别为空格:
\u0009 to \u000D\u0020\u001C\u001D\u001E\u001F\u1680\u180E\u2000至\u200A\u2028\u2029\u202F\u205F\u3000
- 表达式:
- 选择器是条件表达式。 求值结果为 true 的选择器匹配;结果为 false 或未知值的选择器不匹配。
- 算术表达式由自身、算术运算、标识符(标识符值被视为数字字面值)和数字字面值组成。
- 条件表达式由其自身、比较运算符以及逻辑运算符组成。
- 支持用于设置表达式求值顺序的标准括号 ()。
- 按照优先顺序排列的逻辑运算符:
NOT、AND、OR。 - 比较运算符:
=、>、>=、<、<=、<>(不等于)。- 两个字节字符串只有在长度相同且字节顺序相同的情况下才相等。
- 只能比较相同类型的值。 一个例外是,将精确数字值与近似数字值进行比较是有效的 (所需类型转换由 Java 数字提升的规则定义)。 如果尝试比较不同的类型,那么选择器将始终为 false。
- 字符串和布尔值比较限制为
=和<>。 两个字符串只有在包含相同顺序的字符时才相等。
- 按照优先顺序排列的算术运算符:
+,-一元。*乘法和/除法。+加法和-减法。- 不支持对 NULL 值使用算术运算。 如果尝试使用,那么整个选择器均始终为 false。
- 算术运算必须使用 Java 数字提升。
- arithmetic-expr1 [
NOT]BETWEENarithmetic-expr2 and arithmetic-expr3 比较运算符:Age BETWEEN 15 and 19等于age>= 15 AND age <= 19。Age NOT BETWEEN 15 and 19等于age < 15 OR age > 19。- 如果任何
BETWEEN运算的表达式为 NULL,那么运算值为 false。 如果任何NOT BETWEEN运算的表达式为NULL,那么运算值为 true。
- 标识
[NOT] IN (string-literal1, string-literal2,...)比较运算符,其中标识具有字符串或NULL值。Country IN ('UK', 'US', 'France')对于'UK'为 true,对于'Peru'为 false。 它相当于表达式(Country = 'UK') OR (Country = 'US') OR (Country = 'France')。Country NOT IN ('UK', 'US', 'France')对于'UK'为 false,对于'Peru'为 true。 它相当于表达式NOT ((Country = 'UK') OR (Country = 'US') OR (Country = 'France'))。- 如果
IN或NOT IN运算的标识符为 NULL,那么运算值未知。
identifier [NOT] LIKE pattern-value [ESCAPE escape-character ]比较运算符,其中identifier具有字符串值。 pattern-value 是字符串字面值,其中_代表任意单个字符,而%代表任何字符序列(包括空序列)。 所有其他字符均代表其自身。 可选的 escape-character 是单个字符串文字,用于对 pattern-value中_和%的特殊含义进行转义。LIKE运算符只能用于比较两个字符串值。phone LIKE '12%3'对于 123 和 12993 为 true,对于 1234 为 false。word LIKE 'l_se'对于 lose 为 true,对于 loose 为 false。underscored LIKE '\_%' ESCAPE '\'对于_foo为 true,对于bar为 false。phone NOT LIKE '12%3'对于123和12993为 false,对于1234为 true。- 如果
LIKE或NOT LIKE运算的标识符为NULL,那么此运算的值为 unknown。
注: 必须使用LIKE运算符来比较两个字符串值。Root.MQMD.CorrelId的值为 24 字节的字节数组,而不是字符串。 解析器接受选择器字符串Root.MQMD.CorrelId LIKE 'ABC%'作为有效语法,但会求值为 false。 因此在比较字节数组和字符串时,不会使用LIKE。identifier IS NULL比较运算符测试是否存在NULL头字段值或是否缺失属性值。identifier IS NOT NULL比较运算符测试是否存在非空头字段值或属性值。- null 值总而言之,包含
NULL值的选择器表达式的求值由 SQL 92NULL语义定义:- SQL 将
NULL值视为 unknown。 - 带有 unknown 值的比较或算术始终会产生 unknown 值。
IS NULL和IS NOT NULL运算符可将 unknown 值转换为TRUE和FALSE值。
T=TRUE、F=FALSE和U=UNKNOWN)表 1. 逻辑为 A AND B时布尔运算符结果的值运算符 A 运算符 B 结果 (A AND B) TFFTUUTTTFTFFUFFFFUTUUUUUFF表 2. 逻辑为 A OR B时布尔运算符结果的值运算符 A 运算符 B 结果 ( A OR B)TFTTUTTTTFTTFUUFFFUTTUUUUFU表 3. 逻辑为 NOT A时布尔运算符结果的值运算符 A 结果 ( NOT A)TFFTUU - SQL 将
"JMSType = 'car' AND color = 'blue' AND weight > 2500"
尽管 SQL 支持固定的小数比较和算术,但消息选择器并不支持。 这是因为精确数字字面值限制为不带小数点的数字。 还因为某些带有小数点的数字作为近似数字值的替代表示。
不支持 SQL 注释。