Обновить
40

Пользователь

30
Подписчики
Отправить сообщение

Хм, гипермедиа системы - это про очень специфический набор систем, при чем тут инциденты, где есть просто задачи на базовые работы с сущностями? И наличие вложений или изображений не делает систему "гипермедиа", там нет про набор внутренних связей. Даже не всякий документооборот является гипермедиа.
REST проектировался для очень узкого класса систем, к которым да, относится статический web на html, но к которому никак не относится отдельный сервис в распределенной системе.
И да, поэтому в рамках данной статьи выбор REST - явная архитектурная ошибка (впрочем, их в этой статье вообще довольно много). И ошибочный выбор стиля API - не может быть про "идеальное",

Если бы статья называлась "как быстро сделать хоть какой-нибудь API" - не было бы вопросов. Но вот "идеальным" результат назвать никак нельзя.

Причем Филдинг говорил, что REST подходит для гипер-медиа систем, к которым работа с инцидентами никак не относится. И зачем использовать недоREST вместо RPC - не понятно.
При том, что RPC нормально накладывается на OOP (в отличии от REST-style, который с ООП очень плохо соотносится).
Так что в данном сценарии выбор REST-style - является явной ошибкой дизайна и категорически "неидеальным" API.

Так темпорал позволяет делать и так и так.
Т.е. пришел запрос, его сохранили, обрабатываем и отдаем ответ синхронно. Но если в процессе обработки проблемы - кидаем timeout или просьбу повторить запрос. В таком подходе гораздо меньше проблем с отсутствием response, нет проблем с "локальностью контекста" и гораздо ниже latency.
При этом во многих случаях при проблемах с обработкой вообще не надо ничего делать, просто вернуть ошибку, а темпорал нужен только на "самом верху", только при инициализации бизнес-процесса и только на случай крайне редких сбоев (благо современная инфраструктура позволяет сделать синхронный вызов не менее надежным, нежели кафка).

И да и нет.
Асинхронное взаимодействие с состоянием более хрупкое (проще сломать) и сложнее в администрировании. Синхронное в современных условиях, при наличии оркестрации в стиле Temporal - самый простой способ работы в современных распределенных системах.

