文件锁定如何工作?
我一直在尝试使用来获得对文件的独占访问权限,以便:FileLock
- 删除它
- 重命名
- 写信给它
因为(至少在 Windows 上)似乎无法删除、重命名或写入已在使用的文件。我编写的代码如下所示:
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.channels.FileChannel;
import java.nio.channels.FileLock;
public abstract class LockedFileOperation {
public void execute(File file) throws IOException {
if (!file.exists()) {
throw new FileNotFoundException(file.getAbsolutePath());
}
FileChannel channel = new RandomAccessFile(file, "rw").getChannel();
try {
// Get an exclusive lock on the whole file
FileLock lock = channel.lock();
try {
doWithLockedFile(file);
} finally {
lock.release();
}
} finally {
channel.close();
}
}
public abstract void doWithLockedFile(File file) throws IOException;
}
下面是一些演示问题的单元测试。您需要在类路径上使用Apache commons-io才能运行第三个测试。
import java.io.File;
import java.io.IOException;
import junit.framework.TestCase;
public class LockedFileOperationTest extends TestCase {
private File testFile;
@Override
protected void setUp() throws Exception {
String tmpDir = System.getProperty("java.io.tmpdir");
testFile = new File(tmpDir, "test.tmp");
if (!testFile.exists() && !testFile.createNewFile()) {
throw new IOException("Failed to create test file: " + testFile);
}
}
public void testRename() throws IOException {
new LockedFileOperation() {
@Override
public void doWithLockedFile(File file) throws IOException {
if (!file.renameTo(new File("C:/Temp/foo"))) {
fail();
}
}
}.execute(testFile);
}
public void testDelete() throws IOException {
new LockedFileOperation() {
@Override
public void doWithLockedFile(File file) throws IOException {
if (!file.delete()) {
fail();
}
}
}.execute(testFile);
}
public void testWrite() throws IOException {
new LockedFileOperation() {
@Override
public void doWithLockedFile(File file) throws IOException {
org.apache.commons.io.FileUtils.writeStringToFile(file, "file content");
}
}.execute(testFile);
}
}
所有测试均未通过。前 2 个失败,最后一个引发此异常:
java.io.IOException: The process cannot access the file because another process has locked a portion of the file
at java.io.FileOutputStream.writeBytes(Native Method)
at java.io.FileOutputStream.write(FileOutputStream.java:247)
at org.apache.commons.io.IOUtils.write(IOUtils.java:784)
at org.apache.commons.io.IOUtils.write(IOUtils.java:808)
at org.apache.commons.io.FileUtils.writeStringToFile(FileUtils.java:1251)
at org.apache.commons.io.FileUtils.writeStringToFile(FileUtils.java:1265)
似乎该方法对文件设置了一个锁定,然后阻止我重命名/删除/写入它。我的假设是,锁定文件将使我对该文件具有独占访问权限,因此我可以重命名/删除/写入它,而不必担心是否有任何其他进程也在访问它。lock()
要么是我误解了,要么这不是我的问题的合适解决方案。FileLock