无法删除空文件夹
Can't remove empty folder
在现有文件夹中,我使用此方法创建了一个文件夹并在其中包含多个文件:
SeekableByteChannel createFile(String filePathToCreate) throws IOException {
OpenOption[] options = {
StandardOpenOption.WRITE,
StandardOpenOption.CREATE_NEW,
StandardOpenOption.SPARSE,
StandardOpenOption.READ
// TODO: think if we add CREATE if exist rule.
};
return Files.newByteChannel(Paths.get(filePathToCreate), options);
}
folders/files结构是:
- torrents-test
- folder1
- File-I-Created-1
- File-I-Created-2
- File-I-Created-3
然后我尝试用这个方法删除文件夹torrents-test
:
void deleteDirectory(File directoryToBeDeleted) throws IOException {
File[] allContents = directoryToBeDeleted.listFiles();
if (allContents != null) {
for (File file : allContents) {
deleteDirectory(file);
}
}
Files.delete(directoryToBeDeleted.toPath());
}
然后我得到一个异常,告诉我文件夹 folder1
不为空,所以我不能删除它:
java.nio.file.DirectoryNotEmptyException: C:\GIT\university\torrentx\torrents-test\folder1
at sun.nio.fs.WindowsFileSystemProvider.implDelete(WindowsFileSystemProvider.java:266)
at sun.nio.fs.AbstractFileSystemProvider.delete(AbstractFileSystemProvider.java:103)
at java.nio.file.Files.delete(Files.java:1126)
at com.utils.Utils.deleteDirectory(Utils.java:389)
at com.utils.Utils.deleteDirectory(Utils.java:386)
at com.utils.Utils.deleteDownloadFolder(Utils.java:375)
at com.utils.Utils.removeEverythingRelatedToTorrent(Utils.java:87)
at com.steps.MyStepdefs.applicationCreateActiveTorrentFor(MyStepdefs.java:297)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at cucumber.runtime.Utils.call(Utils.java:40)
at cucumber.runtime.Timeout.timeout(Timeout.java:16)
at cucumber.runtime.Utils.invoke(Utils.java:34)
at cucumber.runtime.java.JavaStepDefinition.execute(JavaStepDefinition.java:38)
at cucumber.runtime.StepDefinitionMatch.runStep(StepDefinitionMatch.java:37)
at cucumber.runtime.Runtime.runStep(Runtime.java:300)
at cucumber.runtime.model.StepContainer.runStep(StepContainer.java:44)
at cucumber.runtime.model.StepContainer.runSteps(StepContainer.java:39)
at cucumber.runtime.model.CucumberScenario.run(CucumberScenario.java:44)
at cucumber.runtime.model.CucumberScenarioOutline.run(CucumberScenarioOutline.java:46)
at cucumber.runtime.model.CucumberFeature.run(CucumberFeature.java:165)
at cucumber.runtime.Runtime.run(Runtime.java:122)
at cucumber.api.cli.Main.run(Main.java:36)
at cucumber.api.cli.Main.main(Main.java:18)
我的 deleteDirectory
方法首先删除它试图删除的每个文件夹中的所有文件,然后才会删除该文件夹。该异常表明该文件夹内的每个文件都已成功删除,因为如果不成功,我会在尝试删除该文件夹的一个文件时更早地遇到异常。
我的问题是 - 为什么我得到那个异常?
java.nio.file.Files.delete(Path path)
的 javadoc 很清楚:
If the file is a directory then the directory must be empty.
也说明了:
This method can be used with the walkFileTree method to delete a
directory and all entries in the directory, or an entire file-tree
where required.
使用 Files.walkFileTree()
会使您的代码更清晰、更短,但请注意,它不会解决您的实际问题。
除了您删除所有资源的递归方法是正确的,因为您通过从更深的地方开始并通过备份不太深的方式来删除资源。
问题出在其他地方:实际上您正在使用 Files.newByteChannel()
创建文本文件,这会创建一些 SeekableByteChannel
连接到 File
的实例。因此,当您调用 Files.delete(directoryToBeDeleted.toPath());
.
时,它似乎可以防止文件被即时删除
所以在删除文件之前关闭流,它应该可以工作。
在现有文件夹中,我使用此方法创建了一个文件夹并在其中包含多个文件:
SeekableByteChannel createFile(String filePathToCreate) throws IOException {
OpenOption[] options = {
StandardOpenOption.WRITE,
StandardOpenOption.CREATE_NEW,
StandardOpenOption.SPARSE,
StandardOpenOption.READ
// TODO: think if we add CREATE if exist rule.
};
return Files.newByteChannel(Paths.get(filePathToCreate), options);
}
folders/files结构是:
- torrents-test
- folder1
- File-I-Created-1
- File-I-Created-2
- File-I-Created-3
然后我尝试用这个方法删除文件夹torrents-test
:
void deleteDirectory(File directoryToBeDeleted) throws IOException {
File[] allContents = directoryToBeDeleted.listFiles();
if (allContents != null) {
for (File file : allContents) {
deleteDirectory(file);
}
}
Files.delete(directoryToBeDeleted.toPath());
}
然后我得到一个异常,告诉我文件夹 folder1
不为空,所以我不能删除它:
java.nio.file.DirectoryNotEmptyException: C:\GIT\university\torrentx\torrents-test\folder1
at sun.nio.fs.WindowsFileSystemProvider.implDelete(WindowsFileSystemProvider.java:266)
at sun.nio.fs.AbstractFileSystemProvider.delete(AbstractFileSystemProvider.java:103)
at java.nio.file.Files.delete(Files.java:1126)
at com.utils.Utils.deleteDirectory(Utils.java:389)
at com.utils.Utils.deleteDirectory(Utils.java:386)
at com.utils.Utils.deleteDownloadFolder(Utils.java:375)
at com.utils.Utils.removeEverythingRelatedToTorrent(Utils.java:87)
at com.steps.MyStepdefs.applicationCreateActiveTorrentFor(MyStepdefs.java:297)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at cucumber.runtime.Utils.call(Utils.java:40)
at cucumber.runtime.Timeout.timeout(Timeout.java:16)
at cucumber.runtime.Utils.invoke(Utils.java:34)
at cucumber.runtime.java.JavaStepDefinition.execute(JavaStepDefinition.java:38)
at cucumber.runtime.StepDefinitionMatch.runStep(StepDefinitionMatch.java:37)
at cucumber.runtime.Runtime.runStep(Runtime.java:300)
at cucumber.runtime.model.StepContainer.runStep(StepContainer.java:44)
at cucumber.runtime.model.StepContainer.runSteps(StepContainer.java:39)
at cucumber.runtime.model.CucumberScenario.run(CucumberScenario.java:44)
at cucumber.runtime.model.CucumberScenarioOutline.run(CucumberScenarioOutline.java:46)
at cucumber.runtime.model.CucumberFeature.run(CucumberFeature.java:165)
at cucumber.runtime.Runtime.run(Runtime.java:122)
at cucumber.api.cli.Main.run(Main.java:36)
at cucumber.api.cli.Main.main(Main.java:18)
我的 deleteDirectory
方法首先删除它试图删除的每个文件夹中的所有文件,然后才会删除该文件夹。该异常表明该文件夹内的每个文件都已成功删除,因为如果不成功,我会在尝试删除该文件夹的一个文件时更早地遇到异常。
我的问题是 - 为什么我得到那个异常?
java.nio.file.Files.delete(Path path)
的 javadoc 很清楚:
If the file is a directory then the directory must be empty.
也说明了:
This method can be used with the walkFileTree method to delete a directory and all entries in the directory, or an entire file-tree where required.
使用 Files.walkFileTree()
会使您的代码更清晰、更短,但请注意,它不会解决您的实际问题。
除了您删除所有资源的递归方法是正确的,因为您通过从更深的地方开始并通过备份不太深的方式来删除资源。
问题出在其他地方:实际上您正在使用 Files.newByteChannel()
创建文本文件,这会创建一些 SeekableByteChannel
连接到 File
的实例。因此,当您调用 Files.delete(directoryToBeDeleted.toPath());
.
时,它似乎可以防止文件被即时删除
所以在删除文件之前关闭流,它应该可以工作。