Вскоре после окончания вуза устроился я в информационно-аналитическую контору. Начальство озадачилось внедрением системы сбора и обработки информации, призванной увеличить производительность труда и расширить спектр выходной продукции. От системы требовалось обеспечить сбор информации из интернета, электронных и печатных документов, осуществить их классификацию, кластеризацию и тегирование, отобразить результаты работы в веб-интерфейсе с возможностью выгрузки результатов в файлы.
Разработку и внедрение системы поручили фирме-подрядчику, начальство которой было хорошо знакомо с моим руководством. Два года длилась эпопея с разработкой и установкой программно-аппаратного комплекса. В день приёмки присутствовало высокое начальство с обеих сторон и несколько специалистов со стороны заказчика, осуществлявших тестовую эксплуатацию. Специалисты отказывались подписывать что-либо, утверждали, что система сырая и недоработанная, начальство подрядчика божилось устранить все нарекания в ходе эксплуатации, начальство заказчика ругалось на специалистов, обвиняло их в ребячестве и грозило лишениями премий за срыв приёмки, в результате чего система со скрипом была принята.
Как вы уже, наверное, догадались, после сдачи проекта никакие недостатки устранены не были, представители подрядчика имитировали бурную деятельность: приезжали, слушали жалобы, кивали головами, обещали всё исправить, но ничего не делали. Начальство заказчика ругалось на своих специалистов, почему до сих пор не видно результатов от внедрения новой дорогой системы, специалисты бегали все в мыле и пытались хоть что-то наладить.
Понемногу страсти улеглись, про систему почти забыли, перейдя на самописные костыли, но аппаратно-программный комплекс продолжал «работать» вхолостую, ведь деньги уже уплачены, а техника и ПО на гарантии — сносить ничего нельзя. И решил я как-то ради интереса поглядеть, ради чего был весь этот сыр-бор и почему это всё не используется.
В общем, заканчиваю с затянувшимся вступлением и перехожу непосредственно к описанию этого чудо-комплекса.
Комплекс состоял приблизительно из десятка серверов, каждый из которых был заточен под решение конкретной задачи: один сервер БД, один сервер управления поисковыми роботами, один сервер, собственно, этих роботов, один сервер обработки, один сервер распознавания текста, один сервер веб-интерфейса и ещё разные серверы. Все машины на момент установки уже устарели на два-три года, не отличались большой мощностью, имели оперативную память от 8 до 12 ГБ, что выглядело немного странно, учитывая наличие двух процессоров Xeon в каждом. При грамотном использовании ресурсов весь этот комплекс, в принципе, обладал бы очень неплохой вычислительной мощностью. Однако логика разработчиков, видимо, была проста: одна задача — один сервер, и неважно, что часть задач выполняется последовательно, и большую часть времени половина серверов простаивает, а вторая половина трудится на 5–10% мощности. Сервер распознавания текста вообще не использовался: Файнридер был на каждой клиентской машине.
Программная часть вообще заслуживает целого тома описаний багов и недоработок. Остановлюсь на самых ярких из них.
Подсистема сбора состоит из диспетчера и роботов. Роботы, как я уже говорил, находятся на одном сервере, диспетчер на другом, общаются они друг с другом при помощи таблички в базе данных, развёрнутой на сервере диспетчера. В диспетчере создаются новые задания на загрузку и кладутся в табличку, откуда потом их берут роботы. При этом обратной связи от роботов к диспетчеру не существует, то есть в случае сбоя узнать об этом можно, только зайдя непосредственно на сервер роботов или в следующем месяце, когда в статистике загрузок пойдут нули.
Данные для отображения в веб-интерфейсе диспетчера хранятся в отдельных таблицах БД. При любом действии в интерфейсе вызывается каскад T-SQL-запросов, который вносит изменения в основную базу, пересчитывает таблицы для отображения и потом запрашивает данные. В процессе работы размер таблиц растёт, время выполнения запросов увеличивается, и оператор, слишком быстро нажав пару кнопок, легко и непринуждённо может вызвать блокировку БД, приводящую к падению диспетчера и веб-интерфейса.
Сами роботы тоже гениальны в своей недоработанности. Задания на загрузку представляют собой ссылку на сайт и набор регулярных выражений для разбора страниц, при этом задания, вбитые при сдаче в эксплуатацию, настолько кривы, что перестают работать, если в блоке текста появится перенос строки вида <br>
. На соответствующем сервере крутится несколько инстансов процесса, каждый инстанс независимо друг от друга периодически проверяет таблицу заданий и берёт себе задание, чьё время подошло по графику, при этом ставя таймстемп о последнем выполнении, чтобы другие роботы не пошли его выполнять по новой. Если в процессе загрузки сайта происходит таймаут или какой иной сбой, робот выкидывает эксепшн и уходит в лучший мир, никого об этом не оповестив, и в результате остаётся на один процесс меньше. Если до следующего по графику выполнения сайт по-прежнему недоступен, то же повторяется со следующим роботом, и так до тех пор, пока не кончатся роботы.
Но даже если все сайты работают стабильно, роботы умрут через два-три дня, потому что они не умеют удалять из памяти ненужные больше данные и с каждым запуском отъедают всё больше и больше памяти, что в итоге приводит к их массовому самоубийству через сообщение «системе не хватает ресурсов».
Ах да, забыл сказать: на сервере диспетчера установлена 32-битная Windows XP. Это при двухпроцессорной-то архитектуре и 12 гигах памяти.
Допустим, что данные собраны успешно и легли в соответствующие таблицы MS SQL, далее их надо передать в подсистему обработки. Что тут сложного, спросите вы? А сложно то, что подсистема обработки — это крайне устаревшая проприетарная система с поисковым движком в ядре, работающая на PostgreSQL. То есть данные нужно экспортировать из одной базы в другую. Как же это рациональнее всего сделать? Конечно, сделать передачу по расписанию, которая, дабы днём не снижать производительность сервера обработки, будет каждый день в 00:00 перекидывать накопленный массив данных. Что мы получаем в итоге? Система обработки пыхтит ночь напролёт, индексируя и анализируя полученный одномоментно массив данных, пользователи получают результаты с задержкой в один день, зато сервер обработки днём совершенно разгружен и готов к выполнению работы. Вот только какой?
Далее встаёт проблема классифицировать входной поток и раскидать его по рубрикам. Соответственно, систему надо обучить, по каким критериям проводить эту классификацию. Машинное обучение, обучающая выборка, статистика часто упоминаемых слов и выражений, методы обработки естественного языка? Нет, не слышали. Вместо этого оператору предоставляется уникальная возможность полностью вручную создать классификаторы, используя для этого встроенный редактор поисковых запросов с использованием операторов И, ИЛИ, НЕ; как бонус — задать допустимое расстояние между словами.
Опять же, допустим, что всё получилось и работает нормально. Пользователь зашёл на веб-интерфейс программы обработки, отобрал нужные ему документы и хочет их себе сохранить для дальнейшей работы. Не тут-то было! Экспорт осуществляется в формате либо XML, либо XLS, при этом в экспорте не учитывается информация о рубриках, тексты лишаются намёков на форматирование, получить документ в оригинальном виде просто невозможно, хотя в базе он есть…
В общем, весь этот комплекс можно было довести до ума, обвешав по самое не балуй костылями, игнорировать большинство косячных встроенных функций, забирать данные из баз напрямую сторонними средствами, но весь этот зоопарк потребовал бы колоссальных усилий на поддержание в работоспособном виде и изменение каких-либо параметров. И что мы имеем в итоге? Дорогущая система стоимостью в несколько миллионов, развёрнутая на морально устаревшем в момент приобретения железе, разнородное ПО, скреплённое ржавыми гвоздями и неспособное работать в комплексе более пары дней, один уволившийся программист, психанувший после долгих попыток заставить всё это работать, — и ни одного дня использования этой системы по назначению вплоть до дня официального окончания поддержки, когда выжившие специалисты со скупыми мужскими слезами радости наконец удалили весь этот кошмар и развернули на серверах аналогичное самописное ПО с использованием опенсорса, возможно, тоже в чём-то глючное и несовершенное, но так хорошо справлявшееся с поставленными задачами, ютясь на обычных рабочих станциях, используемых вместо серверов!
А что начальство? А начальство уже заказало той же фирме разработку и внедрение новой системы на смену безвременно скончавшейся. Только, чувствую, в этот раз приёмка не состоится, если только не уволят всех несогласных…