我目前在 linux 机器上遇到问题,作为 root 我有命令返回错误,因为已达到 inotify 监视限制。
# tail -f /var/log/messages
[...]
tail: cannot watch '/var/log/messages': No space left on device
# inotifywatch -v /var/log/messages
Establishing watches...
Failed to watch /var/log/messages; upper limit on inotify watches reached!
Please increase the amount of inotify watches allowed per user via '/proc/sys/fs/inotify/max_user_watches'.`
Run Code Online (Sandbox Code Playgroud)
我用谷歌搜索了一下,我发现的每个解决方案都是通过以下方式增加限制:
sudo sysctl fs.inotify.max_user_watches=<some random high number>
Run Code Online (Sandbox Code Playgroud)
但我无法找到任何有关提高该价值的后果的信息。我猜默认内核值的设置是有原因的,但它似乎不适用于特定用途。(例如,当使用带有大量文件夹的 Dropbox 或监控大量文件的软件时)
所以这里是我的问题:
在最近升级到 Fedora 15 后,我发现许多工具失败并出现以下错误:
tail: inotify resources exhausted
tail: inotify cannot be used, reverting to polling
Run Code Online (Sandbox Code Playgroud)
这不仅仅是tail报告 inotify 的问题。有没有办法询问内核以找出正在消耗 inotify 资源的进程?当前与 inotify 相关的sysctl设置如下所示:
fs.inotify.max_user_instances = 128
fs.inotify.max_user_watches = 8192
fs.inotify.max_queued_events = 16384
Run Code Online (Sandbox Code Playgroud) 我看过这个答案。
您应该考虑使用 inotifywait,例如:
Run Code Online (Sandbox Code Playgroud)inotifywait -m /path -e create -e moved_to | while read path action file; do echo "The file '$file' appeared in directory '$path' via '$action'" # do something with the file done
我的问题是,上面的脚本监视目录以创建任何类型的文件,但是如何修改inotifywait命令以仅在创建特定类型/扩展名的文件(或移动到目录中)时报告 - 例如它应该.xml创建任何文件时报告。
我试过的:
我已经运行了inotifywait --help命令,并阅读了命令行选项。它具有--exclude <pattern>和--excludei <pattern>命令来排除某些类型的文件(通过使用正则表达式),但我需要一种方法来只包括某些类型/扩展名的文件。
我已经编写了一个 shell 脚本来使用 inotifyt-tools 的 inotifywait 实用程序来监视目录。我希望该脚本在后台连续运行,但我也希望能够在需要时停止它。
为了让它连续运行,我使用了while true; 像这样:
while true;
do #a set of commands that use the inotifywait utility
end
Run Code Online (Sandbox Code Playgroud)
我已将其保存在一个文件中/bin并使其可执行。为了让它在后台运行,我使用nohup <script-name> &并关闭了终端。
我不知道如何停止这个脚本。我看过的答案在这里和非常密切相关的问题在这里。
更新 1: 根据下面@InfectedRoot 的回答,我已经能够使用以下策略解决我的问题。第一次使用
ps -aux | grep script_name
Run Code Online (Sandbox Code Playgroud)
并用于sudo kill -9 <pid>杀死进程。然后我不得不再次pgrep inotifywait使用sudo kill -9 <pid>返回的id。
这有效,但我认为这是一种凌乱的方法,我正在寻找更好的答案。
更新 2: 答案包括杀死 2 个进程。这很重要,因为在命令行上运行脚本会启动 2 个进程,1 个脚本本身和 2 个inotify 进程。
我有一个简单的脚本,用于监视文件的更改并将其与远程复制同步:
#!/bin/bash
while inotifywait -e close_write somefile
do
rsync somefile user@host.domain:./somefile
done
Run Code Online (Sandbox Code Playgroud)
它在 nano 上工作得很好,但在 vim 上失败了。当我使用 nano 时,它输出:
somefile CLOSE_WRITE,CLOSE
Run Code Online (Sandbox Code Playgroud)
并开始下一个循环,等待另一个版本。
当我使用 vim 时,没有输出,脚本只是以退出代码 0 关闭。
我做了一些研究,发现 close_write 是使用 initofywait 和 vim 的正确参数(首先我想使用修改事件),但由于某种原因它对我来说失败了。
我正在尝试将移动到一个文件夹的 flac 文件自动转换为另一个文件夹中的 mp3。
我当前的代码行是这样的:
inotifywait -m -r -q -e moved_to --format "'%w%f'" ~/test | xargs -I x flac -cd x - | lame -b 320 - /media/1tb/x.mp3
Run Code Online (Sandbox Code Playgroud)
到目前为止,为了解释这是如何工作的,inotifywait 以递归方式监视 ~/test 移动到那里的文件,将路径和文件名输出到管道。xargs 使用该名称并创建正确的 flac 命令,用文件名替换 x 并将文件解码到另一个管道。在新的管道中,lame 将 flac 的输出处理成 /media 下的 mp3。我希望 xargs 以某种方式穿过管道,替换跛脚命令中的 x 或以某种方式将其发送到两个命令都可以访问的变量或其他东西。我试图搞乱命名管道和爵士乐,但是在两个命令之间传输实际数据的事实让我无法理解。
我正在尝试/tmp使用inotifywatch以下方法监视我的文件夹的更改:
sudo inotifywatch -v -r /tmp
Run Code Online (Sandbox Code Playgroud)
创建几个文件 ( touch /tmp/test-1 /tmp/test-2) 后,我将终止inotifywatch(通过Ctrl-C这向我显示以下统计信息:
Establishing watches...
Setting up watch(es) on /tmp
OK, /tmp is now being watched.
Total of 39 watches.
Finished establishing watches, now collecting statistics.
total attrib close_write open create filename
8 2 2 2 2 /tmp/
Run Code Online (Sandbox Code Playgroud)
输出仅打印统计信息,但不打印我期望的文件(如此处或此处)。我尝试了不同类型的访问(通过cat、mktemp等),但结果是一样的。
我错过了什么?是因为我在使用 VPS 并且某些东西被限制了吗?
操作系统:VPS 上的 Debian 7.3 (inotify-tools)
我在 bash 中编写了一个小“守护进程”,如果检测到它们,它将切换到耳机,如果没有,则切换到带有 PulseAudio 的外部 USB 扬声器。
我正在寻找的是某种方式来获取文件更改的通知/proc/asound/card0/codec#0,就像inotifywait在真实文件上一样(将 /proc 下的文件视为“伪文件”)。
我找到我的代码有点疯狂,因为它运行sleep 1与awk整个一天,也就是86400次,每天:)
while sleep 1; do
_1=${_2:-}
_2=$(awk '/Pin-ctls/{n++;if(n==4)print}' '/proc/asound/card0/codec#0')
[[ ${_1:-} = $_2 ]] ||
if [[ $_2 =~ OUT ]]; then
use_speakers
else
use_internal
fi
done
Run Code Online (Sandbox Code Playgroud)
我正在寻找的是类似的东西(这个例子不起作用):
codec=/proc/asound/card0/codec#0
while inotifywait $codec; do
if [[ $(awk '/Pin-ctls/{n++;if(n==4)print}' $codec) =~ OUT ]]; then
use_speakers
else
use_internal
fi
done
Run Code Online (Sandbox Code Playgroud)
这样,只有在$codec文件发生实际更改时,才会运行循环内的命令。
当我打开 mutt 时,直到我按下一个键,例如向下箭头,我才会看到新的电子邮件。然后出现新的电子邮件。有没有办法让 mutt 识别新电子邮件已经到达,并自动显示电子邮件,而不必每隔几分钟按下一个键?
我正在使用 maildir 格式(本地存储的电子邮件)。最好的方法是什么?mutt 应该每 n 秒检查一次,还是应该由操作系统通知,也许使用 inotify ?