查询标记

Important

此功能目前以公共预览版提供。

本页介绍如何使用查询标记对 Databricks SQL 仓库上的 SQL 工作负荷进行分组、筛选和跟踪成本。

查询标记是应用于 SQL 工作负荷的自定义键值对。 可以使用查询标记按业务上下文对查询进行分组,跟踪仓库成本,并确定长时间运行的查询的来源。

标记显示在 system.query.history 表中,以及Azure Databricks UI 的 Query History 页上。 ListQueries API 还会在存在时返回标记。 例如,可以标记用于跟踪营销工作负荷成本的查询 team:marketing ,或 dbt_model_name:some_model_name 标识特定 dbt 模型生成的查询。

警告

标记数据以纯文本形式存储,可全局复制。 请勿在标记键或值中包含密码、个人身份信息或其他敏感数据。

要求

若要使用查询标记,必须具有以下各项:

  • 必须有权访问 query_tags 表中的 system.query.history 列。 如果没有访问权限,请联系帐户管理员。请参阅 查询历史记录系统表参考

  • 连接器或驱动程序必须满足最低版本要求。 有关版本详细信息,请参阅 “从工具和连接器设置查询标记 ”中的特定工具或连接器部分。

  • databricks SDK for Python:查询标记支持的最低版本 0.86.0。

查询标记的工作原理

查询标记的范围限定为 Databricks SQL 会话。 可以在会话级别或语句级别设置它们:

  • 会话级标记 适用于会话中的所有后续语句。 在使用配置参数创建会话时设置这些参数,或者在会话中使用 SET QUERY_TAGS SQL 语句进行设置。
  • 语句级标记 仅适用于单个语句。 后续语句将还原为会话级标记。 Python连接器(v4.2.6 或更高版本)、Node.js 连接器(v1.12.0 或更高版本)、Go 连接器(v1.9.0 或更高版本)和语句执行 API 中提供语句级标记。

会话配置参数语法

多个工具和连接器支持将查询标签用作名为 query_tags 的会话配置参数(对于基于 Simba 的驱动程序,则为 ssp_query_tags)。 该值是键值对的序列化字符串,其中冒号 (:) 分隔键和值以及逗号 (,) 分隔对。

如果键或值包含冒号()、逗号(:,)或反斜杠(\),则用前导反斜杠对其进行转义。

以下示例指定了标记 team:engcost_center:701、仅包含键的标记 exp,以及带有 JSON 值的 metadata 标记。

未转义意向:

team:eng, cost_center:701, exp, metadata:{"foo":"bar","baz":1}

转义的配置字符串:

query_tags = team:eng,cost_center:701,exp,metadata:{"foo"\\:"bar"\\,"baz"\\:1}

SQL 语句

使用 SET QUERY_TAGS 语句设置、读取或删除当前会话的查询标记。 可以在任意位置使用此语句,以便将 SQL 提交到仓库,包括 SQL 编辑器、笔记本和仪表板。

有关语法、参数和示例,请参阅 SET QUERY_TAGS

从工具和连接器设置查询标记

以下部分介绍如何从每个受支持的工具、连接器和驱动程序设置查询标记。

Databricks SQL 语句执行 API (SEA)

query_tags 字段包含在 POST /api/2.0/sql/语句 的请求正文中,以应用语句级标记。 以这种方式设置的标记仅适用于该语句执行。

curl -X POST "https://${DATABRICKS_HOST}/api/2.0/sql/statements" \
  -H "Authorization: Bearer ${DATABRICKS_TOKEN}" \
  -H "Content-Type: application/json" \
  -d '{
    "warehouse_id": "abc123",
    "statement": "SELECT * FROM samples.nyctaxi.trips LIMIT 10",
    "query_tags": [
        { "key": "team", "value": "engineering" },
        { "key": "env", "value": "prod" }
      ]
  }'

dbt

最低版本:dbt-databricks 1.11.0

以下保留查询标记键会为所有 dbt 运行自动设置,也无法更改:

{
  "dbt_model_name": "my_model",
  "dbt_core_version": "1.10.7",
  "dbt_databricks_version": "1.11.0",
  "dbt_materialized": "incremental"
}

Note

默认标记受语法限制的约束。 包含未转义冒号或逗号的模型名称会导致系统表中出现 tag_invalid: true

可以在项目和模型级别添加自定义查询标记。 模型配置优先于连接配置。

项目级标签

文件:~/.dbt/profiles.yml

your_profile_name:
  target: dev
  outputs:
    dev:
      query_tags: '{"team": "marketing", "cost_center": "3000"}'

模型级标签

文件:~/.dbt/dbt_project.yml

name: 'your_project'
version: '1.0.0'
config-version: 2
models:
  your_model:
    +query_tags: '{"team": "content-marketing"}'

这两种配置下的结果

