сериализация транзакций libpqxx и последствия

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

Я сказал, что две конкурирующие транзакции таким образом приведут к тому, что первая заблокирует вторую, а вторая может завершиться или не завершиться после первой.

Разместите документы, подтверждающие это. Кроме того, что именно происходит со второй транзакцией, если первая блокируется? Будет ли он поставлен в очередь, сбой или какая-то комбинация?

Если это невозможно подтвердить, следует ли установить для этой транзакции уровень изоляции SERIALIZABLE? Если да, то как это можно сделать с помощью подготовленных операторов libpqxx?

Если транзакции сериализуются, будет ли вторая транзакция терпеть неудачу или будет поставлена ​​в очередь до завершения первой?

Если какой-либо из них не работает, как это можно обнаружить с помощью libpqxx?


person Community    schedule 13.04.2014    source источник
comment
Каково ваше определение вмешательства?   -  person jjanes    schedule 14.04.2014
comment
Каков характер письма? Вставить новые записи? Обновить существующие записи? Удалить записи? Обновить, вставить, если не существует (т.е. обновить)?   -  person Craig Ringer    schedule 15.04.2014


Ответы (1)


Единственный способ окончательно предотвратить эффекты параллелизма — это LOCK TABLE ... IN ACCESS EXCLUSIVE MODE каждую таблицу, которую вы хотите изменить.

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

Поэтому обычно вам нужно выяснить, какие именно операции вы хотите выполнить и как они взаимодействуют. Определите, какие эффекты параллелизма вы можете допустить, и как предотвратить те, которые вы не можете.

Этот вопрос в его нынешнем виде слишком широк, чтобы на него можно было дать полезный ответ.

Варианты включают:

  • Исключительно блокировки таблиц. (Это единственный способ сделать многострочную upsert без проблем параллелизма в PostgreSQL прямо сейчас). Остерегайтесь взаимоблокировок, связанных с обновлением блокировки и порядком блокировки.

  • надлежащее использование изоляции SERIALIZABLE, но помните, что вы должны иметь возможность вести учет того, что вы делали во время транзакции, и повторять ее, если tx прерывается.

  • Тщательная блокировка на уровне строк — SELECT ... FOR UPDATE, SELECT ... FOR SHARE.

  • «Оптимистическая блокировка» / оптимистичный контроль параллелизма, где это уместно

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

person Craig Ringer    schedule 15.04.2014
comment
Я не могу четко понять, что вы имеете в виду под вмешательством, поэтому трудно точно сказать, о чем все это. Вам нужно быть немного более конкретным. Судя по вашему описанию в комментариях, я бы сказал, что это случай Вы делаете это неправильно™, т.е. если я не использую последовательности, могут произойти эти плохие вещи, что мне делать? . Использовать последовательности. - person Craig Ringer; 15.04.2014
comment
Поскольку я не могу догадаться, что именно вы имеете в виду, я не могу окончательно сказать, совпадает ли ваша интерпретация того, что говорит Даниэль, с моей, и прав ли он. Даниэль знает свое дело и редко ошибается, но вся дискуссия настолько запутана, что трудно сказать, что она имеет в виду. Послушайте, вы просите конкретный ответ на широкий, общий вопрос. Это не так работает. Дайте мне конкретную проблему, я дам вам конкретный ответ. Ваше описание рабочей нагрузки, которую вы ожидаете, не является конкретным. - person Craig Ringer; 15.04.2014