Scala Spark读取分区文件后分区目录消失的原因及解决方法
问题原因及解决办法
首先明确:Spark的read.parquet()读取操作本身不会删除源分区目录,出现这种情况大概率是其他环节的问题,常见原因和对应解决方法如下:
可能的原因
- 代码中隐藏了删除逻辑:比如读取数据后,后续代码调用了文件系统删除API(如
org.apache.hadoop.fs.FileSystem.delete())、执行了HDFS删除命令(hdfs dfs -rm -r /home/path/date=2022-12-02),或者用overwrite模式将数据写回了同一路径,触发了分区目录的清理。 - 外部进程/误操作:比如其他脚本、运维人员手动删除了该目录,或者集群的定时清理任务(如清理临时文件的脚本)误删了目标目录。
- 分区目录属性异常:如果该目录被标记为临时目录,或者写入时使用了临时路径未正确转正,后续被系统自动清理。
避免方法
- 排查全链路代码:逐行检查读取操作后的所有逻辑,确认没有任何删除、覆盖写相关的代码,重点关注文件系统操作、Spark SQL的DROP/ALTER语句、DataFrame的
write.mode("overwrite")操作。 - 权限加固:给
/home/path/date=2022-12-02目录设置只读权限(除了写入数据的用户),避免非授权操作删除目录,比如执行hdfs dfs -chmod 555 /home/path/date=2022-12-02。 - 日志追踪:开启HDFS审计日志,或者Spark的DEBUG级日志,通过日志定位删除操作的发起者(用户/进程),精准定位问题根源。
- 测试环境复现:在测试集群模拟相同操作,逐步执行代码,每一步后检查目录是否存在,确认是哪一步触发了删除。
- 调整读取方式(非必要但可验证):单个分区读取时可以去掉
basePath参数,直接用spark.read.parquet("/home/path/date=2022-12-02"),Spark依然会自动识别date分区字段,借此排除basePath参数是否间接触发了异常逻辑。
内容的提问来源于stack exchange,提问作者Jelly
相关产品推荐
相关产品推荐

