如何在linux上序列化命令执行?

如何在linux上序列化命令执行?

我想确保系统的任何常规用户一次只能运行一个脚本。可以有多个用户登录,每个用户只能在其他用户运行的命令完成后才能运行命令。

很久以前,在 UNIX 上,我使用batch具有正确的“仅一个任务”队列定义的命令来序列化脚本执行。它解决了很多锁管理问题(只需要在脚本中设置一个简单的超时)。

现在,在 Linux 上,该batch命令的执行方式有所不同,每分钟运行一个任务,任务并行运行,直到达到 1.5 的平均负载。

我制作了自己的锁管理 shell 库来序列化执行,但我想知道是否有一个标准命令可以做到这一点。

答案1

flock对此确实非常出色。您可以flock在 shell 脚本的包装器中使用它,在命令行上使用它,或者将其合并到您的脚本本身中。

最好的一点flock是,当它等待时,它不会在繁忙的循环中等待。

它也是总是当您的进程退出/退出时清除锁flock

如果进程在没有清理的情况下退出(或者如果出现内核恐慌或电源故障......),基于原子文件/目录创建的方法可能会被锁定。

flockLinux 内核使用 进行清理工作。

从手册来看,

(
flock -s 200  
# ... commands executed under lock ...
) 200>/var/lock/mylockfile

在这种形式中,您可以将特定的代码块包装在 shell 脚本中。

或者你可以像这样运行它,

/usr/bin/flock /tmp/lockfile command

如果你不想无限期地阻塞/等待,你可以指定一个超时:

-w  --timeout <secs>     wait for a limited amount of time

或者只使用非阻塞参数:

-n  --nonblock           fail rather than wait

答案2

也许您想要的是对用户可以运行的进程数量进行硬性限制?确保包含他们的 shell 进程以及任何其他必要的内容需要在他们的会议期间运行。

这可以在 /etc/security/limits.conf 中设置,添加一行:

testuser hard nproc 2

请注意,如果有太多东西试图同时运行,这将引发无法分叉的错误。将 2 更改为适合您的需要,并将 'testuser' 更改为您想要限制的用户。

答案3

使用mkdir这是一个原子进程来锁定其他进程。当时只有一个人可以创建一个目录:

#!/bin/bash
if ! mkdir /tmp/TheLock 2> /dev/null ; then
    echo Error, user \'$(stat -c %U /tmp/TheLock)\' has the task
else
    echo Yes, I got it\!
    sleep 1 # do stuff
    rmdir /tmp/TheLock
fi

如果首先运行脚本,它会读出:

Yes, I got it!

如果有人尝试同时运行它,输出将是:

Error, user 'Emmanuel' has the task

相关内容