最近购买了一台腾讯云的服务器跑一些小程序,在整理crontab时发现了一个腾讯云的定时任务,

*/5 * * * * flock -xn /tmp/stargate.lock -c '/usr/local/qcloud/stargate/admin/start.sh > /dev/null 2>&1 &'

脚本是为了保证腾讯云agent存活的,这个不是我们关注的重点,重点是flock这个命令。

虽然经常与服务器打交道,但是flock这个命令还是比较陌生的。

flock

以下内容摘抄自cnblogs。

如果两个进程同时启动了某个脚本,那么很容易导致数据的混乱,这个时候需要锁来协调解决。

flock是建议性锁,不具备强制性。一个进程使用flock将文件锁住,另一个进程也可以直接操作正在被锁的文件,修改文件中的数据。

flock只是用于检测文件是否被加锁,针对文件已经被加锁,另一个进程写入数据的情况,内核不会阻止这个进程的写入操作。

flock主要三种操作类型:

LOCK_SH,共享锁,多个进程可以使用同一把锁,常被用作读共享锁;
LOCK_EX,排他锁,同时只允许一个进程使用,常被用作写锁;
LOCK_UN,释放锁;

参数

-s,--shared:获取一个共享锁,在定向为某文件的FD上设置共享锁而未释放锁的时间内,其他进程试图在定向为此文件的FD上设置独占锁的请求失败,而其他进程试图在定向为此文件的FD上设置共享锁的请求会成功。
-x,-e,--exclusive:获取一个排它锁,或者称为写入锁,为默认项
-u,--unlock:手动释放锁,一般情况不必须,当FD关闭时,系统会自动解锁,此参数用于脚本命令一部分需要异步执行,一部分可以同步执行的情况。
-n,--nb, --nonblock:非阻塞模式,当获取锁失败时,返回1而不是等待
-w, --wait, --timeout seconds:设置阻塞超时,当超过设置的秒数时,退出阻塞模式,返回1,并继续执行后面的语句
-o, --close:表示当执行command前关闭设置锁的FD,以使command的子进程不保持锁。
-c, --command command:在shell中执行其后的语句

最后

flock可以让很多脚本程序变得更规范,比如我有一些增量计算数据的脚本,如果不小心并发执行了就会导致数据错乱。

以前不知道这个命令,都是用一个lock文件来替代,在脚本中判断文件是否存在,非常的繁琐,也不是很严谨。

你是更喜欢把flock放在脚本外部,还是写在脚本里呢?