Заказ был один — интерфейс к записям звонков. Нашли ещё четыре отказа
Заказчик попросил простой веб-интерфейс, чтобы слушать записи разговоров и смотреть детализацию. Пока разворачивали — обнаружили, что журналы станции пусты, 10 ГБ диска заняты невидимым файлом, защита SSH от подбора паролей не срабатывает, а наши скрипты обслуживания не могут зайти. Ни один из отказов не сообщал об ошибке.
Система сообщала о 27 ГБ занятого пространства, тогда как сумма файлов давала 17 ГБ. Разницу удерживал файл, удалённый четырьмя месяцами ранее: процесс не отпустил дескриптор, и место не освободилось.
Ни один из отказов не выдавал ошибки. Все отчитывались об успешном выполнении, поэтому и оставались незамеченными.
Общая черта: отсутствие сообщения об ошибке. Отказ, который отчитывается об успехе, живёт до первого разбора
Задача звучала просто: у заказчика есть телефонная станция, она пишет разговоры, и руководителю нужно уметь их послушать. Не выгружать файлы по SSH, не просить админа, а открыть в браузере, найти звонок по номеру и дате и нажать «play».
Работы на вечер. Но перед установкой мы посмотрели на станцию вблизи — и вечер получился длиннее.
Что получил заказчик
Веб-интерфейс к журналу звонков: детализация за всё время (110 тысяч звонков с 2023 года), поиск по номеру, направлению, статусу и длительности, прослушивание записи прямо в браузере с перемоткой, выгрузка в CSV.
Несколько решений, которые стоит назвать явно, потому что они не про удобство.
Доступ к базе — только на чтение. Интерфейс ходит в базу под отдельной учётной
записью с правом SELECT на одну таблицу. Не под той, которой станция пишет звонки.
Проверили прямо: запрос на удаление возвращает «отказано», обращение к другим базам —
тоже.
Кнопки удаления убраны. У готового интерфейса они есть: удалить запись разговора, удалить строку из журнала. Записи разговоров — это в том числе доказательная база в спорах с клиентами и подрядчиками. Возможность снести их из браузера в два клика не нужна никому.
Отключена «полезная» функция, которая отправляла номера на сторону. В интерфейсе по умолчанию включён поиск информации о номере через внешний сервис: клик по номеру — и он уходит на чужой сервер. Для телефонии заказчика это утечка, поэтому выключено.
Порт открыт только офису и нам. Не «наружу с паролем», а адресными правилами: из офисной сети и с нашего узла администрирования. Публичный интерфейс станции для интерфейса закрыт совсем.
Установка оформлена как код, а не как набор ручных шагов: на второй такой станции это один запуск.
Дальше начинается попутное
Перед установкой мы всегда смотрим, куда ставим: сколько места, что в журналах, чем занят процессор. Обычно это формальность на пять минут.
Диска нет, а файлов нет тоже
Свободно 2,5 ГБ из 30. Первая мысль — записи разговоров, их там почти 10 ГБ. Посчитали скорость роста: около двух недель до полной остановки. Стали проверять — и гипотеза рассыпалась: очистка старше ста дней работает по расписанию, объём давно стабилен.
А расхождение нашлось в другом месте: система сообщала, что занято 27 ГБ, тогда как сумма размеров всех файлов давала 17. Десять гигабайт занимал файл, которого в файловой системе уже не было — удалённый, но всё ещё открытый работающим процессом. Причина — опечатка в настройке ротации журналов, из-за которой станция четыре месяца писала «в никуда».
Подробный разбор с командами — в отдельной статье: Диск занят на 92%, а файлов — на 17 ГБ.
Журналы были пусты
Это следствие той же опечатки, и оно оказалось неприятнее нехватки места. Все текущие журналы станции были нулевого размера с апреля. То есть при любой жалобе «звонок не прошёл», «связь оборвалась», «не дозвонились» смотреть было некуда.
Вернули запись — и в первых же строках увидели непрерывный перебор паролей к телефонии из интернета. Подобранный пароль внутреннего номера означает звонки за счёт владельца станции, и суммы там измеряются не гигабайтами.
Оговорка, чтобы не преувеличивать: невидим перебор был для человека — открывать было нечего, файлы журналов пустые. Автоматическая блокировка по телефонии при этом за всё время работы закрыла около трёх тысяч адресов, и сколько из потока после апреля она успела обработать, по её счётчикам уже не установить.
Защита от подбора была включена и не работала
На станции стоит средство блокировки: заметил перебор — закрыл адрес. По телефонии оно работало и заблокировало почти три тысячи адресов. А по SSH — ни одной блокировки при десятках тысяч попыток входа.
Три независимые причины, каждой достаточно: путь к журналу указан от другого дистрибутива (файла просто нет), шаблон распознавания рассчитан на старую версию сервера и не видит строки новой, а сами записи об отказах попадают в другой файл, чем предполагает стандартная настройка. Исправили все три; первая блокировка прилетела через три секунды.
И отдельно — то, что делают до включения, а не после: адреса администрирования внесли в исключения. Иначе обычная ошибка при входе, повторённая несколько раз, заблокировала бы сам доступ к станции. Такие вещи выясняют заранее, а не после того, как перестал открываться доступ.
Скрипты обслуживания не могли зайти
Обслуживание у нас идёт скриптами: раскатать настройку, собрать отчёт, проверить состояние. На эту станцию они не заходили — из-за дефектов в нашей же настройке. И установка при этом отчитывалась об успехе: каждый шаг проверял себя, а не результат. Файл скопирован — успех. Конфигурация синтаксически верна — успех. Разница между «шаг выполнен» и «получен нужный результат» — ровно та щель, в которую провалились дефекты.
Исправили и добавили проверки результата, а не только шага — на следующих станциях не повторится.
Почему это прожило так долго
Общая черта у всех четырёх находок одна, и она важнее любой из них по отдельности: ничего не падало с ошибкой. Ротация журналов отрабатывала и отчитывалась успехом. Диск заполнялся, и мониторинг занятости честно показывал проценты — только причина в них не видна. Средство блокировки было запущено и в статусе «работает». Установка настроек проходила без единого предупреждения.
Отказ, который сообщает о себе, находят быстро — на него есть алерт, письмо, красный индикатор. Отказ, который отчитывается об успехе, живёт до того дня, когда кто-нибудь посмотрит на систему вблизи и с вопросом «а это правда работает?».
Поэтому в обслуживании ценна не только реакция на заявки. Половина находок этого вечера не имела отношения к заказу — их принесла привычка смотреть по сторонам, пока делаешь что-то другое.
Что стоит проверить у себя
Даже без подрядчика эти четыре проверки занимают минут пятнадцать:
- Сравните «занято» с суммой размеров файлов. Расхождение — признак удалённого, но открытого файла. Занятое место мониторинг видит и покажет рост; чего он не покажет — так это причину: в обычной разбивке занятого места по файлам такого файла нет.
- Проверьте, куда сервис пишет журнал и появляются ли там новые записи. Не только размер файла: сервис может писать в системный журнал или в другой файл, и нулевой размер сам по себе ещё ни о чём не говорит. Смотреть надо, растёт ли то, что он действительно использует.
- Проверьте, сколько адресов заблокировала защита от подбора. Ноль при живых попытках входа в журнале означает не тишину, а то, что защита не срабатывает.
- Убедитесь, что автоматизация действительно заходит. «Установка прошла успешно» и «настройка применилась» — разные утверждения.
Ещё по теме
- 10 ГБdf показывает 27 из 30 ГБ занято (92%), а файлы занимают только 17 ГБ
- 65→86%«Отвечено» ≠ ответил человек: как мы читаем журнал звонков колл-центра
- 23Резервные копии 1С на PostgreSQL заполнили диск — и сломали саму 1С
- 5 ГБЛоги переживают недоступность ELK: disk-assisted очередь rsyslog