다음을 통해 공유

查询数据

查询数据是在 Azure Databricks 中执行几乎所有数据驱动任务的基础步骤。 无论使用何种语言或工具,工作负载首先针对表或其他数据源定义查询,然后执行操作以从数据中获取见解。 本文概述了跨各种 Azure Databricks 产品/服务运行查询的核心概念和过程,并包含可根据你的用例进行调整的代码示例。

可以使用以下方法以交互方式查询数据:

  • Notebooks
  • SQL 编辑器
  • 文件编辑器
  • 仪表板

还可以在 Lakeflow 声明性管道或作业中运行查询。

有关 Azure Databricks 上的流式查询的概述,请参阅查询流式数据

可以使用 Azure Databricks 查询哪些数据?

Azure Databricks 支持查询多种格式、多种企业系统内的数据。 使用 Azure Databricks 查询的数据属于以下两大类之一:Databricks 湖屋中的数据和外部数据。

Databricks 湖屋中有哪些数据?

默认情况下,Databricks Data Intelligence Platform 会将所有数据存储在 Databricks 湖屋中。

这意味着,当你运行基本 CREATE TABLE 语句来创建新表时,你已创建了一个湖屋表。 湖屋数据具有以下属性:

  • 以 Delta Lake 格式存储。
  • 存储在云对象存储中。
  • 受 Unity Catalog 管理。

Azure Databricks 上的大部分湖屋数据以托管表的形式注册在 Unity Catalog 中。 托管表提供最简单的语法,其行为与大多数关系数据库管理系统中的其他表类似。 对于大多数用例,建议使用托管表,托管表适合不想考虑数据存储实现详细信息的所有用户。

非托管表(或外部表)是在指定了 LOCATION 的情况下注册的表。 “外部”一词可能会产生误导,因为外部 Delta 表仍然是湖屋数据。 直接从其他 Delta 读取器客户端访问表的用户可能会首选非托管表。 有关表语义差异的概述,请参阅 Azure Databricks 表

某些旧式工作负载可能会通过文件路径与 Delta Lake 数据专门交互,并且根本不注册表。 此数据仍然是 Lakehouse 数据,但可能更难发现,因其未注册到 Unity Catalog。

注意

你的工作区管理员可能尚未升级你的数据治理以使用 Unity Catalog。 即使没有 Unity Catalog,你也仍然可以获得 Databricks 湖屋的许多好处,但在本文或整个 Azure Databricks 文档中列出的所有功能并非均受支持。

哪些数据被视为外部数据?

任何不在 Databricks lakehouse 中的数据都可以视为外部数据。 外部数据的一些示例包括:

  • 向 Lakehouse Federation 注册的外来表。
  • 受 Parquet 支持的 Hive 元存储中的表。
  • 受 JSON 支持的 Unity Catalog 中的外部表。
  • 存储在云对象存储中的 CSV 数据。
  • 从 Kafka 读取的流式数据。

Azure Databricks 支持配置与许多数据源的连接。 请参阅 “连接到数据源和外部服务”。

虽然可以针对以多种格式、在多种外部系统中存储的数据使用 Unity Catalog 来管理对这些数据的访问并定义表,但若要使数据可被视为湖屋中的数据,Delta Lake 就是一个必要条件了。

Delta Lake 在 Azure Databricks 中提供所有事务性保证,这对于保持数据完整性和一致性至关重要。 若要详细了解 Azure Databricks 数据的事务保证及其重要性,请参阅 Azure Databricks 上的 ACID 保证是什么?

大多数 Azure Databricks 用户查询湖屋数据和外部数据的组合。 与外部数据进行连接始终是用于将数据引入到湖屋的数据引入和 ETL 管道的第一步。 有关引入数据的信息,请参阅 Lakeflow Connect 中的标准连接器

按名称查询表

对于注册为表的所有数据,Databricks 建议使用表名称进行查询。

如果使用 Unity Catalog,则表使用以下格式的三层命名空间:<catalog-name>.<schema-name>.<table-name>

如果没有 Unity Catalog,表标识符将使用格式 <schema-name>.<table-name>

注意

Azure Databricks 从 Apache Spark 继承了其大部分 SQL 语法,它不区分 SCHEMADATABASE

所有 Azure Databricks 执行上下文和受支持的语言都支持按表名称查询。

SQL

SELECT * FROM catalog_name.schema_name.table_name

Python

spark.read.table("catalog_name.schema_name.table_name")

Unity Catalog 标识符解析

Databricks 建议在查询或工作负荷与跨多个架构或目录存储的数据库对象交互时使用完全限定的标识符。

下表概述了部分限定和未限定标识符的行为:

标识符模式 行为
catalog_name.schema_name.object_name 引用标识符指定的数据库对象。
schema_name.object_name 指代与当前目录中指定的 schema_nameobject_name 相关联的数据库对象。
object_name 指与当前目录和架构中的指定 object_name 关联的数据库对象。

什么是当前目录和架构?

在交互式计算环境中,使用 current_catalog()current_schema() 来确认当前目录和架构。

使用 Unity 目录配置的所有工作区在工作区级别设置了默认目录。 请参阅 “管理默认目录”。