设置项目级标记和模型级标记时,将合并标记。 模型级值会覆盖相同键的项目级值。

  "team": "content-marketing",
  "cost_center": "3000",
  "dbt_model_name": "model.dev.your_model",
  "dbt_core_version": "1.10.7",
  "dbt_databricks_version": "1.11.0",
  "dbt_materialized": "incremental"
}

Power BI

最低版本:2025 年 10 月版本

  1. 配置与仓库的连接。
  2. 转到“Azure Databricks设置”对话框。 Power BI 中的 Databricks 设置对话框。
  3. “查询标记 ”文本框中,使用 会话配置参数语法输入查询标记。
  4. 单击 “确定”

Note

更改查询标记并单击 “确定 ”将启动一个新会话。 以前设置的标记将被丢弃。

启用自动查询标记

自动查询标记自动将Power BI上下文元数据附加到发送到Azure Databricks仓库的查询。 仅当使用 箭头数据库连接(ADBC) 驱动程序时,自动查询标记才可用。 ODBC 驱动程序不支持它们。

若要启用自动查询标记,请修改Power Query 编辑器中的 M 查询,以在连接参数中包含 EnableAutoQueryTags="true"

  1. 在 Power BI Desktop 或 Power BI 服务 中,找到包含要标记的查询的语义模型。

  2. 打开 Power Query 编辑器

  3. 打开 高级编辑器

  4. EnableAutoQueryTags="true" 添加到连接器调用选项中。

    连接器调用为 Databricks.Catalogs.

以下示例显示了已启用自动查询标记的 M 查询:

let
    Source = Databricks.Catalogs(
        "adb-<workspace-id>.<random-number>.azuredatabricks.net",
        "/sql/1.0/warehouses/abc123",
        [Catalog=null, Database=null, EnableAutoQueryTags="true",
         EnableAutomaticProxyDiscovery=null, Implementation="2.0"]),
    samples_Database = Source{[Name="samples",Kind="Database"]}[Data],
    nyctaxi_Schema = samples_Database{[Name="nyctaxi",Kind="Schema"]}[Data],
    trips_Table = nyctaxi_Schema{[Name="trips",Kind="Table"]}[Data]
in
    trips_Table

启用自动查询标记后,Power BI会自动将以下保留标记(前缀为 @@)附加到查询。 可用的标记取决于Power BI连接模式:

标记键 DirectQuery Import
@@powerbi_activity_id 是的 是的
@@powerbi_dataset_id 是的
@@powerbi_report_id 是的
@@powerbi_visual_id 是的

Note

在任何模式下,自动查询标记都不会附加到元数据查询(如目录发现查询或架构发现查询)。

将该设置参数化

如果语义模型包含多个表,请将 EnableAutoQueryTags 定义为Power Query参数,以便你可以打开或关闭单个位置的设置,而不是单独编辑每个查询。

  1. Power Query 编辑器 中,选择 Manage Parameters>New Parameter
  2. 创建一个名为 EnableAutoQueryTags 的参数,其类型为 Text,当前值为 "true"
  3. 在每个查询中,将硬编码 EnableAutoQueryTags="true" 替换为对参数的引用。

以下示例演示引用参数的 M 查询:

let
    Source = Databricks.Catalogs(
        "adb-<workspace-id>.<random-number>.azuredatabricks.net",
        "/sql/1.0/warehouses/abc123",
        # highlight-next-line
        [Catalog=null, Database=null, EnableAutoQueryTags=EnableAutoQueryTags,
         EnableAutomaticProxyDiscovery=null, Implementation="2.0"]),
    samples_Database = Source{[Name="samples",Kind="Database"]}[Data],
    nyctaxi_Schema = samples_Database{[Name="nyctaxi",Kind="Schema"]}[Data],
    trips_Table = nyctaxi_Schema{[Name="trips",Kind="Table"]}[Data]
in
    trips_Table

Tableau

使用初始 SQL 功能在 Tableau 中设置查询标记。

  1. 配置与仓库的连接。
  2. 导航到 “初始 SQL ”选项卡。
  3. 使用 SET QUERY_TAGS输入查询标记。 可以在键或值中包含 Tableau 参数。
  4. 单击 “登录 ”保存并进行身份验证。

Note

更改初始 SQL 并单击 “登录 ”会启动一个新会话。 以前设置的标记将被丢弃。

Python 连接器

最低版本:v4.1.3(会话级别)、v4.2.6(语句级别)

会话级标记

创建连接时传递 query_tags 参数。 会话中的所有语句都继承这些标记。

from databricks import sql
import os

with sql.connect(
    server_hostname = os.getenv("DATABRICKS_SERVER_HOSTNAME"),
    http_path       = os.getenv("DATABRICKS_HTTP_PATH"),
    access_token    = os.getenv("DATABRICKS_TOKEN"),
    query_tags = {"team": "engineering", "dashboard": "abc123"}
) as connection:
    with connection.cursor() as cursor:
        cursor.execute("SELECT * FROM samples.nyctaxi.trips LIMIT 10")
        result = cursor.fetchall()

