Сокет с каналом: права не позволяют писать
Именованный канал создаёт systemd, и права на него берутся из описания сокета. Клиенты, не входящие в группу-владельца, писать не смогут — и это самая частая причина молчания такой схемы.
Вероятные причины
По порядку: сверху то, что встречается чаще.
-
Права канала не позволяют запись клиентам
По умолчанию канал создаётся с правами владельца. Другие процессы в него не пишут.
-
Каталог канала не создаётся
Как и для unix-сокетов, каталог в /run нужно объявить через параметр службы.
-
Клиент открывает канал на запись раньше читателя
Открытие канала на запись блокируется, пока нет читателя. При сокет-активации служба поднимается по обращению, но порядок всё равно важен.
Диагностика
Команды идут в том порядке, в котором их стоит выполнять: каждая следующая проверяет то, что осталось после предыдущей.
Права и владелец канала.
sudo ls -l /run/myapp/Описание сокета целиком.
systemctl cat myapp.socketРешение
Решение своё для каждой причины. Сначала определите, какая из них ваша, — иначе правки наложатся друг на друга.
- Почему происходит
- По умолчанию канал создаётся с правами владельца. Другие процессы в него не пишут.
- Как проверить
-
Посмотрите права и описание сокета.
sudo ls -l /run/myapp/input systemctl cat myapp.socket | grep -iE "SocketUser|SocketGroup|SocketMode"
- Как исправить
- Задайте группу и права канала в описании сокета: общая группа с клиентами и права 0620.
- Почему происходит
- Как и для unix-сокетов, каталог в /run нужно объявить через параметр службы.
- Как проверить
-
Посмотрите каталог и параметр.
ls -ld /run/myapp 2>/dev/null systemctl show myapp.service -p RuntimeDirectory
- Как исправить
-
Объявите каталог через
RuntimeDirectory=в службе, которую активирует сокет.
- Почему происходит
- Открытие канала на запись блокируется, пока нет читателя. При сокет-активации служба поднимается по обращению, но порядок всё равно важен.
- Как проверить
-
Посмотрите состояние сокета и службы.
systemctl status myapp.socket --no-pager | head -6
- Как исправить
- Держите сокет включённым постоянно: тогда systemd будет читателем и обращения не заблокируются.
Пример вывода
Клиент не может писать в канал. Пример показательный: он собран на тестовой машине специально для этой страницы, а не взят из чужого журнала.
$ sudo ls -l /run/myapp/input
prw------- 1 app app 0 Sep 15 16:02 /run/myapp/input
$ echo test > /run/myapp/input
bash: /run/myapp/input: Permission denied
Связанные ошибки
- status=235/CHOWN в systemd Код 235/CHOWN: не удалось изменить владельца сокета. Код относится только к unit-файлам сокетов.
- Permission denied в журнале службы Отказ в доступе у службы systemd: права на файл, каталоги по пути, пользователь службы, параметры изоляции, SELinux и AppArmor.
- Сокет без Listen: unit загружен, но ничего не слушает В .socket не задан ни один параметр Listen…= — сокет не принимает соединения. Как объявить адрес прослушивания.
- Puma слушает сокет, а веб-сервер получает отказ доступа Разъём между приложением и веб-сервером: сокет создаётся с правами приложения, читает его другой пользователь.
- uWSGI: веб-сервер не может писать в сокет nginx получает отказ доступа к сокету uWSGI: права и владелец сокета задаются в описании приложения.
- Служба не видит, кто обратился по сокету Сведения о вызывающем не приходят: передача учётных данных через сокет включается отдельно.
- Фильтр почты недоступен почтовой службе: сокет и группы Почтовая служба не может обратиться к фильтру: сокет создан с правами, недоступными её пользователю.
- AppArmor: apparmor="DENIED" в журнале ядра Профиль AppArmor запретил операцию: как прочитать запись, найти профиль и поправить его правильно.
Источники
-
systemd.socket(5)
ListenFIFO=, SocketUser=, SocketMode=. -
Воспроизведено на тестовой машине, systemd 255 (Ubuntu 24.04)
Воспроизведено каналом с правами 0600 при записи от другого пользователя.