下表介绍了 Databricks 产品的配置,这些配置可能替代工作区默认目录:

产品 配置
通用或作业计算 在配置计算时设置 Spark 配置 spark.databricks.sql.initial.catalog.namespace
Lakeflow 声明性管道 管道配置期间指定的目录和架构会覆盖所有管道逻辑的工作区默认值。

注意

连接到外部系统或元存储时,也可以由 JDBC 配置设置默认目录或架构。 如果遇到意外的默认行为,请联系负责配置 Databricks 计算和集成系统的管理员。

使用 USE CATALOGUSE SCHEMA 语法指定当前会话的当前目录或架构。 当查询或语句使用部分限定或未限定的缩进器时,将使用当前目录或架构。

声明 结果
USE CATALOG catalog_name 使用提供的 catalog_name 来设置当前目录。 将当前架构设置为 default
USE SCHEMA schema_name 使用当前目录中提供的 schema_name 设置当前架构。
USE SCHEMA catalog_name.schema_name 使用提供的 catalog_name 设置当前目录,使用提供的 schema_name设置当前架构。

注意

使用完全限定标识符与表、视图、函数或模型等对象交互的查询和命令不会更改当前目录或架构,并且始终引用指定的对象。

按路径查询数据

可以使用文件路径查询结构化、半结构化和非结构化的数据。 Azure Databricks 上的大多数文件都由云对象存储提供支持。 请参阅使用 Azure Databricks 上的文件

Databricks 建议使用 Unity Catalog 配置对云对象存储的所有访问权限,并为直接查询的对象存储位置定义卷。 卷使用文件路径的目录和架构名称,为云对象存储中的位置和文件提供人工可读的别名。 请参阅 使用 Unity 目录连接到云对象存储

以下示例演示如何使用 Unity Catalog 卷路径读取 JSON 数据:

SQL

SELECT * FROM json.`/Volumes/catalog_name/schema_name/volume_name/path/to/data`

Python

spark.read.format("json").load("/Volumes/catalog_name/schema_name/volume_name/path/to/data")

对于未配置为 Unity Catalog 卷的云位置,可以使用 URI 直接查询数据。 必须配置对云对象存储的访问权限才能使用 URI 查询数据。 请参阅 使用旧模式为 Azure Databricks 配置对云对象存储的访问权限

以下示例演示如何使用 URI 查询 Azure Data Lake Storage、GCS 和 S3 中的 JSON 数据:

SQL

SELECT * FROM json.`abfss://container-name@storage-account-name.dfs.core.chinacloudapi.cn/path/to/data`;

SELECT * FROM json.`gs://bucket_name/path/to/data`;

SELECT * FROM json.`s3://bucket_name/path/to/data`;

Python

spark.read.format("json").load("abfss://container-name@storage-account-name.dfs.core.chinacloudapi.cn/path/to/data")

spark.read.format("json").load("gs://bucket_name/path/to/data")

spark.read.format("json").load("s3://bucket_name/path/to/data")

使用 SQL 仓库查询数据

Azure Databricks 在以下接口中将 SQL 仓库用于计算:

  • SQL 编辑器
  • Databricks SQL 查询
  • 仪表板
  • 旧版仪表板
  • SQL 警报

可以选择将 SQL 仓库与以下产品配合使用:

  • Databricks 笔记本
  • Databricks 文件编辑器
  • Lakeflow 任务

通过 SQL 仓库查询数据时,只能使用 SQL 语法。 其他编程语言和 API 不受支持。

对于为 Unity Catalog 启用的工作区,SQL 仓库始终使用 Unity Catalog 来管理对数据源的访问。

在 SQL 仓库上运行的大多数查询将表作为目标。 将数据文件作为目标的查询应利用 Unity Catalog 卷来管理对存储位置的访问。

在 SQL 仓库上运行的查询中直接使用 URI 可能会导致意外错误。

使用通用计算或作业计算查询数据

从 Databricks 笔记本、工作流和文件编辑器运行的大多数查询均针对配置了 Databricks Runtime 的计算群集运行。 可以将这些群集配置为以交互方式运行,或将其部署为用于为工作流提供支持的作业计算。 Databricks 建议始终对非交互式工作负载使用作业计算。

交互式工作负载与非交互式工作负载

许多用户发现,在开发过程中处理转换时查看查询结果很有帮助。 将交互式工作负载从通用计算转移到作业计算,可以通过删除显示结果的查询来节省时间和处理成本。

Apache Spark 使用惰性代码执行,这意味着仅在必要时计算结果,并且如果不强制要求结果,针对数据源的多个转换或查询可以优化为单个查询。 这与 pandas 中使用的预先执行模式形成鲜明对比,后者要求在将结果传递给下一个方法之前按顺序处理计算。

如果你的目标是将清理、转换、聚合的数据保存为新数据集,则应在安排代码运行之前从代码中删除显示结果的查询。

对于小型操作和小型数据集,时间和成本节省可能微乎其微。 然而,在进行大型操作时,可能会浪费大量时间来计算结果并将结果输出到笔记本,而这些结果可能不会被人工检查。 存储这些结果后,可能会从保存的输出中查询它们,但成本几乎为零。