Уведомления об изменениях в файлах
Несколько операционных систем поддерживают наблюдение за файловыми системами на предмет изменений в файлах или их атрибутах. При правильной настройке Emacs статически подключает соответствующую библиотеку, такую как inotify, kqueue, gfilenotify или w32notify. Эти библиотеки позволяют наблюдать за файловыми системами на локальном компьютере.
Также возможно наблюдать за файловыми системами на удалённых машинах, см. Удаленные файлы в Справочнике GNU Emacs. Это не зависит от одной из библиотек, подключенных к Emacs.
Поскольку все эти библиотеки генерируют различные события при уведомлении об изменениях в файлах, Emacs предоставляет специальную библиотеку filenotify, которая представляет собой единый интерфейс для приложений. Программы Lisp, которые хотят получать уведомления о файлах, должны всегда использовать эту библиотеку вместо системных.
- Функция: file-notify-add-watch file flags callback
-
Добавляет наблюдение за событиями в файловой системе, относящимися к файлу file. Это обеспечивает, чтобы события в файловой системе, относящиеся к file, сообщались Emacs.
Возвращаемое значение — это дескриптор добавленного наблюдения. Его тип зависит от базовой библиотеки и, как правило, нельзя считать целым числом, как в примере ниже. Его следует использовать для сравнения только с
equal.Если файл file по какой-либо причине невозможно отслеживать, эта функция сигнализирует об ошибке
file-notify-error.Иногда смонтированные файловые системы не могут отслеживаться на предмет изменений файлов. Это не обнаруживается этой функцией, и поэтому возвращаемое значение, отличное от
nil, не гарантирует, что изменения в файле file будут фактически уведомлены.flags — это список условий, определяющих, за чем будет вестись наблюдение. Он может содержать следующие символы:
changeнаблюдение за изменениями содержимого файла
attribute-changeнаблюдение за изменениями атрибутов файла, таких как разрешения или время изменения
Если file является каталогом,
changeследит за созданием и удалением файлов в этом каталоге. Некоторые из системных библиотек уведомлений о файлах также сообщают об изменениях файлов в этом случае. Это не работает рекурсивно.При возникновении любого события Emacs вызовет функцию callback, передав ей один аргумент event, который имеет вид
(descriptor action file [file1])
descriptor — это тот же объект, что и возвращаемый этой функцией. action — описание события. Он может быть любым из следующих символов:
createdфайл file был создан
deletedфайл file был удален
changedсодержимое файла file изменилось; с библиотекой w32notify также сообщает об изменениях атрибутов
renamedфайл file был переименован в file1
attribute-changedбыл изменён атрибут файла file
stoppedнаблюдение за файлом file остановлено
Обратите внимание, что библиотека w32notify не сообщает о событиях
attribute-changed. Когда изменяется какой-либо атрибут файла, например, разрешения или время последнего изменения, эта библиотека сообщает об событииchanged. Аналогично, библиотека kqueue ненадёжно сообщает об изменениях атрибутов файлов при наблюдении за каталогом.Событие
stoppedозначает, что наблюдение за файлом прекращено. Это может произойти потому, что была вызвана функцияfile-notify-rm-watch(см. ниже), или потому, что отслеживаемый файл был удален, или из-за другой ошибки, сообщённой базовой библиотекой, которая делает дальнейшее наблюдение невозможным.file и file1 — имена файла(ов), о которых сообщается событие. Например:
(require 'filenotify) ⇒ filenotify(defun my-notify-callback (event) (message "Event %S" event)) ⇒ my-notify-callback(file-notify-add-watch "/tmp" '(change attribute-change) 'my-notify-callback) ⇒ 35025468(write-region "foo" nil "/tmp/foo") ⇒ Event (35025468 created "/tmp/.#foo") Event (35025468 created "/tmp/foo") Event (35025468 changed "/tmp/foo") Event (35025468 deleted "/tmp/.#foo")(write-region "bla" nil "/tmp/foo") ⇒ Event (35025468 created "/tmp/.#foo") Event (35025468 changed "/tmp/foo") Event (35025468 deleted "/tmp/.#foo")(set-file-modes "/tmp/foo" (default-file-modes) 'nofollow) ⇒ Event (35025468 attribute-changed "/tmp/foo")Возвращается ли действие
renamedзависит от используемой библиотеки наблюдения. В противном случае, действияdeletedиcreatedмогут быть возвращены в произвольном порядке.(rename-file "/tmp/foo" "/tmp/bla") ⇒ Event (35025468 renamed "/tmp/foo" "/tmp/bla")(delete-file "/tmp/bla") ⇒ Event (35025468 deleted "/tmp/bla")
- Функция: file-notify-rm-watch descriptor
Удаляет существующее наблюдение за файлом, указанное его дескриптором descriptor. descriptor должен быть объектом, возвращённым функцией
file-notify-add-watch.
- Функция: file-notify-valid-p descriptor
-
Проверяет корректность наблюдения, заданного его дескриптором descriptor. descriptor должен быть объектом, возвращённым функцией
file-notify-add-watch.Наблюдение может стать недействительным, если файл или каталог, за которым оно наблюдает, удалены или если поток наблюдателя завершается аномально по какой-либо другой причине. Удаление наблюдения путём вызова
file-notify-rm-watchтакже делает его недействительным.(make-directory "/tmp/foo") ⇒ Event (35025468 created "/tmp/foo")(setq desc (file-notify-add-watch "/tmp/foo" '(change) 'my-notify-callback)) ⇒ 11359632(file-notify-valid-p desc) ⇒ t(write-region "bla" nil "/tmp/foo/bla") ⇒ Event (11359632 created "/tmp/foo/.#bla") Event (11359632 created "/tmp/foo/bla") Event (11359632 changed "/tmp/foo/bla") Event (11359632 deleted "/tmp/foo/.#bla");; Deleting a file in the directory doesn't invalidate the watch. (delete-file "/tmp/foo/bla") ⇒ Event (11359632 deleted "/tmp/foo/bla")(write-region "bla" nil "/tmp/foo/bla") ⇒ Event (11359632 created "/tmp/foo/.#bla") Event (11359632 created "/tmp/foo/bla") Event (11359632 changed "/tmp/foo/bla") Event (11359632 deleted "/tmp/foo/.#bla");; Deleting the directory invalidates the watch. ;; Events arrive for different watch descriptors. (delete-directory "/tmp/foo" 'recursive) ⇒ Event (35025468 deleted "/tmp/foo") Event (11359632 deleted "/tmp/foo/bla") Event (11359632 deleted "/tmp/foo") Event (11359632 stopped "/tmp/foo")(file-notify-valid-p desc) ⇒ nil
Copyright © 1990-1996, 1998-2022 Free Software Foundation, Inc.
Licensed under the GNU GPL license.
https://www.gnu.org/software/emacs/manual/html_node/elisp/File-Notifications.html