Java如何删除设置了不可变位的文件
在Java8项目中,我从外部源复制文件。在其中一个源中,文件设置为不可变位标志 在OSX中这样设置Java如何删除设置了不可变位的文件,java,Java,在Java8项目中,我从外部源复制文件。在其中一个源中,文件设置为不可变位标志 在OSX中这样设置 sudo chflags schg /path/to/file 在Linux中 chattr +i /path/to/file 我现在需要删除已复制的文件。我一直在使用Apache Commons IO来删除目录,就像这样 FileUtils.deleteDirectory(new File("/path/here")); 但是,这会导致java.io.IOException崩溃 是否有跨平
sudo chflags schg /path/to/file
在Linux中
chattr +i /path/to/file
我现在需要删除已复制的文件。我一直在使用Apache Commons IO来删除目录,就像这样
FileUtils.deleteDirectory(new File("/path/here"));
但是,这会导致java.io.IOException
崩溃
是否有跨平台的方式删除这些文件?正在运行的进程是文件的所有者
有没有跨平台的方式来删除这些文件
不是我能找到的。我不得不采用你已经考虑过的显而易见的解决方案,这是一个漫长的过程:
- 检测我正在运行的操作系统
- 发出相应的shell命令以删除不可变位
- 确认它已被删除
- 最后删除(在我的例子中,更改)文件
private static String OS = System.getProperty("os.name").toLowerCase();
if(OS.indexOf("win") >= 0)
//your code for windows OS.
else if(OS.indexOf("mac") >= 0)
//your code for MAC OS.
else if(OS.indexOf("sunos") >= 0)
//your code for Solaris OS
- 对所有已知二进制文件(
等)盲目执行解锁命令,使用完整路径避免可能的安全问题。他们很快就会失败,只有一个例外;例如,在Linux上,对/usr/bin/chattr
或ATTRIB.EXE
的任何调用都将失败。如果全部失败,则系统不受支持chflags
- 使用适当的参数执行一个未失败的二进制文件,或相应的检查二进制文件(例如,
forlsattr
),以验证标志的删除chattr
- 或者您可以尝试删除该文件,然后捕获
java.io.IOException
chattr
做了什么,但很明显,我需要发出几个专门的、特定于操作系统的系统调用:因此,调用外部二进制文件没有什么真正的优势,也许除了性能,但在我的例子中这不是问题
一旦你走上了特定于操作系统(本机)的道路,无论是通过JNI还是在Linux系统上,调用
请注意,仅识别操作系统是不够的,您还需要识别文件系统,因为在例如FAT32文件系统或NTFS-3G FSs上,IOCTL将返回错误(该标志在低级别不可用,或者IOSS中间驱动程序(尚未)支持)
在中也存在同样的问题,在高级别上提供了一个与操作系统无关的调用。。。但它并不适用于任何地方。问题:因为,我们知道设置了不可变属性的文件不能被任何用户删除。即使根用户也无法删除以下文件。现在,要删除该文件,必须删除不可变属性,然后删除该文件。
现在,您要做的是通过代码应用shell命令并删除文件上的不可变属性。
正如您提到的跨平台问题
所以基本算法是
步骤1:检测您正在使用的操作系统示例代码为:
private static String OS = System.getProperty("os.name").toLowerCase();
if(OS.indexOf("win") >= 0)
//your code for windows OS.
else if(OS.indexOf("mac") >= 0)
//your code for MAC OS.
else if(OS.indexOf("sunos") >= 0)
//your code for Solaris OS
注意:我没有添加检查所有操作系统的代码。因此,您可以自己看一看。步骤2:此步骤帮助您解决跨平台问题
通过
java.lang.Runtime.exec
发出相应的shell命令以删除文件的不可变属性看这张照片。
java.lang.Runtime.exec:通过该命令,您可以为任何底层环境(无论是MAC、Windows、Linux等)提供适当的shell命令 示例代码为
注意:要运行包含管道的其他shell命令,可以使用以下示例代码:
Process p = Runtime.getRuntime().exec(new String[]{"csh","-c","cat /home/narek/pk.txt"});
步骤3:使用相同的Runtime.exec()检查不可变属性是否已删除,如下所示:
Process p = Runtime.getRuntime().exec("lsattr /whateverPath");
//Play with the process to check whether the attribute is set or not, using the documentation.
步骤4:如果步骤3为true | false,则无论应用何种逻辑,然后使用Runtime.exec()再次使用相应的命令删除该文件 事情是看一看上面链接的java.lang.Runtime.exec文档并使用它。
请告诉我它是否有一定的帮助。您是否尝试过查看
java.nio.file.attribute
中的类chattr
是非常特定于Linux的,它的一些参数是特定于文件系统的,所以我怀疑Java是否绑定到它。通过shell命令提供您自己的实现可能更安全。是的,我看过了。我确实考虑过剥壳,但我想有一个跨平台的方法来处理这个问题,而不是必须在多个平台上实现Linux /BSD/Windows层。只是我的意见,不确定它是否适用于这里,但是我将避免处理java中如此低的东西。我的建议是使用相关的OS命令(或shell)。例如,使用chflags
将是chflags-r0/path/here
。然后您可以使用可移植的java代码…不确定,但java nio2文件属性会有帮助吗?看看这个项目:neat sol,我只建议在复制文件后立即执行unset
命令,所以剩下的步骤是:处理和删除。。。光滑的;)那很酷。我在想该怎么评论,但后来觉得你的评论更酷p@Yazan