sqlpostgresqldatabase-lockingread-committed

Does SELECT prevent returned rows from getting deleted?


Say I have:

  1. T1: SELECT id FROM x WHERE timestamp < y (returns id = [1, 2, 3])
  2. T2: DELETE FROM x WHERE id = 1
  3. T1: SELECT timestamp, value FROM x WHERE id = 1

with READ-COMMITTED isolation.

Does step 3 run the risk of returning an empty result, or does step 1 acquire some sort of lock/snapshot that prevents step 2 from altering the result? (I assume REPEATABLE-READ will do what I want, but this question is about READ-COMMITTED).

I am using postgresql, but I am interested in a DB-independent answer. For example, if some databases block the delete while others do not, I'd like to know that. Thank you.


Solution

  • The PostgreSQL case:

    In PostgreSQL, reading a row doesn't acquire a lock that prevents the row from being deleted concurrently:

    The general case:

    Database system have different ways to provide transaction isolation, and the behavior will vary depending on the method used.

    A solution:

    If you are looking for a solution to make the behavior deterministic on all database systems, you can either use a higher isolation level, or you can use pessimistic locking by specifying FOR UPDATE in the SELECT statement in step 1. Then step 2 will always block.