Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Java and python processes can exclusive lock the same file on linux

Tags:

java

python

linux

I have a java app and a python launcher for it. The java app locks a file to avoid multiple startups using this code:

java.nio.channels.FileLock lock = lockWrapper.getChannel().tryLock();
if (lock == null) {
     logger.info("Anotheris already running");
}
lock.release();
staticLock = lockWrapper.getChannel().lock();

The python launcher tries to lock on the same file with fcntl and it can. Two java processes can't do this and neither two python processes can lock exclusively on the same file. But a java and a python can, in any directions. I'm on a xubuntu with openjdk 6 and python2.7 I use portalocker for python.

    lockfile =open(lockfilename, 'w+')
    portalocker.lock(lockfile, portalocker.LOCK_EX| portalocker.LOCK_NB)

Also work fine on win7.

like image 710
zeller Avatar asked Oct 23 '22 03:10

zeller


2 Answers

I've got the answer from a co-worker and it's quite simple. Java does not use the POSIX locks, but python does. So they can't inter operate...


Actually they could, but only if one can force both runtimes to use the same locking mechanisms. But that forces you to hardcode it making the code fragile and very platform dependent.

like image 180
zeller Avatar answered Nov 02 '22 06:11

zeller


This works for me on Linux el6. Oracle Java 7 using FileLock and python 2.6 can properly lock a file. Edit: Use F_SETLKW for blocking/waiting operation.

Python code not portable. That's not an issue in my environment.

import fcntl, struct, time

f = open("/tmp/TestLock","w")

lockdata = struct.pack('hhllhh', fcntl.F_WRLCK, 0, 0, 0, 0, 0)
unlockdata = struct.pack('hhllhh', fcntl.F_UNLCK, 0, 0, 0, 0, 0)
while True:
    try:
        fcntl.fcntl(f.fileno(),fcntl.F_SETLK, lockdata)
        print "Lock held"
        time.sleep(5)
    except IOError as ex:
        print "Lock failed: "+ex.strerror
        if ex.errno == 11:
            time.sleep(0.5)
        else:
            break
        continue
    else:
        fcntl.fcntl(f.fileno(),fcntl.F_SETLK, unlockdata)

Reference: https://docs.python.org/2/library/fcntl.html Search page for SVR4 (at the bottom)

Reference: https://community.dur.ac.uk/physics.astrolab/file_locking.html

like image 38
Steve Jankowski Avatar answered Nov 02 '22 07:11

Steve Jankowski