Поделитесь ссылкой на доку.
Путём проверки на deadlocks каждым процессом, если он ждёт lock более deadlock_timeout, и (почти всегда, кроме случая, когда один из участников — autovacuum, тогда "застрелят" его) "самоубийства" процесса, если он обнаруживает deadlock. Обратите внимание, что никаких приоритетов и т.п. нет (т.е. реализация "теоретически" дефектна — случай PostgreSQL выделен на слайде) , поэтому в принципе можно попасть в ситуацию starvation (к счастью, на практике это бывает крайне редко, например: https://murcode.ru/forum/7-postgresql/1224988-deadlock-priority/ ).
Т.е. оба в откат, или первый коммит, второй назад? Выбрать стратегию можно?
Только один процесс откатывается, разумеется. Стратегию выбрать нельзя, см. выше.
Понял, в оракле можно выбирать
я так понял ,кто первый попался, того и прибивают. мс сиквел старается откатить более легкую, по его мнению, не всегда правильному, транзакцию,
Однако! Это ещё хуже, мне кажется. Откат обеих более правильный вариант, имхо, тк приоритеты равные у сессий.
Кто первый проверил на deadlock, тот и сам "умрёт". Т.е. для этого нет отдельного процесса deadlock detector, каждый backend проверяет сам, если попадает в эту ситуацию (когда ему пришлось ждать получения блокировки на протяжении deadlock_timeout). Потому, в т.ч. "the check for deadlock is relatively expensive", и проверки такие редкие: "The default is one second (1s), which is probably about the smallest value you would want in practice."
ну я это и имел в виду.
Зачем откатывать обе сессии?! Во-первых, такое поведение "убивает" ту транзакцию, у которой были все шансы завершиться. Во-вторых, оно практически гарантирует starvation (потому что при повторении тех же транзакций та же ситуация с большой вероятностью повторится снова... и снова).
потому что завершение этой транзакции приведет к нежелательному виду "конкурентного ресурса" у убитой транзакции. в общем это холивар, примем как данность, что вторая умирает и всё тут.
> приведет к нежелательному виду "конкурентного ресурса" у убитой транзакции Что Вы имели в виду? У убитой транзакции никаких ресурсов уже нет (потому что её не существует), если что. > в общем это холивар Это не "холивар", а классическая теория (родом из 1980-х, а то и раньше), "принимать как данность" там ничего не нужно — там всё давно разработано и доказано (знай себе аккуратно сдирай реализацию с учебников). > вторая умирает и всё тут. И это, как раз, "содрано" с "классики". ;)
пример: сидят две тёти и правят справочник - 1я хотела поменять название на А, 2я на Б. В итоге будет А. 2й убитой хотелось Б, но ей не дали (она обиделась). Если бы все было однозначно, то стратегии не выдумали. Такое поведение не всегда нужно, иногда надо отменять обе, тк возникла спорная ситуация. Вообще конечно нужно просто лочить селекты c for update и отстреливать на эксепшене, чтобы не давать таким ситуациям возникать.
> 2й убитой хотелось Б, но ей не дали (она обиделась). Она повторит, как обычно (и далее будет так, как предусмотрел программист). > Если бы все было однозначно, то стратегии не выдумали. "Стратегии" выдумали для того, чтобы не попадать в ситуации, когда "эта музыка будет вечной", понимаете (опять-таки, см. слайд и пример того, как это бывает в жизни (по ссылке))? > иногда надо отменять обе, тк возникла спорная ситуация. Не надо. И вообще... а Вы можете показать хоть одну СУБД, которая отменяет обе транзакции при deadlock?
А зачем откатывать обе, не пойму? зачем тратить ресурс на откат обеих транзакций, когда можно оду все-таки нормально зафиксировать?
Откуда я знаю? Это надо у @amino256 спросить. Что я знаю, так это то, что в теории concurrency control такого варианта ("стратегии") не существует, и ни одной СУБД, которая ведёт себя подобным образом, я лично не знаю.
Это был риторический вопрос...
да, действительно из коробки такого варианта нет, но в приложении так делали через перехват ошибки, была необходимость в убийстве обеих
закрываем период в той же 1С, транзакция около часа... на 59 минуте возникла взаимоблокировка с короткой транзакцией, откатываем обе, и теряем 2 часа времени? Смысл?
Ну это да, "допрограммироваться" можно до совсем уж странных "необходимостей" (например, нам вот как-то пришлось преднамеренно провоцировать (!) deadlocks c целью получения корректных данных (т.е. либо транзакция сразу попадает в deadlock→откатывается→повторяется, либо получает нужные данные), а всё оттого, что кто-то там ранее "допрограммировался" с управлением транзакциями "вручную" — и другого варианта мы не нашли).
на длинных в DWH спору нет, такие кейсы в OLTP больше, когда спор на милисекунды и потеря обеих особо не портит ничего, ждать нельзя, и нужно целостность сохранить
перефразируя один фильм: "откат обоих транзакций — это как любовь в резинке: движенье есть, прогресса нет".
Обсуждают сегодня