限制
SQL 插件有以下限制
不支持对表达式进行聚合
只能将聚合应用于字段。聚合不能接受表达式作为参数。例如,不支持 avg(log(age))
。
FROM 子句中的子查询
仅当查询合并为一个查询时,才支持 FROM
子句中以下格式的子查询:SELECT outer FROM (SELECT inner)
。例如,以下查询受支持
SELECT t.f, t.d
FROM (
SELECT FlightNum as f, DestCountry as d
FROM opensearch_dashboards_sample_data_flights
WHERE OriginCountry = 'US') t
但是,如果外部查询包含 GROUP BY
或 ORDER BY
,则不受支持。
JOIN 查询
由于 OpenSearch 不原生支持关系操作,JOIN
查询仅作为尽力而为的功能受支持。
JOIN 不支持对连接结果进行聚合
JOIN
查询不支持对连接结果进行聚合。
例如,不支持 SELECT depo.name, avg(empo.age) FROM empo JOIN depo WHERE empo.id = depo.id GROUP BY depo.name
。
性能
JOIN
查询容易产生昂贵的索引扫描操作。
当处理超过 500 万条匹配记录的结果集时,JOIN
查询可能会遇到性能问题。要提高 JOIN
性能,请首先通过过滤数据来减少要连接的记录数量。例如,将连接限制在特定范围的键值
SELECT l.key, l.spanId, r.spanId
FROM logs_left AS l
JOIN logs_right AS r
ON l.key = r.key
WHERE l.key >= 17491637400000
AND l.key < 17491637500000
AND r.key >= 17491637400000
AND r.key < 17491637500000
LIMIT 10
默认情况下,JOIN 查询会在 60 秒后自动终止,以防止过多的资源消耗。您可以使用查询中的提示调整此超时时间。例如,要设置 5 分钟(300 秒)超时,请使用以下代码
SELECT /*! JOIN_TIME_OUT(300) */ left.a, right.b FROM left JOIN right ON left.id = right.id;
当查询外部数据源时,这些性能限制不适用。
分页仅支持基本查询
分页查询使您能够获得分页响应。
目前,分页仅支持基本查询。例如,以下查询返回带有游标 ID 的数据。
POST _plugins/_sql/
{
"fetch_size" : 5,
"query" : "SELECT OriginCountry, DestCountry FROM opensearch_dashboards_sample_data_flights ORDER BY OriginCountry ASC"
}
带有游标 ID 的 JDBC 格式响应。
{
"schema": [
{
"name": "OriginCountry",
"type": "keyword"
},
{
"name": "DestCountry",
"type": "keyword"
}
],
"cursor": "d:eyJhIjp7fSwicyI6IkRYRjFaWEo1UVc1a1JtVjBZMmdCQUFBQUFBQUFCSllXVTJKVU4yeExiWEJSUkhsNFVrdDVXVEZSYkVKSmR3PT0iLCJjIjpbeyJuYW1lIjoiT3JpZ2luQ291bnRyeSIsInR5cGUiOiJrZXl3b3JkIn0seyJuYW1lIjoiRGVzdENvdW50cnkiLCJ0eXBlIjoia2V5d29yZCJ9XSwiZiI6MSwiaSI6ImtpYmFuYV9zYW1wbGVfZGF0YV9mbGlnaHRzIiwibCI6MTMwNTh9",
"total": 13059,
"datarows": [[
"AE",
"CN"
]],
"size": 1,
"status": 200
}
目前不支持带有 aggregation
和 join
的查询进行分页。
查询处理引擎
在 OpenSearch 3.0.0 之前,SQL 插件使用两个查询处理引擎:V1
和 V2
。两个引擎都支持大多数功能,但只有 V2
处于积极开发中。当您运行查询时,插件首先尝试使用 V2
引擎执行它,如果执行失败则回退到 V1
。如果查询在 V2
中受支持但在 V1
中不受支持,则查询将失败并返回错误响应。
从 OpenSearch 3.0.0 开始,SQL 插件引入了一个新的查询引擎(V3
),它利用 Apache Calcite 进行查询优化和执行。由于 V3
是 OpenSearch 3.0.0 中的一个实验性功能,默认情况下它是禁用的。要启用此新引擎,请将 plugins.calcite.enabled
设置为 true
。与 V2
到 V1
的回退逻辑类似,当您运行查询时,插件首先尝试使用 V3
引擎执行它,如果执行失败则回退到 V2
。有关 V3
的更多信息,请参阅 PPL Engine V3。
V1 引擎限制
V1
查询引擎是 OpenSearch 中最初的 SQL 处理引擎。虽然它已在很大程度上被更新的引擎取代,但了解其限制有助于解释某些查询行为,尤其是在查询从 V2
回退到 V1
时。以下限制专门适用于 V1
引擎
- 不支持没有
FROM
子句的选择字面量表达式。例如,不支持SELECT 1
。 WHERE
子句不支持表达式。例如,不支持SELECT FlightNum FROM opensearch_dashboards_sample_data_flights where (AvgTicketPrice + 100) <= 1000
。- 大多数相关性搜索函数仅在
V2
引擎中实现。
除非这些查询包含 V1
特定的函数,否则它们会由 V2
引擎成功执行。您可能永远不会遇到这些限制。
V2 引擎限制
V2
查询引擎处理大多数现代 SQL 查询模式。但是,它有一些限制可能会影响您的查询开发,特别是对于复杂的分析工作负载。了解这些限制可以帮助您设计与 OpenSearch 最佳配合的查询
- 游标功能仅由
V1
引擎支持。- 有关
V2
引擎中cursor
/pagination
的支持,请跟踪 GitHub 问题 #656。
- 有关
json
格式输出仅在V1
引擎中支持。V2
引擎不跟踪查询执行时间,因此不会报告慢查询。V2
查询引擎不仅在 OpenSearch 引擎中运行查询,还支持复杂查询的后处理。因此,explain
输出不再是 OpenSearch 领域特定语言 (DSL),而是还包括来自V2
查询引擎的查询计划信息。V2
查询引擎不支持聚合查询,例如histogram
、date_histogram
、percentiles
、topHits
、stats
、extended_stats
、terms
或range
。- 不支持 JOIN 和子查询。要了解 JOIN 和子查询的最新开发情况,请跟踪 GitHub 问题 #1441 和 GitHub 问题 #892。
- OpenSearch 不原生支持数组数据类型,但隐式允许多值字段。SQL/PPL 插件严格遵守索引映射中定义的数据类型语义。解析 OpenSearch 响应时,它期望数据与声明的类型匹配,并且不解释数组中的所有数据。如果启用了
plugins.query.field_type_tolerance
设置,SQL/PPL 插件会通过返回标量数据类型来处理数组数据集,从而允许基本查询(例如,SELECT * FROM tbl WHERE condition
)。但是,在表达式或函数中使用多值字段将导致异常。如果此设置被禁用或未设置,则仅返回数组的第一个元素,从而保留默认行为。 - 不支持
nested
查询的 PartiQL 语法。
V3 引擎的限制
V3
查询引擎使用 Apache Calcite 提供了增强的查询处理能力。作为 OpenSearch 3.0.0 中的实验性功能,它在开发查询时有一些您应该注意的限制和行为差异。这些限制分为三类:新限制、不支持的功能和行为更改。
限制
V3
引擎引入了对 OpenSearch 元数据字段更严格的验证。在使用操作字段名称的命令时,请注意以下限制
eval
不允许您使用OpenSearch 元数据字段作为字段。rename
不允许重命名为OpenSearch 元数据字段。as
不允许您使用OpenSearch 元数据字段作为别名。
不支持的功能
V3
引擎不支持以前引擎中可用的所有功能。对于以下功能,查询将自动转发到 V2
查询引擎
趋势线
显示数据源
描述
top
和rare
fillnull
模式
- 带有
consecutive=true
的dedup
- 搜索相关命令
AD
ML
Kmeans
- 带有
fetch_size
参数的命令 - 带有元数据字段(例如
_id
或_doc
)的查询 - JSON 相关函数
转换为 json
json(JSON)
json_valid
- 搜索相关函数
match
match_phrase
match_bool_prefix
match_phrase_prefix
simple_query_string
query_string
multi_match
V2 与 V3 对比
由于 V3
引擎内部使用了不同的实现,因此某些行为已与以前的版本发生变化。V3
中的行为被认为是正确的,但它们可能与 V2
中相同查询产生不同的结果。下表强调了这些差异。
项目 | V2 | V3 |
---|---|---|
timestampdiff 的返回类型 | 时间戳 | 整数 |
regexp 的返回类型 | 整数 | 布尔值 |
count 、dc 、distinct_count 的返回类型 | 整数 | 大整数 |
ceiling 、floor 、sign 的返回类型 | 整数 | 与输入相同的类型 |
值“Amber JOHnny”上的 like(firstname, 'Ambe_') | true | false |
值“Amber JOHnny”上的 like(firstname, 'Ambe*') | true | false |
cast(firstname as boolean) | false | null |
启用 pushdown 时多个 null 值的总和 | 0 | null |
percentile(null, 50) | 0 | null |