select for update in the postgresql job delete trigger

we think this will avoid a deadlock condition where an insert takes the
ShareRowExclusiveLock at the wrong moment and deadlocks us inside the
trigger.

test plan: not consistently reproducable without major postgresql
instrumentation. ensure that jobs with a strand function as normal
(running the specs is a good sanity check)

Change-Id: Ib8c8ba972fd3c51ff116776213c936b9d7a48785
Reviewed-on: https://gerrit.instructure.com/10663
Reviewed-by: Zach Wily <zach@instructure.com>
Tested-by: Jenkins <jenkins@instructure.com>
This commit is contained in:
Brian Palmer 2012-05-10 09:16:38 -06:00
parent b3bd68d894
commit 840de40085
1 changed files with 2 additions and 2 deletions

View File

@ -1,4 +1,4 @@
class DelayedJobsDeleteTriggerRevertLock < ActiveRecord::Migration class DelayedJobsDeleteTriggerLockForUpdate < ActiveRecord::Migration
tag :predeploy tag :predeploy
def self.connection def self.connection
@ -10,7 +10,7 @@ class DelayedJobsDeleteTriggerRevertLock < ActiveRecord::Migration
execute(<<-CODE) execute(<<-CODE)
CREATE OR REPLACE FUNCTION delayed_jobs_after_delete_row_tr_fn () RETURNS trigger AS $$ CREATE OR REPLACE FUNCTION delayed_jobs_after_delete_row_tr_fn () RETURNS trigger AS $$
BEGIN BEGIN
UPDATE delayed_jobs SET next_in_strand = 't' WHERE id = (SELECT id FROM delayed_jobs j2 WHERE j2.strand = OLD.strand ORDER BY j2.strand, j2.id ASC LIMIT 1); UPDATE delayed_jobs SET next_in_strand = 't' WHERE id = (SELECT id FROM delayed_jobs j2 WHERE j2.strand = OLD.strand ORDER BY j2.strand, j2.id ASC LIMIT 1 FOR UPDATE);
RETURN OLD; RETURN OLD;
END; END;
$$ LANGUAGE plpgsql; $$ LANGUAGE plpgsql;