Scala中调用File.delete()无法删除csv文件如何解决
核心原因
Spark DataFrame的csv()写入方法不会在指定路径生成单个csv文件,而是会创建一个名为data/temporaryBasis的目录,目录内包含:
- 多个按分区生成的
part-*.csv数据文件 - 标记任务成功的
_SUCCESS文件 - 每个文件对应的
.crc校验隐藏文件 - 可能存在的子分区目录
而JDK原生的java.io.File.delete()方法仅支持删除单个文件或空目录,对存有内容的非空目录调用该方法会直接返回false,不会执行递归删除,这就是删除操作失效的根本原因。
可行解决方案
方案1:使用Spark内置的Hadoop FileSystem API删除(推荐)
这是和Spark生态兼容性最好的方案,不需要额外引入依赖,同时支持本地文件系统、HDFS、对象存储等所有Spark支持的存储路径,不会出现路径适配问题:
import org.apache.hadoop.fs.Path // 从当前Spark会话获取Hadoop配置 val hadoopConf = result.sparkSession.sessionState.newHadoopConf() val targetPath = new Path("data/temporaryBasis") val fs = targetPath.getFileSystem(hadoopConf) // 第二个参数传入true代表开启递归删除 fs.delete(targetPath, true)
方案2:手动实现JDK文件递归删除
如果不想依赖Hadoop相关API,可以自己实现目录递归遍历逻辑,从最内层的文件开始依次删除,清空所有内容后再删除外层目录,注意不要漏删Spark生成的隐藏校验文件、成功标记文件。
方案3:使用临时目录自动清理
如果这个路径只是用来存中间临时结果,不需要持久化,直接使用Spark自带的临时目录能力即可,任务执行结束后Spark会自动回收临时路径,不需要手动编写删除逻辑,避免文件残留。
注意:如果开启了Spark的异步写入配置,需要等待写入任务完全执行完成后再触发删除操作,否则会出现写入过程中路径被删、或者删除时文件还被占用的问题。
内容的提问来源于stack exchange,提问作者informatic_aa
相关产品推荐
相关产品推荐

