Сокет активен, службы нет: обращения повисают
Активный сокет открывает порт до запуска службы, поэтому клиенты подключаются успешно и ждут ответа. Если службы нет или она замаскирована, соединение просто висит — снаружи это выглядит хуже отказа, потому что клиент не получает ошибки.
Вероятные причины
По порядку: сверху то, что встречается чаще.
-
Службы с соответствующим именем нет
Сокет держит порт и при обращении пытается запустить службу. Её отсутствие даёт отказ активации, а клиент остаётся в ожидании.
-
Служба замаскирована
Маскировка делает запуск невозможным. Сокет продолжает принимать обращения и отказывать при активации.
-
Служба падает сразу после активации
Сокет принимает обращение, служба запускается и падает. Клиент получает разрыв соединения без объяснения.
Диагностика
Команды идут в том порядке, в котором их стоит выполнять: каждая следующая проверяет то, что осталось после предыдущей.
Какую службу активирует сокет и сколько соединений.
systemctl show myapp.socket -p Unit -p NConnectionsСостояние активируемой службы.
systemctl status myapp.service --no-pager | head -8Журнал сокета и службы вместе: видна последовательность.
journalctl -u myapp.socket -u myapp.service -n 30 --no-pagerРешение
Решение своё для каждой причины. Сначала определите, какая из них ваша, — иначе правки наложатся друг на друга.
- Почему происходит
- Сокет держит порт и при обращении пытается запустить службу. Её отсутствие даёт отказ активации, а клиент остаётся в ожидании.
- Как проверить
-
Посмотрите сокет и наличие службы.
systemctl show myapp.socket -p Unit systemctl list-unit-files "myapp*" --no-legend
- Как исправить
- Создайте службу с нужным именем или укажите её явно. Сокет без службы бесполезен и вводит клиентов в заблуждение.
- Почему происходит
- Маскировка делает запуск невозможным. Сокет продолжает принимать обращения и отказывать при активации.
- Как проверить
-
Посмотрите состояние службы.
systemctl is-enabled myapp.service 2>&1; systemctl status myapp.service --no-pager 2>&1 | head -4
- Как исправить
-
Снимите маскировку со службы либо остановите и отключите сокет. Оставлять открытый порт без обслуживания нельзя.
sudo systemctl unmask myapp.service
- Почему происходит
- Сокет принимает обращение, служба запускается и падает. Клиент получает разрыв соединения без объяснения.
- Как проверить
-
Посмотрите журнал службы после обращения.
journalctl -u myapp.service -n 30 --no-pager | tail -15
- Как исправить
- Разберите падение службы обычным порядком. Сокет-активация усложняет разбор: обращение и отказ разнесены по времени.
Пример вывода
Сокет активен, служба замаскирована. Пример показательный: он собран на тестовой машине специально для этой страницы, а не взят из чужого журнала.
systemd[1]: myapp.socket: Failed to queue service startup job (Maybe the service file is missing or not a non-template unit?): Unit myapp.service is masked.
systemd[1]: myapp.socket: Failed with result 'resources'.
$ sudo ss -tlnp | grep :8080
LISTEN 0 4096 *:8080 *:* users:(("systemd",pid=1,fd=46))
Связанные ошибки
- Unit is masked: служба запрещена к запуску Сообщение Unit is masked: unit заблокирован ссылкой на /dev/null. Как найти и снять маскировку.
- Служба не получает сокет при сокет-активации Сокет активен, служба запускается, но не находит переданный дескриптор. Разбор: Accept, FileDescriptorName, соответствие имён.
- Сокет без Listen: unit загружен, но ничего не слушает В .socket не задан ни один параметр Listen…= — сокет не принимает соединения. Как объявить адрес прослушивания.
- Служба получает не тот сокет из нескольких При нескольких слушателях служба берёт первый и путает их: сокеты нужно различать по имени.
- Bad file descriptor в журнале службы Ошибка 9 при операции с файлом: дескриптор закрыт или не тот. Разбор для служб и сокет-активации.
- File exists при создании файла или сокета Ошибка 17: объект уже существует. Разбор для сокетов, файлов блокировки и каталогов службы.
- MySQL: Can't connect to local server through socket Клиент не находит unix-сокет MySQL: сервер не запущен, путь к сокету другой, каталог в /run не создан.
- Puma слушает сокет, а веб-сервер получает отказ доступа Разъём между приложением и веб-сервером: сокет создаётся с правами приложения, читает его другой пользователь.
Источники
-
systemd.socket(5)
Активация службы по обращению и её отказы. -
Воспроизведено на тестовой машине, systemd 255 (Ubuntu 24.04)
Проверено на systemd 255: при замаскированной службе сокет отказывает при активации.