Вы забыли упомянуть, что: 1 нужно решать вопрос консистентности, пока финалтная маленькая транзакция не закомичена, система находится в неконсистентном состоянии, и нужно уметь с зтим жить. 2 процесс отката маленьких транзакций иакде может обломаться, это собственно коррелирует с первыми вопросом. И с жтим также нужно уметь жить.
0:00 В чем "пессимистичность" алгоритма двухфазного коммита (2PC) и почему это плохо в микросервисах 1:25 Паттерн Saga, определение и какую проблему он решает 4:10 Как обеспечить атомарность цепочки отдельных транзакций (Саги) 5:52 "Оптимистичность" саг ССЫЛКА НА КУРС: it-es-course.getcourse.ru/y/3b92c9c Автор курса: Андрей Суховицкий Действующий разработчик ПО, работает над проектированием и разработкой высоконагруженных систем. Последние 4 года создаю и провожу авторские курсы по микросервисной архитектуре, проектированию производительных систем и проектированию ПО в университете ИТМО и МФТИ. В 2021 году получил награду как лучший преподаватель ИТМО.
Ну, у лога транзакций много разных предназначений. Он может использоваться для восстановления состояния хранилища, для репликации. Сага - узкоспециализированный паттерн, который помогает реализовать распределенную транзакцию, объединяющую множество неоднородных хранилищ, и при этом сохраняющую свойства атомарности, долговечности и в различной мере консистентности и изолированности.
@@sukhoa по ACID тут вопросы. Транзакции - они обычно длинные не потому, что разработчик не догадался сделать их короткими, а потому что этого требует бизнес-логика. Если в длинной транзакции на счёт с 0-м остатком начисляется 100$ и должно сразу начислится 20%, как бонус за пополнение, то выполнится это должно атомарно, даже если будет длинно. Теперь представим, что параллельная короткая транзакция пытается списать 70$ с того же счёта за покупку чего-то. Без саг она, как вариант, прочтёт 0-й остаток и скажет, что недостаточно средств. Это правильно. Теперь вариант с патерном саги, делим долгую транзакцию: комитим 100$ ( -100 компенсационная ), но тут встревает эта короткая и списывает 70$. И на что же мы будем начислять %? На 30$ вместо 100? А если у разбитой транзакции откат, от какого остатка произойдет компенсация?
Да, дело тут не столько в атомарности, сколько в изолированности. Давайте рассмотрим несколько вариантов. 1. Конечно, сумма процента должна вычисляться не от текущего состояния счета, а от суммы начисления. Эта информация будет передаваться в сообщениях (событиях). Поэтому 20% всегда начислятся верно 2. Для организации изоляции в сагах могут использоваться целый ряд так называемых "контр-мер", каждая из которых помогает избавиться от определенных аномалий изоляции (dirty read, non-repeatable read, read uncommitted). В данном случае, вы можете сделать так, что параллельные саги не увидят, что сумма на счету более 0 до тех пор, пока не будет внесен и необходимый процент-бонус. То есть сделать эти 100$ "невидимыми", избавиться от аномалии read-uncommitted. 3. Есть очень много вариантов, я очень подробно разбираю похожую сагу в курсе. Еще вы всегда можете прочитать про контр-меры в этой научной статье "Semantic ACID Properties in Multidatabases Using RPC and Update Propagations. Lars Frank and Torben U. Zahle"
@@sukhoa да, спасибо. Похоже всё-таки, что патерн в первую очередь для распределённых систем, где у каждого микросервиса м. б. своя БД, свои шарды, но все они должны отработать последовательно, как единое целое. Там да - Сага будет делать ретраи, пинговать, принимать решения о доступности узлов и т.д. В монолите, где транзакция может отработать в рамках одной сессии - смысл этого оверхеда не очень ясен. Всё равно остаток лочится и для короткой транзакции списания он по-прежнему недоступен. Как, собственно, и должно быть. Ну так и проще тогда делать транзакции serializable или read committed стнадартными средствами СУБД и не заморачиваться. Ещё может кейс для Саги, если в монолите нужно атомарно что-то выполнить из разных сессий, взятых скажем, из пула сединений веб-сервера, но пример, зачем так делать, на вскидку сложно придумать...
Вы забыли упомянуть, что:
1 нужно решать вопрос консистентности, пока финалтная маленькая транзакция не закомичена, система находится в неконсистентном состоянии, и нужно уметь с зтим жить.
2 процесс отката маленьких транзакций иакде может обломаться, это собственно коррелирует с первыми вопросом. И с жтим также нужно уметь жить.
0:00 В чем "пессимистичность" алгоритма двухфазного коммита (2PC) и почему это плохо в микросервисах
1:25 Паттерн Saga, определение и какую проблему он решает
4:10 Как обеспечить атомарность цепочки отдельных транзакций (Саги)
5:52 "Оптимистичность" саг
ССЫЛКА НА КУРС:
it-es-course.getcourse.ru/y/3b92c9c
Автор курса: Андрей Суховицкий
Действующий разработчик ПО, работает над проектированием и разработкой высоконагруженных систем.
Последние 4 года создаю и провожу авторские курсы по микросервисной архитектуре, проектированию производительных систем и проектированию ПО в университете ИТМО и МФТИ.
В 2021 году получил награду как лучший преподаватель ИТМО.
а если компенсационного механизма в принципе не может быть?
Проблема в том ещё что не все представляют что есть лог транзакций
А Сага - это и есть попытка реализовать лог транзакций, только узко заточенный
Ну, у лога транзакций много разных предназначений. Он может использоваться для восстановления состояния хранилища, для репликации.
Сага - узкоспециализированный паттерн, который помогает реализовать распределенную транзакцию, объединяющую множество неоднородных хранилищ, и при этом сохраняющую свойства атомарности, долговечности и в различной мере консистентности и изолированности.
@@sukhoa по ACID тут вопросы. Транзакции - они обычно длинные не потому, что разработчик не догадался сделать их короткими, а потому что этого требует бизнес-логика. Если в длинной транзакции на счёт с 0-м остатком начисляется 100$ и должно сразу начислится 20%, как бонус за пополнение, то выполнится это должно атомарно, даже если будет длинно. Теперь представим, что параллельная короткая транзакция пытается списать 70$ с того же счёта за покупку чего-то. Без саг она, как вариант, прочтёт 0-й остаток и скажет, что недостаточно средств. Это правильно. Теперь вариант с патерном саги, делим долгую транзакцию: комитим 100$ ( -100 компенсационная ), но тут встревает эта короткая и списывает 70$. И на что же мы будем начислять %? На 30$ вместо 100? А если у разбитой транзакции откат, от какого остатка произойдет компенсация?
Да, дело тут не столько в атомарности, сколько в изолированности. Давайте рассмотрим несколько вариантов.
1. Конечно, сумма процента должна вычисляться не от текущего состояния счета, а от суммы начисления. Эта информация будет передаваться в сообщениях (событиях). Поэтому 20% всегда начислятся верно
2. Для организации изоляции в сагах могут использоваться целый ряд так называемых "контр-мер", каждая из которых помогает избавиться от определенных аномалий изоляции (dirty read, non-repeatable read, read uncommitted). В данном случае, вы можете сделать так, что параллельные саги не увидят, что сумма на счету более 0 до тех пор, пока не будет внесен и необходимый процент-бонус. То есть сделать эти 100$ "невидимыми", избавиться от аномалии read-uncommitted.
3. Есть очень много вариантов, я очень подробно разбираю похожую сагу в курсе. Еще вы всегда можете прочитать про контр-меры в этой научной статье "Semantic ACID Properties in Multidatabases Using RPC and Update Propagations. Lars Frank and Torben U. Zahle"
@@sukhoa да, спасибо. Похоже всё-таки, что патерн в первую очередь для распределённых систем, где у каждого микросервиса м. б. своя БД, свои шарды, но все они должны отработать последовательно, как единое целое. Там да - Сага будет делать ретраи, пинговать, принимать решения о доступности узлов и т.д. В монолите, где транзакция может отработать в рамках одной сессии - смысл этого оверхеда не очень ясен. Всё равно остаток лочится и для короткой транзакции списания он по-прежнему недоступен. Как, собственно, и должно быть. Ну так и проще тогда делать транзакции serializable или read committed стнадартными средствами СУБД и не заморачиваться. Ещё может кейс для Саги, если в монолите нужно атомарно что-то выполнить из разных сессий, взятых скажем, из пула сединений веб-сервера, но пример, зачем так делать, на вскидку сложно придумать...
@@test_bot5541ну так и задумано, жертвуем консистентностью в пользу скорости