语句级标记

query_tags 传递给 cursor.execute() 以标记单条语句。 后续语句将还原为会话级标记。

from databricks import sql
import os

with sql.connect(
    server_hostname = os.getenv("DATABRICKS_SERVER_HOSTNAME"),
    http_path       = os.getenv("DATABRICKS_HTTP_PATH"),
    access_token    = os.getenv("DATABRICKS_TOKEN"),
) as connection:
    with connection.cursor() as cursor:
        cursor.execute(
            "SELECT * FROM samples.nyctaxi.trips LIMIT 10",
            query_tags={"team": "engineering", "dashboard": "abc123"}
        )
        result = cursor.fetchall()

Node.js 连接器

最低版本:v1.12.0

会话级标记

打开会话时传递 queryTags 。 会话中的所有语句都继承这些标记。

const { DBSQLClient } = require('@databricks/sql');
const client = new DBSQLClient();

client
  .connect({
    host: process.env.DATABRICKS_SERVER_HOSTNAME,
    path: process.env.DATABRICKS_HTTP_PATH,
    token: process.env.DATABRICKS_TOKEN,
  })
  .then(async (client) => {
    const session = await client.openSession({
      queryTags: {
        team: 'engineering',
        env: 'prod',
      },
    });

    const queryOperation = await session.executeStatement('SELECT * FROM samples.nyctaxi.trips LIMIT 10');
    const result = await queryOperation.fetchAll();

    await queryOperation.close();
    await session.close();
    await client.close();
  })
  .catch((error) => {
    console.error(error);
  });

语句级标记

queryTags 传递给 executeStatement() 以标记单条语句。 后续语句将还原为会话级标记。

const { DBSQLClient } = require('@databricks/sql');
const client = new DBSQLClient();

client
  .connect({
    host: process.env.DATABRICKS_SERVER_HOSTNAME,
    path: process.env.DATABRICKS_HTTP_PATH,
    token: process.env.DATABRICKS_TOKEN,
  })
  .then(async (client) => {
    const session = await client.openSession();

    const queryOperation = await session.executeStatement('SELECT * FROM samples.nyctaxi.trips LIMIT 10', {
      queryTags: {
        team: 'engineering',
        request_id: 'abc-123',
      },
    });
    const result = await queryOperation.fetchAll();

    await queryOperation.close();
    await session.close();
    await client.close();
  })
  .catch((error) => {
    console.error(error);
  });

Go 连接器

最低版本:v1.9.0

DSN 连接字符串

query_tags 作为查询参数包含在 DSN 字符串中。

package main
    "database/sql"
    "fmt"
    _ "github.com/databricks/databricks-sql-go"
)

func main() {
    dsn := "token:dapi1234@myworkspace.cloud.databricks.com:443/sql/1.0/endpoints/abc123?query_tags=team:engineering,env:prod"

    db, err := sql.Open("databricks", dsn)
    if err != nil {
        panic(err)
    }
    defer db.Close()

    rows, err := db.Query("SELECT * FROM samples.nyctaxi.trips LIMIT 10")
    if err != nil {
        panic(err)
    }
    defer rows.Close()
}

带有 WithQueryTags 的 NewConnector

用于 WithQueryTags 从映射中设置会话级标记。 连接器会自动处理序列化。

package main

import (
    "database/sql"
    "os"
    dbsql "github.com/databricks/databricks-sql-go"
)

func main() {
    connector, err := dbsql.NewConnector(
        dbsql.WithAccessToken(os.Getenv("DATABRICKS_ACCESS_TOKEN")),
        dbsql.WithServerHostname(os.Getenv("DATABRICKS_HOST")),
        dbsql.WithPort(443),
        dbsql.WithHTTPPath(os.Getenv("DATABRICKS_HTTP_PATH")),
        dbsql.WithQueryTags(map[string]string{
            "team": "engineering",
            "env":  "prod",
        }),
    )
    if err != nil {
        panic(err)
    }

    db := sql.OpenDB(connector)
    defer db.Close()

    rows, err := db.Query("SELECT * FROM samples.nyctaxi.trips LIMIT 10")
    if err != nil {
        panic(err)
    }
    defer rows.Close()
}

语句级标记

用于 driverctx.NewContextWithQueryTags 将标记附加到单个语句。 将生成的上下文传递给 QueryContextExecContext.

package main

import (
    "context"
    "database/sql"
    "os"
    dbsql "github.com/databricks/databricks-sql-go"
    "github.com/databricks/databricks-sql-go/driverctx"
)

