Tanto el nivel de aislamiento Repeatable Read como el Serializable pueden producir errores diseñados para
evitar anomalías de serialización. Como se indicó anteriormente, las aplicaciones que utilicen estos niveles
deben estar preparadas para reintentar las transacciones que fallen debido a errores de serialización. El texto
del mensaje de dicho error variará según las circunstancias precisas, pero siempre tendrá el código SQLSTATE
40001 (serialization_failure).
También puede ser aconsejable reintentar los fallos por callejón sin salida (deadlock).
Estos tienen el código SQLSTATE 40P01 (deadlock_detected).
En algunos casos también es apropiado reintentar los fallos de clave única, que tienen el código SQLSTATE
23505 (unique_violation), y los fallos de restricción de exclusión,
que tienen el código SQLSTATE 23P01 (exclusion_violation).
Por ejemplo, si la aplicación selecciona un nuevo valor para una columna de clave primaria tras inspeccionar las
claves almacenadas actualmente, podría obtener un fallo de clave única porque otra instancia de la aplicación
seleccionó la misma clave nueva simultáneamente. Esto es efectivamente un fallo de serialización, pero el
servidor no lo detectará como tal porque no puede “ver” la conexión entre el valor insertado y las
lecturas anteriores. También hay algunos casos límite en los que el servidor emitirá un error de clave única o de
restricción de exclusión a pesar de que, en principio, dispone de información suficiente para determinar que
un problema de serialización es la causa subyacente. Aunque se recomienda reintentar los errores de tipo
serialization_failure de forma incondicional, se necesita más cuidado al reintentar estos
otros códigos de error, ya que podrían representar condiciones de error persistentes en lugar de fallos transitorios.
Es importante reintentar la transacción completa, incluyendo toda la lógica que decide qué SQL emitir y/o qué valores utilizar. Por lo tanto, PostgreSQL no ofrece una facilidad de reintento automático, ya que no puede hacerlo con ninguna garantía de corrección.
El reintento de la transacción no garantiza que la transacción reintentada se complete; pueden ser necesarios múltiples reintentos. En casos con una contención muy alta, es posible que la finalización de una transacción requiera muchos intentos. En casos que impliquen una transacción preparada en conflicto, puede no ser posible avanzar hasta que la transacción preparada se comprometa o se revierta.