Spark全局临时视图查询时机与跨应用数据传递机制问询
Spark全局临时视图跨Databricks笔记本的执行逻辑与数据传递解析
核心疑问背景
在Databricks笔记本(Spark应用)间传递DataFrame时,我需要在全局临时视图和存储方案间做选择,核心想搞清楚两个问题:
- 若查询在应用A创建全局临时视图时执行,数据如何传递给应用B?是通过内存吗?
- 若查询在应用B中执行,A传递的查询计划是否包含数据源的访问方式、位置及凭证信息?
测试过程与结果
应用A执行代码
import time import pyspark.sql.functions as F t1 = time.time() df = spark.read.parquet(*paths) t2 = time.time() df = df.filter((F.col('createdate') >= F.lit(start)) & (F.col('createdate') < F.lit(end))) t3 = time.time() df.show() t4 = time.time() df.createOrReplaceGlobalTempView('testview') t5 = time.time() print(t2-t1, t3-t2, t4-t3, t5-t4)
输出:16.02s, 0.15s, 1.96s, 0.014s
应用B执行代码
import time t1 = time.time() sqlContext.table('global_temp.testview').show() print(time.time()-t1)
输出:
- 当A中执行
show()时,B耗时2.16s - 当A中未执行
show()时,B耗时2.30s
测试初步结论
从耗时可以看出:创建全局临时视图时几乎没有计算开销,仅传递了查询计划,并未执行数据读取或计算。
关键问题解答
1. 应用B何时访问Parquet数据源?
全局临时视图的本质是共享逻辑执行计划,而非数据本身:
- 应用A执行
createOrReplaceGlobalTempView时,只是把DataFrame对应的逻辑执行计划(包含读取Parquet路径、过滤条件等逻辑)注册到集群级的元数据存储中,不会触发任何数据读取或计算,这也是创建视图耗时极短的原因。 - 当应用B执行
sqlContext.table('global_temp.testview').show()时,会先从元数据存储中拉取这个逻辑执行计划,经过Spark Catalyst优化器转换成物理执行计划,此时才会触发Parquet数据源的访问——也就是在B执行show()的阶段,才会真正读取Parquet文件、执行过滤操作并返回结果。
2. 查询计划是否包含数据源的访问信息?
- 查询计划会包含数据源的位置(Parquet路径)和读取配置(比如文件格式、过滤条件),但不会包含凭证信息。
- 凭证信息是绑定到执行查询的Spark Session(应用B的Session)的,也就是说应用B必须拥有访问该Parquet路径的权限(比如云存储IAM权限、Databricks访问控制),才能成功读取数据。如果B没有权限,即使拿到查询计划,执行时也会抛出权限错误。
3. 测试中耗时差异的原因
当应用A执行df.show()时,Spark会自动将部分计算结果缓存到集群的内存/磁盘中(基于Spark的自动缓存机制)。当应用B执行show()时,会复用这部分缓存的数据,因此耗时略短。这是Spark缓存机制的作用,并非全局临时视图直接传递内存数据的结果。
总结
全局临时视图适合跨Databricks笔记本共享查询逻辑,无需提前计算和存储数据,节省存储成本;但依赖集群元数据共享,且执行查询的应用必须具备数据源的访问权限。
内容的提问来源于stack exchange,提问作者이준서
相关产品推荐
相关产品推荐

