Может watchman прислать, почему файл изменился?

Способен ли сторож отправлять сообщения настроенной команде, почему он отправляет файл этой команде?

Например:

  1. файл является новым для папки, возможно, будет флагом FILE_CREATE;
  2. удаленный файл передаст команде флаг FILE_DELETE;
  3. измененный файл отправит флаг FILE_MOD и т. д.
  4. Возможно, даже когда папка удаляется (и, следовательно, файлы в ней), будет отправлен параметр FOLDER_DELETE с именем папки, а также FILE_DELETE для файлов под ней / FOLDER_DELETE для папок под ней

Что-то подобное существует?


person bnoeafk    schedule 02.03.2016    source источник


Ответы (1)


Нет, это невозможно. Причины довольно фундаментальны для его дизайна. TL;DR заключается в том, что клиенту намного сложнее, чем вы думаете, правильно обрабатывать эти отдельные события, и почти во всех случаях они вам на самом деле не нужны.

Большинство систем слежения за файлами представляют собой абстракции, которые просто преобразуют специфичную для системы информацию об уведомлении в некоторую общую форму. Они не очень хорошо справляются или вообще не справляются с переполнением очереди уведомлений и не предоставляют своим клиентам способ надежно отреагировать на эту ситуацию.

Вдобавок к этому файловая система может подвергаться многим и разнообразным изменениям за очень короткий промежуток времени и из-за нескольких параллельных потоков или процессов. Это делает эту область чрезвычайно подверженной TOCTOU проблемам, с которыми трудно справиться. Например, создание и запись в файл обычно приводит к серии уведомлений о файле и содержащем его каталоге. Если файл удаляется сразу после этой последовательности (возможно, это был промежуточный файл на этапе сборки), к моменту появления уведомлений о создании файла велика вероятность, что он уже удален.

Watchman принимает входной поток уведомлений и передает его в свою внутреннюю модель файловой системы: упорядоченный список наблюдаемых файлов. Каждый раз, когда получено уведомление, сторож воспринимает его как сигнал к тому, что он должен пойти и просмотреть файл, который был сообщен как измененный, а затем переместить запись для этого файла в самый последний конец упорядоченного списка.

Когда вы запрашиваете у Watchman информацию о файловой системе, возможно или даже вероятно, что могут быть ожидающие уведомления от ядра. Чтобы минимизировать TOCTOU и обеспечить актуальность его состояния, watchman создает файл cookie синхронизации и ожидает, пока это уведомление станет видимым, прежде чем ответить на ваш запрос.

Сочетание двух вышеуказанных вещей означает, что данные результатов сторожа имеют два важных свойства:

  1. Вы гарантированно просмотрели все уведомления, которые произошли до вашего запроса.
  2. Вы получаете самую последнюю информацию для любого данного файла только один раз в результатах запроса (результаты изменений объединяются вместе)

Давайте поговорим о случае переполнения. Если ваша система не справляется со скоростью изменения файлов (например, у вас большой проект, и вы очень быстро создаете и удаляете файлы, а система сильно загружена), ОС не может вместить все ожидающие изменения. уведомления в буферных ресурсах, выделенных часам. Когда это происходит, он сбрасывает эти буферы и отправляет сигнал переполнения. Это означает, что клиент наблюдающего API пропустил некоторое количество событий и больше не синхронизируется с состоянием файловой системы. Если этот клиент поддерживает состояние файловой системы, оно больше недействительно.

Watchman решает эту проблему, повторно исследуя отслеживаемое дерево и синтетически помечая все файлы как измененные. Это заставляет следующий запрос от клиента видеть все в дереве. Мы называем это результирующим набором свежий экземпляр, потому что это то же самое представление, которое вы получите при первом запросе. Мы устанавливаем флаг в результате, чтобы клиент знал, что это произошло, и мог предпринять соответствующие шаги для исправления своего состояния. Это поведение можно настроить с помощью параметров запроса.

В этих наборах результатов свежий экземпляр мы не знаем, действительно ли изменился какой-либо данный файл или нет (возможно, он изменился таким образом, что мы не можем обнаружить с помощью lstat), и даже если мы видим, что его метаданные изменились, мы не знаем причину этого изменения.

Может быть несколько событий, которые влияют на то, почему данный файл появляется в результатах, предоставленных сторожем. Мы не записываем их по отдельности, потому что мы не можем отслеживать их с неограниченной историей; представьте себе файл, который постепенно записывается один раз в секунду в течение всего дня. Храним ли мы 86400 записей об изменениях в день и доставляем их нашим клиентам? Что, если таких файлов сотни тысяч? Нам пришлось бы обрезать эти данные, и в этот момент потеря данных снижает то, насколько хорошо вы можете рассуждать об этом.

В конце концов, клиент очень редко делает что-то большее, чем пытается прочитать файл или просмотреть его метаданные, и, вообще говоря, он хочет делать это только тогда, когда файл перестал изменяться. Для этого варианта использования watchman-wait, watchman-make и trigger имеют концепцию периода согласования, который приводит к задержке доставки уведомлений об изменениях до тех пор, пока файловая система не перестанет изменяться.

person Wez Furlong    schedule 02.03.2016
comment
Wez - прежде всего, спасибо за такой подробный ответ, я, конечно, не ожидал всего, что вы написали - просто не ожидалось! Ваше объяснение действительно помогает мне, так как я использовал предшественника для сторожа (наблюдателя, от splitbrain), но в ходе продолжающегося тестирования выяснилось, что я теряю уведомления о файлах, которые даже попадают в файловую систему (в большинстве случаев примерно 50% более 100 файлов) - я уверен, что этот проект восприимчив к тому, что вы здесь описали. Я буду упорно работать с наблюдателем в надежде, что он сможет делать то, что мне нужно. Спасибо. - person bnoeafk; 03.03.2016