Как отслеживать полное дерево каталогов на предмет изменений в Linux?
Как я могу отслеживать все дерево каталогов на предмет изменений в Linux (файловая системаext3)?
В настоящее время каталог содержит около полумиллиона файлов в примерно 3000 подкаталогах, организованных на трех уровнях каталога.
В основном это небольшие файлы (< 1 КБ, некоторые - до 100 КБ). Это своего рода очередь, и мне нужно знать, когда файлы создаются, удаляются или их содержимое изменяется в течение 5-10 секунд после этого.
Я знаю, что есть inotify и сортирует, но AFAIK они контролируют только один каталог, а это значит, что в моем случае мне понадобится 3000 дескрипторов inotify - больше, чем обычные 1024 дескриптора, разрешенные для одного процесса. Или я не прав?
В случае, если система Linux не может сказать мне, что мне нужно: возможно, есть проект FUSE, который имитирует файловую систему (реплицирует все обращения к файлам в реальной файловой системе) и отдельно регистрирует все модификации (не может точно)?
11 ответов
Насколько мне известно, нет другого пути, чем рекурсивная установка inotify
смотреть на каждый каталог.
Тем не менее, вы не исчерпаете файловые дескрипторы, потому что inotify
не нужно резервировать fd для просмотра файла или каталога (его предшественник, dnotify
страдал от этого ограничения). inotify
вместо этого использует "дескрипторы часов".
Согласно документации для inotifywatch, ограничение по умолчанию составляет 8192 дескриптора наблюдения, и вы можете увеличить его, записав новое значение в /proc/sys/fs/inotify/max_user_watches
,
Я сделал что-то подобное, используя inotifywait
инструмент:
#!/bin/bash
while true; do
inotifywait -e modify,create,delete -r /path/to/your/dir && \
<some command to execute when a file event is recorded>
done
Это настроит рекурсивный просмотр каталогов по всему дереву и позволит вам выполнить команду, когда что-то изменится. Если вы просто хотите просмотреть изменения, вы можете добавить -m
флаг, чтобы перевести его в режим монитора.
$ inotifywait -m -r /path/to/your/directory
Этой команды достаточно для рекурсивного просмотра каталога для всех событий, таких как доступ, открытие, создание, удаление...
inotify - лучший вариант, когда у вас много подкаталогов, но если нет, я привык использовать эту команду ниже:
watch -d find <<path>>
Используйте inotifywait от inotify-tools:
sudo apt install inotify-tools
Теперь создайте скрипт myscript.sh
это включает в себя скрытые файлы и папки тоже:
#!/bin/bash
while true; do
inotifywait -e modify,create,delete,move -r $1
done
Сделайте скрипт исполняемым с chmod +x myscript.sh
Запустить его с ./myscript.sh /folder/to/monitor
Если вы не предоставите аргумент, он будет использовать рабочий каталог по умолчанию.
Также вы можете запустить несколько команд добавления && \
в конце предыдущей команды добавить следующую:
#!/bin/bash
while true; do
inotifywait -e modify,create,delete,move -r $1 && \
echo "event" && \
echo "event 2"
done
Если вы не хотите выполнять какие-либо команды для событий, просто запустите команду непосредственно с -m
модификатор так не закрывается:
inotifywait -e modify,create,delete,move -m -r /path/to/your/dir
У меня есть другое предложение, только для изменений в файлах и записи изменений истории
использовать git
cd /folder_to_monitor
git init
git add *
git commit -m "first snapshot"
поэтому после внесения изменений
git diff
Разве Fanotify не должен был предоставить такую возможность в конце концов? Цитируя LWN:
"У fanotify есть два основных" режима ", направленных и глобальных. Вместо этого [...] fanotify global указывает, что ему нужно все в системе, а затем индивидуально помечает иноды, которые ему не нужны. "
Я потерял след, каким был его последний статус.
Я столкнулся с той же проблемой: у меня была программа, которая создавала некоторые файлы (начинающиеся с точки), содержимое которых я хотел проверить вручную, но она автоматически удаляла их снова вскоре после создания.
Использование inotify в цикле без параметра монитора у меня не сработало, потому что оно было слишком медленным и пропускало события, поэтому я придумал этот скрипт:
target="$1"
cd "$target"
mkdir backup/
inotifywait -e modify,create,delete --monitor -r --include "\..*" "$target" | \
while read line
do
echo "$line"
if [[ "$line" == "$target CREATE "* ]] || [[ "$line" == "$target MODIFY "* ]]
then
filename=${line#"$target CREATE "}
filename=${filename#"$target MODIFY "}
cp --verbose "$filename" backup/
fi
done
Специально для больших и сложных задач мониторинга, в котором вы хотите, чтобы вызвать события, основанные на том, что вы видите, проверить сторож Файл смотреть службы. Вот простой пример запуска инструмента minify-css при каждом изменении файла CSS:
$ watchman watch ~/src
$ watchman -- trigger ~/src buildme '*.css' -- minify-css
Он выполняет всестороннее ведение журнала, может эффективно обрабатывать несколько наблюдений, которые перекрываются в структуре каталогов, может управляться из командной строки или через json и многое другое. Смотрите также
Он доступен через Debian Sid и Ubuntu 20.04 и почти дважды попал в Fedora из того, что я вижу (1450590 и 1564720).
используйте команду watch, она проста в использовании и является встроенной командой Linux (установлена почти в каждом дистрибутиве Linux)
watch -n <interval> <command> <path>
например
это будет показывать изменения каталога /tmp/test каждые 200 миллисекунд.
watch -n 0.2 ls -la /tmp/test
для рекурсивного использования вы можете использовать часы , как показано ниже
watch -n 0.2 find <path>
Я использую это, чтобы получить краткий обзор в текущем каталоге:
watch 'find . -printf "%T@ %Tc %p\n" | sort -nr | head '