func main() {
    connector, err := dbsql.NewConnector(
        dbsql.WithAccessToken(os.Getenv("DATABRICKS_ACCESS_TOKEN")),
        dbsql.WithServerHostname(os.Getenv("DATABRICKS_HOST")),
        dbsql.WithPort(443),
        dbsql.WithHTTPPath(os.Getenv("DATABRICKS_HTTP_PATH")),
    )
    if err != nil {
        panic(err)
    }

    db := sql.OpenDB(connector)
    defer db.Close()

    ctx := driverctx.NewContextWithQueryTags(context.Background(), map[string]string{
        "team":        "data-eng",
        "application": "etl-pipeline",
    })

    rows, err := db.QueryContext(ctx, "SELECT * FROM samples.nyctaxi.trips LIMIT 10")
    if err != nil {
        panic(err)
    }
    defer rows.Close()
}

JDBC 驱动程序 (OSS)

最低版本:v3.0.3

连接 URL

query_tags 直接包含在 JDBC 连接 URL 字符串中。

String url = "jdbc:databricks://myworkspace.cloud.databricks.com:443/default;" +
             "httpPath=/sql/1.0/endpoints/abc123;" +
             "query_tags=team:engineering,env:prod;" +
             "AuthMech=3;UID=token;PWD=dapi1234";
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT * FROM samples.nyctaxi.trips LIMIT 10");

Properties 对象

还可以使用query_tags对象设置Properties

String url = "jdbc:databricks://myworkspace.cloud.databricks.com:443/default";
Properties properties = new Properties();
properties.put("httpPath", "/sql/1.0/endpoints/abc123");
properties.put("query_tags", "team:engineering,env:prod");
properties.put("UID", "token");
properties.put("PWD", "dapi1234");

Connection conn = DriverManager.getConnection(url, properties);
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT * FROM samples.nyctaxi.trips LIMIT 10");

JDBC 驱动程序 (Simba)

Simba 驱动程序使用参数名称 ssp_query_tags 而不是 query_tags

连接 URL

在 JDBC 连接 URL 字符串中包含 ssp_query_tags

String url = "jdbc:databricks://myworkspace.cloud.databricks.com:443;" +
             "httpPath=/sql/1.0/endpoints/abc123;" +
             "ssp_query_tags=team:engineering,env:prod;" +
             "AuthMech=3;UID=token;PWD=dapi1234";

Connection conn = DriverManager.getConnection(url);
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT * FROM samples.nyctaxi.trips LIMIT 10");

Properties 对象

还可以使用ssp_query_tags对象设置Properties

String url = "jdbc:databricks://myworkspace.cloud.databricks.com:443";
Properties properties = new Properties();
properties.put("httpPath", "/sql/1.0/endpoints/abc123");
properties.put("ssp_query_tags", "team:engineering,env:prod");
properties.put("AuthMech", "3");
properties.put("UID", "token");
properties.put("PWD", "dapi1234");

Connection conn = DriverManager.getConnection(url, properties);
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT * FROM samples.nyctaxi.trips LIMIT 10");

ODBC 驱动程序

在 ODBC 连接配置中包含参数 ssp_query_tags 。 还必须在连接配置中设置 ApplySSPWithQueries=0

查看查询标记

查询system.query.history表以查看查询标签。 可以按键或键值对进行分组和筛选。

SELECT statement_id, query_tags, executed_by, start_time
FROM system.query.history
WHERE MAP_CONTAINS_KEY(query_tags, 'team')
  AND query_tags['team'] = 'engineering'
ORDER BY start_time DESC
LIMIT 100;

仅键标记会显示一个 null 值。 若要按仅含键的标签进行筛选:

WHERE MAP_CONTAINS_KEY(query_tags, 'key') AND query_tags['key'] IS NULL

有关详细信息,请参阅 查询历史记录系统表参考

局限性

以下限制适用于查询标记。

一般限制

以下限制适用于所有查询标记,而不考虑这些标记的设置方式。

  • 仅 Databricks SQL 工作负荷支持查询标记。 该列不会为其他计算类型填充。
  • 每个会话的查询标记限制为 10 KB。 如果总大小超过此限制,则会丢弃传入的标记,并添加一个 tags_dropped: true 哨兵标记。
  • 每个查询最多支持 20 个用户指定的标记。
  • 标记键和值不得超过 128 个字符。
  • 标记键不得包含字符,:-/=.
  • 开头的 @@ 密钥保留供内部使用。

会话配置参数行为

使用会话配置参数(而不是 SQL)设置标记时,将应用以下附加行为:

  • 超过 20 个标签上限的标签将被丢弃,并添加一个 tag_truncated: true 哨兵标签。
  • 键或值超过 128 个字符的标记,以及键包含无效字符的标记,都会被丢弃,并添加一个 tag_invalid: true 哨兵标记。

使用 SQL 语句设置标记时,无效标记键会导致语句在执行时失败并出现错误。