Locks are not taken when the statement starts, but when the row is found. Since you are using pg_sleep(5)
in the WHERE
condition, it take five seconds before the row is found and PostgreSQL attempts to lock it. By that time your second statement has locked the row, so the first statement has to wait until the transaction that runs the second statement finishes. Also, don't forget that pg_sleep(5)
will be executed for every row, so the first statement can take considerably longer than 5 seconds.