Про распил

Jul 11, 2017 01:54

Хотел в заголовок поставить слово "микросервисы", но все же не про них речь.

Дело такое. Есть у меня сервис, обеспечивающий первые 2 этапа ETL-процесса: загрузка сырых данных с источников и трансформаця их в каноничный внутренний формат. Этот формат потом жрет платная сложная тула, которая раскидывает из него данные по табличкам детального слоя, data vault и всё такое.

Сервис представляет из себя планировщик quartz, в который пихаются задачи на загрузку и трансформацию. При этом с одного источникам мы можем загружать разные документы, и, скорей всего, это будут разные процессы. В простейшем случае (всего один тип документа и один "реестр") имеем 2 джоба (загрузка и трансформация), в сложном - 2-3 десятка. Есть еще такой момент, что может существовать одна реализация YobaLoaderJob, которая в конфигах тиражируется на 12 задач с разными параметрами.

С точки зрения кода, если отбросить весь common и utility код, имеем ОДНУ библиотеку, где по папочкам разложены реализации всего этого зверинца. В целом, это было достаточно удобно:
- простая и понятная структура проектов (хост, реализация, тесты)
- элементарное добавление нового источника (запилил реализацию, накалякал тестов, занес задачи в конфиг планировщика нужного контура и погнали)
- удобный рефакторинг (с точки зрения унификации - все рядышком, посмотрел, подумал, обобщил; с точки зрения правок базовых классов - всё, что можно сломать, лежит в этом же проекте)
- легкий деплой (один раз настроил сценарий разворачивания хоста и всё)

К сожалению, минусы стали такими жирными, что теперь каждый новый источник делает меня грустить. А именно:
1. правка одного источника приводит к необходимости рестартовать все (аналогично, если надо отключить один конкретный процесс)
2. библиотека с реализациями обросла диким количеством зависимостей, а ее выхлоп весит много мегабайтов
3. когда хост запущен, он штатно жрет память в пределах 8-14 Гб, что сильно осложняет снятие и исследование дампов
4. когда какие-то процессы штатно не реагируют на сигнал завершения работы (сервис не тормозит ни за 2, ни за 5, ни за 15 минут) очень трудной найти причину (см. п3)
5. примитивные мониторинги (состояние сервиса, его потребление ресурсов) становятся абсолютно бесполезны, поскольку на фоне больших и ресурсоемких источников мелкие не видны
6. все задачи кроме своего штатного расписания имеют триггер "выполниться при запуске", что реально нагибает базу, из-за чего треть процессов получает отлуп и логи краснеют
7. долгий цикл CI/CD (для одного контура оно строится 3-4 минуты, примерно столько же идут тесты, еще 3-10 минут уходит на деплой). Итого, между запуском билда и наблюдаемой активностью проходит минут 10 минимум.

Логично, что всё это дело надо распилить, но у меня нет четкого понимания, как это сделать, чтобы не усложнять разработку. Как организовать структуру проектов и как правильно выбрать гранулярность. То есть, можно представить вот такую шкалу, на какое количество логики надо создавать отдельный сервис:
1. один для всех (текущий вариант)
2. один на источник
3. один на группу зависимостей (идея примерно такая: все джобы которые, к примеру, ходят на ftp, наследуют один класс ведут себя одинаково и им не нужен остальной хлам)
4. один на каждый джоб (другая крайность)
* п2 и п3 могут только чуть облегчить боль, но проблему они не решают

Понятно, что хотелось бы иметь п4 ОДИН ХОСТ НА КАЖДЫЙ ДЖОБ. Но как этого добиться?

По поводу сценариев сборки и развертывания я беспокоюсь мало, в худшем случае всегда можно на коленке собрать "сервер приложений", который будет мониторить папки, находить изменения, стопарить процесс и запускать с новыми сырцами. Это просто. Написать билд, который что-то соберет по определенным паттернам названий проектов еще проще.

Но я не понимаю, как это организовать в коде. Я уже выше писал, одна имплементация может иметь несколько инстансов в конфиге. И так выходит, что у меня 350+ джобов, и на каждый на выходе должен получиться типо отдельный запускаемый бинарник? Очень стремно. На каждую реализацию делать по одному проекту, прикладывать туда все необходимые конфиги, а сервер приложений из них запустит по отдельному хосту?

Я в растерянности. Не знаю, акторы-хуякторы и прочие трендовые микросервисы не помогают.
Может, у кого есть подобный опыт? Ну или соображения на этот счет?

[dw]

etl, c, программирование

Previous post Next post
Up