PathExists=, PathChanged= и наблюдение за путями
Параметры секции [Path] задают, за чем следит path-unit: существование файла, его изменение, непустой каталог. При срабатывании systemd запускает связанную службу.
Что делает
Разница между вариантами важна на практике. PathExists= срабатывает, когда файл появился, и повторно не сработает, пока тот не исчезнет. DirectoryNotEmpty= срабатывает снова и снова, пока каталог не пуст — именно это нужно для обработки очереди файлов.
Наблюдение работает через уведомления ядра, поэтому на части сетевых файловых систем оно не срабатывает. Для таких случаев остаётся опрос таймером.
Где ставится. В секции [Path]. Запускаемая служба берётся по имени unit или задаётся параметром Unit=.
Значения
| Значение | Что происходит |
|---|---|
PathExists=/etc/myapp/trigger | файл появился. |
PathExistsGlob=/var/spool/myapp/*.job | появился файл по образцу. |
PathChanged=/etc/myapp/config.yml | файл изменён и закрыт. |
PathModified=/var/log/myapp/out.log | файл изменён, в том числе без закрытия. |
DirectoryNotEmpty=/var/spool/myapp | в каталоге есть файлы; срабатывает повторно. |
MakeDirectory=yes | создать наблюдаемый каталог, если его нет. |
Пример
Обработка очереди файлов по мере их появления.
# process-spool.path
[Path]
DirectoryNotEmpty=/var/spool/myapp
MakeDirectory=yes
DirectoryMode=0750
[Install]
WantedBy=paths.target
# process-spool.service — без RemainAfterExit, иначе сработает один раз
[Service]
Type=oneshot
ExecStart=/usr/local/bin/process-spool
Задача обязана завершаться: пока служба активна, новое срабатывание её не запустит.
Типичные ошибки
PathExists= срабатывает однократно: для очереди нужен DirectoryNotEmpty=.
Если служба остаётся активной (RemainAfterExit=yes), повторные срабатывания ничего не делают.
В автозапуск нужно ставить path-unit, а не службу.
На части сетевых файловых систем уведомления ядра не работают, и наблюдение не срабатывает.
Связанные ошибки
- Path-unit не реагирует на измененияUnit .path не запускает службу при появлении или изменении файла. Разбор: не включён, следит не за тем, служба уже активна.
- status=0/SUCCESS, но служба считается упавшейПрограмма завершилась успешно, а systemctl показывает inactive или failed. Разбор: Type=simple против forking, RemainAfterExit, демонизация.
Рядом стоящие параметры
Источники
- systemd.path(5)
- Воспроизведено на тестовой машине, systemd 255 (Ubuntu 24.04)