172 похожих чатов

Подскажите пожалуйста почему одна из сериализационных транзакций не фейлит: Первая транзакция: SELECT

* FROM users WHERE email = ’test@test.com’
(тут пауза 5 сек)
INSERT INTO users (email) VALUES ('test@test.com')

Вторая транзакция:
INSERT INTO users (email) VALUES ('test@test.com')

Первая транзакция запускается сразу. Вторая в промежутке между запросами в первой транзакции

По идее результат второй транзакции, влияет на то, что возвращает первый запрос в первой транзакции. Но фейла не происходит.

Почему так?

Если во вторую транзакцию добавить select (такой же как у первой), то фейл происходит.

30 ответов

27 просмотров

Как уровень изоляцыи выставляете?

Alexander
serializable

Я спросил -- как.

Alexander- Автор вопроса

Фигня, впрочем. Действительно, почему должна. Добавились две строчки, сначала из первой транзакцыи, затем из второй. Отличная сериализацыя.

Alexander- Автор вопроса
Ilya Anfimov
Фигня, впрочем. Действительно, почему должна. Доба...

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

Alexander
Ну пока выполянется первая транзакция, и приходит ...

Так вторая выполняется после первой. Ну, в рамках сериализацыи.

Alexander- Автор вопроса
Ilya Anfimov
Так вторая выполняется после первой. Ну, в рамках ...

А почему добавления select заставляет фейлить?

Alexander
А почему добавления select заставляет фейлить?

Потому, что после этого ужэ не скажэшь что "вторая выполнилась после первой". Если бы это было так -- во втором селекте был бы этот результат, а его нет.

Alexander- Автор вопроса
Ilya Anfimov
Так вторая выполняется после первой. Ну, в рамках ...

Я вот тут не понимаю. У меня вторая транзакции накладывается на первую и влияет на то как бы отработала первая

Alexander
Я вот тут не понимаю. У меня вторая транзакции нак...

Вторая транзакцыя не влияет на первую потому, что считается, что она отработала после первой.

Alexander- Автор вопроса
Ilya Anfimov
Вторая транзакцыя не влияет на первую потому, что ...

Так а почему тогда я добавляю select фэйл происходит, если вторая считается отработавшей после первой?

Alexander
Так а почему тогда я добавляю select фэйл происход...

Потому, что она не получила результатов первой транзакцыи. А если бы отработала после -- то должна была получить.

Alexander- Автор вопроса
Ilya Anfimov
Потому, что она не получила результатов первой тра...

Тогда в такой ситуации должно зафейлить? Но не фейлит Первая транзакция: BEGIN SET TRANSACTION ISOLATION LEVEL SERIALIZABLE INSERT INTO users (email) VALUES ('test@test.com') — в этот момент запускается вторая — COMMIT Вторая транзакция: BEGIN SET TRANSACTION ISOLATION LEVEL SERIALIZABLE SELECT * FROM users WHERE email = 'test@test.com’ COMMIT

Alexander- Автор вопроса
Alexander
Тогда в такой ситуации должно зафейлить? Но не фей...

Пробовал делать коммит второй до заврешения первой и после завершения. Не фейлит

Alexander
Тогда в такой ситуации должно зафейлить? Но не фей...

Нет, почему бы? Вторая считается отработала до первой, всё в порядке.

Alexander- Автор вопроса
Ilya Anfimov
Нет, почему бы? Вторая считается отработала до пер...

А если коммит делать после коммита первой?

Alexander- Автор вопроса
Ilya Anfimov
Да без разницы в данном случае.

Почему? Не понимаю механизм

Alexander- Автор вопроса
Ilya Anfimov
Почему что?

Почему без разницы?

Alexander
Почему без разницы?

Потому, что это сработает.

Alexander- Автор вопроса
Alexander
Почему?

Почему что?

> По идее результат второй транзакции, влияет на то, что возвращает первый запрос в первой транзакции. > Но фейла не происходит. > Почему так? Потому что всё это не имеет отношения к фундаментальному принципу / требованию serializable, вот и всё. В PostgreSQL apparent transaction order может не совпадать ни с последовательностью запуска транзакций, ни с последовательностью их завершения. И уж тем более он не обязан иметь хоть какое-то отношение к реальному времени.

