用于读写的Java FileLock

我有一个进程,它会被cron相当频繁地调用,以读取其中包含某些与移动相关的命令的文件。 我的进程需要读取和写入此数据文件 – 并将其锁定以防止其他进程在此期间触摸它。 用户可以执行完全独立的过程(可能)写入/附加到该相同的数据文件。 我希望这两个进程运行良好,并且一次只访问一个文件。

nio FileLock似乎是我需要的(没有编写我自己的信号量类型文件),但是我无法锁定它进行阅读。 我可以锁定并写得很好,但是在读取时尝试创建锁定时会出现NonWritableChannelException。 甚至可以锁定文件进行阅读吗? 看起来像RandomAccessFile更接近我需要的东西,但我不知道如何实现它。

这是失败的代码:

FileInputStream fin = new FileInputStream(f); FileLock fl = fin.getChannel().tryLock(); if(fl != null) { System.out.println("Locked File"); BufferedReader in = new BufferedReader(new InputStreamReader(fin)); System.out.println(in.readLine()); ... 

FileLock行抛出exception。

 java.nio.channels.NonWritableChannelException at sun.nio.ch.FileChannelImpl.tryLock(Unknown Source) at java.nio.channels.FileChannel.tryLock(Unknown Source) at Mover.run(Mover.java:74) at java.lang.Thread.run(Unknown Source) 

它说,看看JavaDocs

尝试写入最初未打开以进行写入的通道时,抛出未经检查的exception。

但我不一定要写信给它。 当我尝试创建FileOutpuStream等用于写入目的时,我很高兴直到我尝试在同一文件上打开FileInputStream。

(a)您是否知道锁定文件不会阻止其他进程接触它,除非它们也使用锁?
(b)您必须通过可写通道锁定。 通过“rw”模式下的RandomAccessFile获取锁定,然后打开FileInputStream 。 一定要关闭它们!

如果使用tryLock(0L, Long.MAX_VALUE, true)创建锁定会更好。

这会创建一个共享锁,这是阅读的正确选择。

tryLock()tryLock()的简写tryLock(0L, Long.MAX_VALUE, false) ,即它请求独占写锁。