How to check if a file is locked in Python
December 14, 2010 Comments
My colleague showed me a trick on how to do this earlier. What I was trying to do is poll a folder for a bunch of files and if they’re not there keep polling until they arrive, then process them. The problem is before they can be processed we need to be sure that the file transfer is complete.
The trick on how to do this is to try and open the file once it arrives in ‘append’ mode. This will fail if another process is using the file. So what we can do in this case is then keep trying to open it in append mode until it’s successful and at that point we know that there is no longer a lock on the file.
Sounds a bit hacky but we couldn’t think of a more elegant way to do it.
import os, time def is_locked(filepath): """Checks if a file is locked by opening it in append mode. If no exception thrown, then the file is not locked. """ locked = None file_object = None if os.path.exists(filepath): try: print "Trying to open %s." % filepath buffer_size = 8 # Opening file in append mode and read the first 8 characters. file_object = open(filepath, 'a', buffer_size) if file_object: print "%s is not locked." % filepath locked = False except IOError, message: print "File is locked (unable to open in append mode). %s." % \ message locked = True finally: if file_object: file_object.close() print "%s closed." % filepath else: print "%s not found." % filepath return locked def wait_for_files(filepaths): """Checks if the files are ready. For a file to be ready it must exist and can be opened in append mode. """ wait_time = 5 for filepath in filepaths: # If the file doesn't exist, wait wait_time seconds and try again # until it's found. while not os.path.exists(filepath): print "%s hasn't arrived. Waiting %s seconds." % \ (filepath, wait_time) time.sleep(wait_time) # If the file exists but locked, wait wait_time seconds and check # again until it's no longer locked by another process. while is_locked(filepath): print "%s is currently in use. Waiting %s seconds." % \ (filepath, wait_time) time.sleep(wait_time) # Test if __name__ == '__main__': files = [r"C:\testfolder\testfile1.txt", r"C:\testfolder\testfile2.txt"] print wait_for_files(files)<br>
Output:
Trying to open C:\testfolder\testfile1.txt. File is locked (unable to open in append mode). [Errno 13] Permission denied: ‘C:\\testfolder\\testfile1.txt’. C:\testfolder\testfile1.txt is currently in use. Waiting 5 seconds. Trying to open C:\testfolder\testfile1.txt. C:\testfolder\testfile1.txt is not locked. C:\testfolder\testfile1.txt closed. Trying to open C:\testfolder\testfile2.txt. C:\testfolder\testfile2.txt is not locked. C:\testfolder\testfile2.txt closed.
Tags: python, tech, software development