Yaroslav Schekin
> По идее результат второй транзакции, влияет на т...

>apparent transaction order может не совпадать ни с последовательностью запуска транзакций, ни с последовательностью их завершения. Интересно, кстати, а то, что он будет совпадать с календарным если время старта и завершэния полностью разделено (т.е. вторая началась после того, как завершылась первая) -- разработчики как-то пытаются гарнтировать -- или это просто пока вот так получается что совпадает из-за особенностей реализацыи?

Ilya Anfimov
>apparent transaction order может не совпадать ни ...

Это, вполне возможно, вопрос определения. Первая попавшаяся ссылка: https://aphyr.com/posts/313-strong-consistency-models "In a serializable database, a transaction like read x is always allowed to execute at time 0, when x had not yet been initialized. Or it might be delayed infinitely far into the future! The transaction write 2 to x could execute right now, or it could be delayed until the end of time, never appearing to occur." ну и т.д., там есть примеры. В ISO SQL требования совпадения порядка в случае "вторая началась после того, как завершылась первая" тоже нет, насколько я помню. Но "обычные" (не распределённые) СУБД этот принцип всегда соблюдают, насколько я знаю.

В примере, как у Вас, если вначале выполнится первая тразакция, а потом вторая, то результат будет такой же, как при конкурентном выполнении, описанном Вами. Другими словами в данном случае можно придумать сериализованный порядок, при котором результат будет совпадать с Вашим результатом. Если добавить select во второй транзакции, то уже не получится подобрать последовательный запуск транзакции, при котором результат будет такой же, как у Вас. Проверьте сами, это просто.

>Другими словами в данном случае можно придумать сериализованный порядок Кстати, что-то подумал поутру -- возможно у вас тупик по поводу того, как postgresql это делает. Возможно, если бы я не знал как -- тожэ был бы в шоке, что за квантовая запутанность. На самом деле да, он запоминает критэрии поиска. И если потом какое-то обновление начинает обновлять что-то, подходящее под эти критэрии -- то начинает откатывать, какую откатывать -- выбирает по обстоятельствам. Это кроме правила создания снапшота для repeatable read -- что видны только данные (и все данные), у которых номер транзакцыи их записавшэй меньшэ либо равен текущей.

Aleksey Stavrov
В примере, как у Вас, если вначале выполнится перв...

> Другими словами в данном случае можно придумать сериализованный порядок, Я бы дажэ сказал, не "можно", а "получилось". В соответствии с упрощёнными правилами "придумывания", которые реализованы в postgres и для которых когда-то кто-то доказал (в достаточной степени) их корректность.

Похожие вопросы

Обсуждают сегодня

Господа, а что сейчас вообще с рынком труда на делфи происходит? Какова ситуация?
Rꙮman Yankꙮvsky
29
А вообще, что может смущать в самой Julia - бы сказал, что нет единого стандартного подхода по многим моментам, поэтому многое выглядит как "хаки" и произвол. Короче говоря, с...
Viktor G.
2
30500 за редактор? )
Владимир
47
а через ESC-код ?
Alexey Kulakov
29
Чёт не понял, я ж правильной функцией воспользовался чтобы вывести отладочную информацию? но что-то она не ловится
notme
18
У меня есть функция где происходит это: write_bit(buffer, 1); write_bit(buffer, 0); write_bit(buffer, 1); write_bit(buffer, 1); write_bit(buffer, 1); w...
~
14
Добрый день! Скажите пожалуйста, а какие программы вы бы рекомендовали написать для того, чтобы научиться управлять памятью? Можно написать динамический массив, можно связный ...
Филипп
7
Недавно Google Project Zero нашёл багу в SQLite с помощью LLM, о чём достаточно было шумно в определённых интернетах, которые сопровождались рассказами, что скоро всех "ибешни...
Alex Sherbakov
5
Ребят в СИ можно реализовать ООП?
Николай
33
https://github.com/erlang/otp/blob/OTP-27.1/lib/kernel/src/logger_h_common.erl#L174 https://github.com/erlang/otp/blob/OTP-27.1/lib/kernel/src/logger_olp.erl#L76 15 лет назад...
Maksim Lapshin
20
Карта сайта