def get_fullpath(mod_dir, mod_name, oid, opts={}): suffix = build_suffix(mod_name, opts) if suffix: store_name = COMPONENT_DELIM.join([oid, suffix]) else: store_name = oid filename_fp = os.path.join(mod_dir, store_name) return filename_fp
def acquire_file_lock(modname, oid, opts, write=False, delay=1, timeout=10): lockid, lockfile = get_lockfilename(modname, oid, opts) logger.debug("Locking %s", lockfile) suffix = build_suffix(modname, opts) start_time = time.time() while True: # Since during processing the lockfile name might change and yet fail # to open, get the lockfile fresh every iteration of the loop. lockid, lockfile = get_lockfilename(modname, oid, opts) try: # If we have the lock already. Just return. if lockid in locked_files: break # If someone else is writing, we need to wait. if not os.path.isfile(lockfile+".write"): other_read_locks = glob(lockfile+"*") # If someone else is reading... if other_read_locks: # If we want to write, we need to wait if write: break # For reading, get the next read lock lockfile = lockfile + "." + \ str(max([int(s.rsplit('.',1)[-1]) for s in other_read_locks])+1) # No one else is reading or writing else: if write: lockfile = lockfile + ".write" else: lockfile = lockfile + ".0" fp = os.open(lockfile, os.O_CREAT|os.O_EXCL|os.O_RDWR) # if we get here, we've got the lock locked_files[lockid] = dict(fp=fp, mod=modname, oid=oid, suffix=suffix, name=lockfile) break except OSError, e: if e.errno != errno.EEXIST: logger.error("Unexpected os error trying to get lockfile %s.", lockfile) print "failed:", e raise elif (time.time() - start_time) >= timeout: logger.error("File locking timeout on lockfile %s.", lockfile) print "failed:", e raise time.sleep(delay)
def get_lockfilename(modname, oid, opts): lockid = oid + '_' + build_suffix(modname, opts) + "_" + modname return lockid, os.path.join(datastore_dir, lockid+".lock")