Ну, рефакторинг монолита обычно проще (на нормальных языках). В микросервисах любые изменения за пределами одного микросервиса становятся крайне сложными.
Так что микросервисы протухают, обычно, много быстрее. Обычно - еще до выхода в продакшен (

  1. Хм, зависит в любом случае и дело тут не в слоях. В любом случае если сервис A и сервис B как-то взаимодействуют, то они зависят друг от друга. И в асинхронном взаимодействии эта зависимость гораздо больше (так как нет возможности нормально поддерживать версионирование).
    Ну и Event Sourcing не обязательно про асинхронное взаимодействие. И торможение на, например, чтение (которое синхронное) никак и никто не компенсирует.
    Так что это все легенды и мифы, в реальности автономность для раздельных сервисов получить очень сложно и, в реальности, не нужно.

  2. Язык не содержит слова create или update. Но issueCard или там changeName - это как раз вполне себе CRUD операции (create и update). Исключение - команды, меняющие множество агрегатов, но это вообще отдельная тема и в CRUD и в DDD.

    И пара разных create могут быть в одном агрегате, не говоря уж про один BC (в котором может быть много агрегатов). Например создание разных вариантов одной сущности, типа createRectangle и createSquare на агрегате геометрических фигур.

Не, не противоречат. Просто книжки надо читать внимательно.

1. В рамках МСА можно говорить о выделении сервисов по бизнес-функциям. Но далеко не всегда МСА является подходящим стилем для конкретного продукта, более того, часто гораздо удобнее использовать другие распределенные стили (от других вариантов SOA и до каких-нибудь pipes-and-filters). И да, большая часть компаний, говорящих об использовании МСА - использует что-то другое. Кстати, даже у Ньюмана в определении МСА - нет ничего про "around business capabilities". И, да, business capability - не то же, что и business function. Хотя разница там достаточно тонкая, да.

2. Угу. Но в реальности для МСА не получается ни индивидуального деплоя (так как сервисы зависят по API и не могут выкладываться полностью независимо) ни индивидуального масштабирования (так как сервисы зависят друг от друга и один тормозящий сервис авторизации убивает масштабирование всех прочих). Фаулер пишет не про априорное свойство МСА, а про стремление к выполнению этого свойства. В реальности, увы, это свойство крайне редко достижимо.

3. И каким образом из определения Problem space вылезли business functions (которые, вообще говоря, несколько про другое).

4. Я Эванса читал. И да, у тебя методы идут из языка. Поэтому для Create будет пара глаголов (по созданию агрегата), для Update еще с пяток (по разным изменениям агрегата, для Select - тоже несколько. Но это вообще не какое-то свойство DDD, это вообще база ООП. И в любом CRUD у тебя тоже будут разные методы для разных задач, но эти методы будут сводится к одному из 4х типов. Только не надо путать CRUD и дурно-понятный REST.

Эээ, меньше читайте разные кривые ссылки.
Микросервисы никак не лучше в масштабировании, нежели монолиты. Даже наоборот, в МСА больше взаимодействий, так что масштабирование в МСА сложнее, чем горизонтальное масштабирование монолита (тем более модульного монолита). И да, я много раз масштабировал монолит, никаких проблем с этим нет.

Business function - это не DDD, это просто про "бизнес-функции". Да и выделение сервисов по бизнес-функциям - довольно спорная идея, работающая, опять-таки, при отсутствии НФТ. И да, про " developed, deployed, and scaled independently" - это рекламная агитка, в реальности ничего из этого не получается (по вполне очевидным причинам).

Хм, вот чем комады в DDD - не CRUD? Или путаете CRUD с плохо понятым REST? Или CRUD - это когда у объекта ровно 4 метода? Но это все никак не про CRUD. В ссылке на SO - написано что-то очень странное, зачем такое читать?

А пишу я на основании своего и не только своего опыта, многочисленных книжек, обсуждений и докладов. Ну и просто базовой логики )

Охх. DDD категорически не про масштабирование (так как работает только если нет существенных нефункциональных требований), впрочем и микросервисы не про масштабирование (по крайней мере - не про масштабирование решения, но может про масштабирование по числу команд разработки). CQRS тоже редко помогает при масштабировании, а уж Event Sourcing скорее мешает. И у Вернона и Ричардсона (остальных, увы, не читал) очень часто написаны довольно спорные утверждения.

Хм, пока не видно никаких поводов уходить от БД. Так что не понятно, с чего бы тут упоминать Мартина.

DDD - да, разработка, ориентированная на домен (перевод как "предметно-ориентированная" довольно сомнителен). CRUD - это как раз описание конкретных операций с элементами домена (агрегатами). CRUD - это просто четыре типа команд DDD (и, кстати, уже разделены command и query). И DDD - как раз про метод реализации CRUD (т.е. как именно реализовывать различные варианты create-read-update-delete). Не понятно, как можно вообще противопоставлять CRUD и DDD.

Ну, я бы не назвал event sourcing хорошей практикой, это крайне редко когда полезный подход, в очень, очень специфических условиях. CQRS, впрочем, тоже. И к DDD эти паттерны не имеют особого отношения, просто очередная попса. Впрочем, и микросервисы в большинстве случаев будут неудачным решением.
Луковая архитектура тоже никак не помогает уйти от БД, с чего бы это? Там точно так же нужно работать с сущностями и точно так же реляционки с этим справляются проще других подходов (а использование монги - вообще характерный признак проблем с архитектурой проекта).
Не понял, что значит фраза "в случае crud DDD избыточен"? Это бессмысленное утверждение, весь тактический DDD - про реализацию CRUD.

Ну, сам Вернон к DDD относится, ээ, не очень, лучше уж Эванса читать.
Но вообще DDD ни в коем случае не про "против СУБД" или "против join". DDD - просто по подход к работе с предметной областью (иерархия доменов, использование словаря для выделения контестов, описание методов взаимодействия доменов) и некоторая терминология для реализации (агрегаты, value object, доменные события).
Никаких реальных технических паттернов ни в стратегии, ни в тактике нет (хотя в книжке и используется слово паттерн - это совсем не в смысле Банды Четырех или там Фаулера), есть только некоторый набор именованных концепций.
Ну и nosql, конечно, никак не связан с DDD (да и вообще слово без содержания). Ну и CRUD никак не противоречит DDD, собственно для круд-проектов DDD и применим лучше всего (для более сложных систем в DDD возникают проблемы).
Ну и надо еще помнить про DDD Trilema (т.е. DDD применим только для продуктов без существенных НФТ).

Увы, но то, что вы описали как DDD - никак в Domain Driven Development не соотносится, это какие-то странные фантазии на тему скорее Вернона, нежели Эванса.

А зачем давать "свой код"? Можно делать regexp по stacktrace или вообще по логгеру (методу), обычно для кластеризации ошибок этого хватает.
И даже если сообщение поменяется - то это значит, что события до деплоя и после деплоя попадут в два разных issue - но это, кажется, не так часто и не так страшно.

Хм, все равно не понятно, откуда появилось 5000 IOPS даже для неравномерной нагрузки со средним в 30rps? При этом 5000 - странное число, для HDD слишком много, для SSD слишком мало.

Ну и вставки даже в 100 записей не сильно увеличивают требования по памяти (совсем не увеличивают), а производительность улучшают многократно. Я уж не говорю про bulk insert, который работает много эффективнее простого insert.

Т.е. интересно, во что точно вы упирались - но это не память и не IOPSы, а что-то совсем другое. И вряд ли тут проблема в MS SQL.

1) Ага, тут проблема не в числе событий, а в их объеме. К сожалению, не знаю специфики, если эти 5-7 мегбайт хорошо пакуются (json/xml/etc), то в том же CH будут храниться довольно экономно, так что можно и на дешевом железе все сохранить. Впрочем, могут быть и другие варианты, когда крупные блобы с ответами вообще живут не в общей системе логирования, а отдельно (я такое встречал). Тогда задача про структурирование всех остальных записей.

