Распределённые данные · проверено по источникам

Аномалия сериализации

Аномалия сериализации — совместный результат зафиксированных параллельных транзакций, который невозможен ни при одном последовательном порядке тех же транзакций. Каждая операция по отдельности при этом может выглядеть правильной.

Также ищут: Serialization anomaly · non-serializable outcome

Практический смысл

Почему это важно

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

Доказательная часть

Что подтверждено

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

    Граница применимости: Определение аномалии сериализации в модели изоляции SQL.

  2. PostgreSQL Serializable может отклонить транзакцию, чтобы не допустить несериализуемого результата. После ошибки сериализации приложение должно быть готово начать транзакцию заново и повторить всю её логику, включая чтения и выбор значений для записи.

    Граница применимости: PostgreSQL 18, обработка ошибки сериализации; это не правило автоматического повтора любой ошибки.

  3. На складе одна единица, резервов нет. Две транзакции по своим снимкам видят ноль резервов и каждая вставляет отдельный резерв на одну единицу. Вместе они резервируют две. При последовательном выполнении вторая увидела бы первый резерв и отказала. Это аномалия сериализации без записи в одну общую строку.

    Граница применимости: Учебный пример отклонения записи по общему условию: разные ключи резервов, нет ограничения или блокировки, отдельно защищающих их сумму; каждая транзакция проверяет свободный остаток перед вставкой.

  4. Для аномалии сериализации не требуется грязное чтение. Транзакции могут опираться только на ранее зафиксированные строки, но принять несовместимые решения, потому что не видят будущих изменений друг друга.

    Граница применимости: Параллельные транзакции с зависимостью решения о записи от прочитанного состояния.

  5. PostgreSQL Repeatable Read сохраняет снимок и исключает неповторяемое и фантомное чтение, однако не гарантирует сериализуемость. Пример с двумя резервами требует проверки совместного правила, а не только повторного чтения тех же строк.

    Граница применимости: PostgreSQL 18; более сильные гарантии другого продукта из названия Repeatable Read не выводятся.

  6. Повтор после ошибки сериализации включает расчёт условий операции заново. В примере с последней единицей новый снимок может показать уже созданный резерв; тогда правильный итог повтора — отказ во втором резерве, а не вставка с прежним решением.

    Граница применимости: Учебный пример повторного выполнения всей транзакции в PostgreSQL Serializable; первый резерв уже зафиксирован и не снят.

  7. Ошибка сериализации и зафиксированная аномалия — разные события. Отклонённая транзакция может быть результатом работы защиты. Само наличие таких ошибок не доказывает, что база сохранила несовместимые изменения.

    Граница применимости: Диагностика PostgreSQL Serializable; ошибки нужно сопоставлять с результатами COMMIT и поведением повторов.

  8. Кредитный предел покупателя — 100, сумма принятых заказов — 0. Две транзакции по своим снимкам проверяют заказ на 70 и вставляют разные строки. Вместе получается 140. При последовательной работе вторая проверка увидела бы сумму 70 и отклонила новый заказ. Repeatable Read сам не исключает такой результат.

    Граница применимости: Учебные числа; PostgreSQL 18 Repeatable Read, оба снимка получены до фиксации новых заказов, разные ключи строк, нет отдельного ограничения или блокировки общей суммы; каждая транзакция проверяет сумму с учётом своего нового заказа.

Граница терминов

Не путать

Сериализуемость

Сериализуемость — требование к совместному результату, а аномалия сериализации — его нарушение. Многоверсионный снимок помогает организовать чтение, но сам этого требования не обеспечивает.

Фантомное чтение

Фантом меняет результат повторного запроса. При аномалии сериализации каждый снимок может оставаться неизменным, а несовместимость проявляется в сумме зафиксированных изменений.

Перед спецификацией

Что проверить

  1. Сформулируйте общее правило числом или условием: например, сумма резервов не больше остатка.
  2. Запишите чтения, решения и изменения каждой из двух параллельных транзакций.
  3. Сравните совместный итог с обоими последовательными порядками этих транзакций.
  4. Испытайте запись в разные строки: отсутствие конфликта одной строки ещё ничего не доказывает.
  5. Проверьте фактический уровень изоляции всех участников операции.
  6. После ошибки сериализации повторяйте чтения и расчёт решения, а не только последнюю запись.
  7. В журнале приложения различайте отклонённую попытку, успешный повтор и сохранённое нарушение правила.
Открытые основания

Первоисточники

  • Официальная документация

    PostgreSQL 18 Documentation: Transaction Isolation

    PostgreSQL Global Development Group · PostgreSQL 18, Chapter 13.2

    Определяет isolation phenomena и фактическое поведение PostgreSQL levels, включая Serializable.

    Открыть первоисточник
  • Официальная документация

    PostgreSQL 18 Documentation: Introduction to MVCC

    PostgreSQL Global Development Group · PostgreSQL 18, Chapter 13.1

    Объясняет multiversion snapshots и границу между MVCC и explicit locking.

    Открыть первоисточник
Сообщить об ошибке

Опишите проблему — постараемся исправить как можно скорее.

Спасибо!

Получили ваше сообщение.
Подтвердите действие