PostgreSQL
 sql >> Database >  >> RDS >> PostgreSQL

Blocca per SELECT in modo che un altro processo non ottenga vecchi dati

La tua domanda, facendo riferimento a una fonte sconosciuta:

Ho esaminato il blocco delle righe, ma dice che non puoi impedire selectstatements che suona come se non funzionerà per le mie condizioni qui. È la mia unica opzione per utilizzare i blocchi di avviso?

La documentazione ufficiale in merito:

I blocchi a livello di riga non influiscono sull'esecuzione di query sui dati; bloccano solo scrittori e armadietti alla stessa riga.

I tentativi simultanei non si limiteranno a selezionare, ma tenteranno di eliminare lo stesso blocco a livello di riga con SELECT ... FOR UPDATE - che fa sì che qualsiasi transazione precedente con un blocco sulla stessa riga attenda per eseguire il commit o il rollback. Proprio quello che volevi.

Tuttavia , molti casi d'uso possono essere risolti meglio con blocchi di avviso - nelle versioni precedenti alla 9.5. Puoi ancora bloccare le righe in elaborazione con FOR UPDATE inoltre per sicurezza. Ma se la transazione successiva vuole solo elaborare "la prossima riga libera", spesso è molto più efficiente non aspettare la stessa riga, che quasi sicuramente non è disponibile dopo il rilascio del blocco, ma passare immediatamente al "successivo libero".

In Postgres 9.5+ considera FOR UPDATE SKIP LOCKED per questo. Come ha commentato @Craig, questo può in gran parte sostituire i blocchi di avviso.

Domanda correlata che inciampa sullo stesso maiale delle prestazioni:

  • Funzione che impiega un'eternità per essere eseguita per un numero elevato di record

Spiegazione ed esempio di codice per i blocchi di avviso o FOR UPDATE SKIP LOCKED in Postgres 9.5+:

  • AGGIORNAMENTO Postgres... LIMITE 1

Per bloccare più righe contemporaneamente :

  • Come contrassegnare un certo numero di righe nella tabella in caso di accesso simultaneo