Question

I'm investigating the best (cross-platform) way to lock some files that are used by a Java application.

The worst-case scenario is that the program quits unexpectedly (user forces termination, or unclean exit). In this case, what is the best way to ensure file locks are released, so they don't affect any subsequent access by a program?

I've looked at using FileLock, but an unclean termination could leave the file in a locked unusable state.

Is there a way to resolve this issue with code? either catching such problems to first 'clean-up', or on a subsequent run of the program?

Was it helpful?

Solution

I don't think FileLock has the problem you think it has. According to the documentation it uses the OS file lock functionality which I think means most OSs would clean up any locks held by the process when it quits (though you may want to do some tests to verify this).

Otherwise you need a way to determine whether the lock is stale or not.

A common method for handling this with things like shell scripts is to put the process' ID (PID) in the lock file. This way other apps which see the lock file can verify whether the lock is still valid by checking for that process running. If the process isn't running the lock can be cleaned up.

Though I don't know of a way to do this through Java...

OTHER TIPS

The worst-case scenario is that the program quits unexpectedly

In that case your program itself can not be responsible for freeing the locks, as it ceases to execute. You must therefore rely on something outside the program. But that thing can not itself be a program, because it too could quit unexpectedly. You therefore must rely on the operating system itself. Of course there is no cross-platform way of doing that.

You could register a shut-down hook to release any FileLocks when the application terminates. Obviously this code will not run if the JVM dies unexpectedly due to the PC being reset, Hotspot error, etc.

File lockFile = new File("c:/tmp/lock");
final FileLock lock = lockFile.channel().lock();

Runtime.getRuntime().addShutDownHook(new Thread(new Runnable() {
  public void run() {
    lock.release();
  }
}));
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top