PySpark overwrite模式未删除陈旧Parquet文件且无报错问题排查
问题描述
- 环境:9.1 LTS ML(包含Apache Spark 3.1.2、Scala 2.12)
- 执行操作:
df.repartition(parts).write.mode('overwrite').parquet(s3_output_path) - 现象:操作显示成功并写入新Parquet表,但未删除全部旧版本的陈旧Parquet文件;原以为Spark的overwrite模式会先删除所有陈旧文件再写入新文件,推测
_committed_vacuum*文件可能与此相关,但未找到该文件用途的文档说明(注:未使用Delta) - 疑问:为何陈旧文件未完全删除时未抛出错误?
问题解答
- Spark在S3这类对象存储上的overwrite逻辑并非“先删后写”,而是先写入新文件,再尝试清理旧文件。这种设计是为了避免写新数据过程中失败,导致旧数据也被删除的风险,优先保证数据的可用性。
_committed_vacuum*文件的作用是记录overwrite操作需要删除的旧文件列表。当新文件写入成功后,Spark会依据这个列表批量删除旧文件,但如果部分文件因权限限制、已被其他进程删除、S3自身一致性延迟等原因删除失败,Spark不会将这种失败判定为任务失败——因为核心的新数据写入目标已经完成。- 任务成功的判定仅基于新Parquet文件是否完整写入,旧文件清理属于后置的非强制性步骤,所以即使清理不彻底,任务仍会显示成功,且不会抛出错误。
内容的提问来源于stack exchange,提问作者Matthew Thomas
相关产品推荐
相关产品推荐

