fcntl(文件上锁)&& atexit 妙用--多进程锁

2020-03-03  本文已影响0人  周周周__

fcntl

一、python中的文件锁

我们在写python应用的时候,当涉及到多个进程向同一个文件write(或者read)的情况,如果几个进程同时都对这个文件进行写操作,那么文件的内容就会变得非常混乱,这个时候文件锁就派上用场了。
python中的文件锁,可以保证同时只有一个进程写文件,目前使用的是fcntl这个库,它实际上为 Unix上的ioctl,flock和fcntl 函数提供了一个接口。python通过调用fcntl.flock()函数对文件加锁。
fcntl这个模块是Python自带的,但Windows没有,可以手工下载fcntl.py文件,然后保存到python的Lib目录下。

二、锁类型

例如:一个文件设置了排它锁,如果这个锁已经被某个进程获取了,那么其他进程请求获取这个锁的时候将会被阻塞。
如果想要在没有获得这个排他锁的情况下不阻塞那些进程,可以与 LOCK_NB 联合使用,那么系统就不会阻塞该进程。即: fcnt.flock(f,fcntl.LOCK_EX|fcntl.LOCK_NB)

三、注意点
  1. 对于文件的 close() 操作会使文件锁失效;
  2. 同理,进程结束后文件锁失效;
  3. flock() 的 LOCK_EX是“劝告锁”,系统内核不会强制检查锁的状态,需要在代码中进行文件操作的地方显式检查才能生效。
  4. 在给文件加锁之前,一定要保证文件以相应的访问模式打开,
    例如:要对一个文件加上共享锁,一定要首先按读模式打开文件;若要给文件加上排他锁,则首先要按写模式打开对应文件;若想加两种锁,则需要按读写模式打开.*

atexit

python atexit 模块定义了一个 register 函数,用于在 python 解释器中注册一个退出函数,这个函数在解释器正常终止时自动执行,一般用来做一些资源清理的操作。 atexit 按注册的相反顺序执行这些函数; 例如注册A、B、C,在解释器终止时按顺序C,B,A运行。
PS:如果程序是非正常crash,或者通过os._exit()退出,注册的退出函数将不会被调用
装饰器

# 装饰器法
import  os
from atexit import register
def main():
    print('no atexit .')
@register
def atexit1():
    print('atexit .')
if __name__ == '__main__':
    main()

传参

# 传参
import  os
from atexit import register
def main():
    print('atexit ')
def goodbye(name, adjective):
    print('Goodbye, %s, it was %s to meet you.' % (name, adjective))
if __name__ == '__main__':
    register(goodbye, adjective='nice', name='Donny')
    main()
    exit(1) #程序退出了
    print ("chegn xu")

多进程文件锁

        fcntl = __import__("fcntl")
        f = open('scheduler.lock', 'wb')  # 打开锁文件
        try:
            fcntl.flock(f, fcntl.LOCK_EX | fcntl.LOCK_NB)  # 注册文件锁
            scheduler.init_app(app)
            scheduler.start()
            app.logger.debug('Scheduler Started,---------------')
        except:
            pass
        def unlock():
            fcntl.flock(f, fcntl.LOCK_UN)
            f.close()
        atexit.register(unlock)  # 在此进程结束时释放掉锁
上一篇 下一篇

猜你喜欢

热点阅读