2) Насколько помню, в OpenTelemetry предполагается отправлять логи по факту окончания обработки запроса (внутри спана), а это лишает нужной информации в самых противных случаях (падение сервиса или потеря связи). Ну и как хранилище otlp очень, ээ, неторопливый. Описание архитектуры не нашел, но бенчмарки очень разочаровывают, типа 10k rps на ядро, это очень мало (у меня некоторые сервисы больше rps на ядро обрабатывают).

Это вообще проблема современных популярных инструментов логирования (ELK стек и т.п.) - они работают гораздо медленнее, чем современные решения на java/go/c#. Потому и возникает желание "писать только info, делать сэмплинг" и прочие попытки маскировать проблемы инструментов "лучшими практиками".
Но в тот же Clikhouse я легко получал что-то около 100k string-per-second на ядро на шпиндельных дисках, на vector.io тоже около десятка тысяч rps на полядра в режиме сайдкара.

Но подобрав/доработав нормальный инструментарий - можно решить кучу проблем с логированием.

Не совсем понял арифметику. 200rps * 20 строк - это всего 4000 строк в секунду, до 50k строк нужно писать 2500 строк на запрос. Впрочем, если взять Clickhouse вместо ELK-стека, то это достаточно нормальные объемы, ничего страшного.

Sentry - это инструмент, в первую очередь, для аналитики по exception - для объединения одинаковых проблем в одну задачу, для генерации задач в трекере и так далее.
Но все тоже можно сделать более-менее простыми запросами поверх того же Clickhouse или VictoriaLogs - и зачем тогда Sentry?

А зачем для записи лога транзакций там много IOPS? Можно же (и нужно) просто лить пачками. Ну а миллионы в сутки - это вообще 30 в секунду, откуда там появилось 5000 IOPS?
Да, память для MS SQL имеет значение, но в 2015м 4GB оперативки - вполне норм.

А что у вас тогда используется? Что прошло аудит?

Ну и Клеппман пишет, по большей части, о более сложных сценариях, нежели описаны в статье. Возможно, автор никогда не сталкивался с действительно сложными и крупными базами и проблемами целостности в них.

Да ладно, я в 2007 году спокойно делал 100 пишущих транзакций в секунду со сложной обработкой на тех же двух ядрах и не было с этим никаких проблем. Вот 10k пишущих транзакций в секунду на дешевом железе времен HDD - уже вызов, да.

Информация

В рейтинге
5 410-й
Зарегистрирован
Активность