inst-jobs 3.1.16 → 3.1.17
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/delayed/backend/active_record.rb +32 -1
- data/lib/delayed/version.rb +1 -1
- metadata +13 -27
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 8b4b6a00b5e6b9ec0916e799819a8ae75aac19faa368e869772b336f860a8109
|
4
|
+
data.tar.gz: 8f6a562afbf654e5937a5dc4d2540304ead783bab594722ca5c3b5782f6fdeb6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4bbd25cfe653768aa2a755eab2c3ea45530debba4d86e12b8d5a1cfd169ddf3d59fc0fef9773a0e81b2abaeaf886e0dd7be2a208c22fc0e0323fec77205e64e7
|
7
|
+
data.tar.gz: 9a61ada6fb4f816c0dadaf159f0852d4a31d933dff50ad7dfb5e8439e0dfc09ce9c3c1baf2dc24ab79f41fa79b6ea0b4f703d4903248d436b576924c629511a6
|
@@ -47,11 +47,13 @@ module Delayed
|
|
47
47
|
|
48
48
|
def attempt_advisory_lock(lock_name)
|
49
49
|
fn_name = connection.quote_table_name("half_md5_as_bigint")
|
50
|
+
lock_name = connection.quote_string(lock_name)
|
50
51
|
connection.select_value("SELECT pg_try_advisory_xact_lock(#{fn_name}('#{lock_name}'));")
|
51
52
|
end
|
52
53
|
|
53
54
|
def advisory_lock(lock_name)
|
54
55
|
fn_name = connection.quote_table_name("half_md5_as_bigint")
|
56
|
+
lock_name = connection.quote_string(lock_name)
|
55
57
|
connection.execute("SELECT pg_advisory_xact_lock(#{fn_name}('#{lock_name}'));")
|
56
58
|
end
|
57
59
|
end
|
@@ -409,7 +411,36 @@ module Delayed
|
|
409
411
|
RETURNING #{quoted_table_name}.*
|
410
412
|
SQL
|
411
413
|
|
412
|
-
|
414
|
+
begin
|
415
|
+
jobs = find_by_sql(query)
|
416
|
+
rescue ::ActiveRecord::RecordNotUnique => e
|
417
|
+
# if we got a unique violation on a singleton, it's because next_in_strand
|
418
|
+
# somehow got set to true on the non-running job when there is a running
|
419
|
+
# job. AFAICT this is not possible from inst-jobs itself, but has happened
|
420
|
+
# in production - either due to manual manipulation of jobs, or possibly
|
421
|
+
# a process in something like switchman-inst-jobs
|
422
|
+
raise unless e.message.include?('"index_delayed_jobs_on_singleton_running"')
|
423
|
+
|
424
|
+
# just repair the "strand"
|
425
|
+
singleton = e.message.match(/Key \(singleton\)=\((.+)\) already exists.$/)[1]
|
426
|
+
raise unless singleton
|
427
|
+
|
428
|
+
transaction do
|
429
|
+
# very conservatively lock the locked job, so that it won't unlock from underneath us and
|
430
|
+
# leave an orphaned strand
|
431
|
+
advisory_lock("singleton:#{singleton}")
|
432
|
+
locked_jobs = where(singleton: singleton).where.not(locked_by: nil).lock.pluck(:id)
|
433
|
+
# if it's already gone, then we're good and should be able to just retry
|
434
|
+
if locked_jobs.length == 1
|
435
|
+
updated = where(singleton: singleton, next_in_strand: true)
|
436
|
+
.where(locked_by: nil)
|
437
|
+
.update_all(next_in_strand: false)
|
438
|
+
raise if updated.zero?
|
439
|
+
end
|
440
|
+
end
|
441
|
+
|
442
|
+
retry
|
443
|
+
end
|
413
444
|
# because this is an atomic query, we don't have to return more jobs than we needed
|
414
445
|
# to try and lock them, nor is there a possibility we need to try again because
|
415
446
|
# all of the jobs we tried to lock had already been locked by someone else
|
data/lib/delayed/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: inst-jobs
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.1.
|
4
|
+
version: 3.1.17
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Cody Cutrer
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: exe
|
12
12
|
cert_chain: []
|
13
|
-
date: 2024-04-
|
13
|
+
date: 2024-04-23 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: activerecord
|
@@ -130,20 +130,6 @@ dependencies:
|
|
130
130
|
- - ">="
|
131
131
|
- !ruby/object:Gem::Version
|
132
132
|
version: '0'
|
133
|
-
- !ruby/object:Gem::Dependency
|
134
|
-
name: byebug
|
135
|
-
requirement: !ruby/object:Gem::Requirement
|
136
|
-
requirements:
|
137
|
-
- - ">="
|
138
|
-
- !ruby/object:Gem::Version
|
139
|
-
version: '0'
|
140
|
-
type: :development
|
141
|
-
prerelease: false
|
142
|
-
version_requirements: !ruby/object:Gem::Requirement
|
143
|
-
requirements:
|
144
|
-
- - ">="
|
145
|
-
- !ruby/object:Gem::Version
|
146
|
-
version: '0'
|
147
133
|
- !ruby/object:Gem::Dependency
|
148
134
|
name: database_cleaner
|
149
135
|
requirement: !ruby/object:Gem::Requirement
|
@@ -173,35 +159,35 @@ dependencies:
|
|
173
159
|
- !ruby/object:Gem::Version
|
174
160
|
version: '2.0'
|
175
161
|
- !ruby/object:Gem::Dependency
|
176
|
-
name:
|
162
|
+
name: debug
|
177
163
|
requirement: !ruby/object:Gem::Requirement
|
178
164
|
requirements:
|
179
|
-
- - "
|
165
|
+
- - ">="
|
180
166
|
- !ruby/object:Gem::Version
|
181
|
-
version:
|
167
|
+
version: '0'
|
182
168
|
type: :development
|
183
169
|
prerelease: false
|
184
170
|
version_requirements: !ruby/object:Gem::Requirement
|
185
171
|
requirements:
|
186
|
-
- - "
|
172
|
+
- - ">="
|
187
173
|
- !ruby/object:Gem::Version
|
188
|
-
version:
|
174
|
+
version: '0'
|
189
175
|
- !ruby/object:Gem::Dependency
|
190
|
-
name:
|
176
|
+
name: diplomat
|
191
177
|
requirement: !ruby/object:Gem::Requirement
|
192
178
|
requirements:
|
193
|
-
- - "
|
179
|
+
- - "~>"
|
194
180
|
- !ruby/object:Gem::Version
|
195
|
-
version:
|
181
|
+
version: 2.6.3
|
196
182
|
type: :development
|
197
183
|
prerelease: false
|
198
184
|
version_requirements: !ruby/object:Gem::Requirement
|
199
185
|
requirements:
|
200
|
-
- - "
|
186
|
+
- - "~>"
|
201
187
|
- !ruby/object:Gem::Version
|
202
|
-
version:
|
188
|
+
version: 2.6.3
|
203
189
|
- !ruby/object:Gem::Dependency
|
204
|
-
name:
|
190
|
+
name: pg
|
205
191
|
requirement: !ruby/object:Gem::Requirement
|
206
192
|
requirements:
|
207
193
|
- - ">="
|