roqua-support 0.1.25 → 0.1.26

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c59df394193f13d45c71f26b935f59e890b98f96
4
- data.tar.gz: b0f6dc5880a4dfda1d96f554d5460dd180e6fc3b
3
+ metadata.gz: ecfd7d74378220979e7a8839f07ea9793a37265c
4
+ data.tar.gz: 8dfb4a419c0d3bc0222a2f743fcad30fc0e43141
5
5
  SHA512:
6
- metadata.gz: 0ccdada5a2cff7e753ae5e8d0278473a70d4e39b7c0f85f1287811946850f73612ade4bed1d5a081290cc6edde938a4190a32969cad62913e5e401e178a57f68
7
- data.tar.gz: 29ea857840bd5f40b59efd2b94eb599909cec72d2e9b58dcd16e71a210935ca9dd6344ad2dee79fda8772257db4edfa2276e9cd57745618d35c143b823474935
6
+ metadata.gz: d69f343ba3c51be195a532a892d8839eea4bea7cea5ee54f23e790f6fb56c2299c3aa1f94de49a1cad22f342c0feb78d5878d3a0bffed9be143d719224b7497f
7
+ data.tar.gz: 76a3f96b867e176bf948ea7bab491c1abd319b7eb02faf8dbb1f0aed73eb9c7251cef075ee5f51fca81b6383c35f1c05408aded3fda050bd339e77ddab60a668
data/.gitlab-ci.yml CHANGED
@@ -3,10 +3,6 @@ image: "registry.roqua.nl/roqua/roqua-build-images:ruby-2.3-rails-base-test"
3
3
  variables:
4
4
  RAILS_ENV: "test"
5
5
 
6
- stages:
7
- - test
8
- - publish
9
-
10
6
  cache:
11
7
  paths:
12
8
  - .gems
@@ -18,26 +14,13 @@ before_script:
18
14
  - bundle --jobs 2 --retry 3
19
15
 
20
16
  rails_41:
21
- stage: test
22
17
  script:
23
18
  - bundle exec appraisal rails41 bundle exec rspec
24
19
 
25
20
  rails_42:
26
- stage: test
27
21
  script:
28
22
  - bundle exec appraisal rails42 bundle exec rspec
29
23
 
30
24
  rails_50:
31
- stage: test
32
25
  script:
33
26
  - bundle exec appraisal rails50 bundle exec rspec
34
-
35
- build_and_publish_gem:
36
- stage: publish
37
- dependencies:
38
- - rails_41
39
- - rails_42
40
- - rails_50
41
- script:
42
- - gem build roqua-support.gemspec
43
- - gem push roqua-support-0.1.25.gem
data/Gemfile.lock CHANGED
@@ -8,7 +8,7 @@ GIT
8
8
  PATH
9
9
  remote: .
10
10
  specs:
11
- roqua-support (0.1.25)
11
+ roqua-support (0.1.26)
12
12
  active_interaction (~> 3.0)
13
13
  activesupport (>= 3.2, < 6)
14
14
  naught (~> 1.0)
@@ -33,6 +33,10 @@ GEM
33
33
  activemodel (>= 4, < 6)
34
34
  activemodel (5.0.1)
35
35
  activesupport (= 5.0.1)
36
+ activerecord (5.0.1)
37
+ activemodel (= 5.0.1)
38
+ activesupport (= 5.0.1)
39
+ arel (~> 7.0)
36
40
  activesupport (5.0.1)
37
41
  concurrent-ruby (~> 1.0, >= 1.0.2)
38
42
  i18n (~> 0.7)
@@ -44,6 +48,7 @@ GEM
44
48
  thor (>= 0.14.0)
45
49
  appsignal (2.3.1)
46
50
  rack
51
+ arel (7.1.4)
47
52
  ast (2.3.0)
48
53
  builder (3.2.3)
49
54
  coderay (1.1.1)
@@ -52,6 +57,11 @@ GEM
52
57
  railties (>= 3.0.0)
53
58
  thor (>= 0.14.6)
54
59
  concurrent-ruby (1.0.4)
60
+ delayed_job (4.1.4)
61
+ activesupport (>= 3.0, < 5.2)
62
+ delayed_job_active_record (4.1.2)
63
+ activerecord (>= 3.0, < 5.2)
64
+ delayed_job (>= 3.0, < 5)
55
65
  diff-lcs (1.3)
56
66
  erubis (2.7.0)
57
67
  ffi (1.9.17)
@@ -151,8 +161,10 @@ GEM
151
161
  ruby_dep (1.5.0)
152
162
  shellany (0.0.1)
153
163
  slop (3.6.0)
164
+ sqlite3 (1.3.13)
154
165
  thor (0.19.4)
155
166
  thread_safe (0.3.5)
167
+ timecop (0.9.1)
156
168
  tzinfo (1.2.2)
157
169
  thread_safe (~> 0.1)
158
170
  unicode-display_width (1.3.0)
@@ -167,14 +179,17 @@ DEPENDENCIES
167
179
  appsignal
168
180
  bundler (~> 1.0)
169
181
  combustion (~> 0.5.2)
182
+ delayed_job_active_record
170
183
  guard-rspec (~> 4.2.6)
171
- rake (~> 12.1)
184
+ rake
172
185
  responders
173
186
  roqua-support!
174
187
  roqua_styleguide!
175
188
  rspec (>= 2.12.0, < 4.0)
176
189
  rspec-instrumentation-matcher
177
190
  rspec-rails
191
+ sqlite3
192
+ timecop
178
193
 
179
194
  BUNDLED WITH
180
- 1.15.4
195
+ 1.16.1
data/README.md CHANGED
@@ -100,6 +100,16 @@ class ApiAreaController < ApplicationController
100
100
  ...
101
101
  ```
102
102
 
103
+ # AppSignal Probes
104
+
105
+ roqua-support contains one generic probe to monitor the current delayed job backlog count: `Roqua::Probes::DelayedJobProbe`
106
+
107
+ Enable it in a project by calling:
108
+
109
+ ```ruby
110
+ Roqua::Probes::DelayedJobProbe.enable
111
+ ```
112
+
103
113
  ### ActiveInteraction extensions
104
114
 
105
115
  ```
@@ -0,0 +1,11 @@
1
+ module Roqua
2
+ module Probes
3
+ module BaseProbe
4
+ def enable
5
+ new.tap do |probe|
6
+ Appsignal::Minutely.probes << probe unless Appsignal::Minutely.probes.map(&:class).include?(probe.class)
7
+ end
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,17 @@
1
+ require_relative 'base_probe'
2
+
3
+ module Roqua
4
+ module Probes
5
+ class DelayedJobProbe
6
+ extend BaseProbe
7
+
8
+ def backlog_count
9
+ Delayed::Job.where(locked_at: nil).where('run_at < ?', Time.zone.now).count
10
+ end
11
+
12
+ def call
13
+ Appsignal.set_gauge('delayed_job_backlog_count', backlog_count)
14
+ end
15
+ end
16
+ end
17
+ end
@@ -69,7 +69,7 @@ module Roqua
69
69
  end
70
70
 
71
71
  def notify_appsignal?(exception)
72
- const_defined?(:Appsignal) && !Appsignal.is_ignored_exception?(exception) && Appsignal.active?
72
+ const_defined?(:Appsignal) && Appsignal.active? && !Appsignal.is_ignored_exception?(exception)
73
73
  end
74
74
 
75
75
  def notify_appsignal(exception, labels, namespace)
@@ -1,5 +1,5 @@
1
1
  module Roqua
2
2
  module Support
3
- VERSION = '0.1.25'.freeze
3
+ VERSION = '0.1.26'.freeze
4
4
  end
5
5
  end
data/lib/roqua-support.rb CHANGED
@@ -2,6 +2,10 @@ require "roqua-support/version"
2
2
  require "roqua/support"
3
3
 
4
4
  module Roqua
5
+ module Probes
6
+ autoload :DelayedJobProbe, 'roqua/probes/delayed_job_probe'
7
+ end
8
+
5
9
  module Responders
6
10
  autoload :ApiErrorsResponder, 'roqua/responders/api_errors_responder'
7
11
  autoload :ActiveInteractionAwareResponder, 'roqua/responders/active_interaction_aware_responder'
@@ -23,7 +23,10 @@ Gem::Specification.new do |gem|
23
23
  gem.add_dependency 'active_interaction', '~> 3.0'
24
24
 
25
25
  gem.add_development_dependency 'bundler', '~> 1.0'
26
- gem.add_development_dependency 'rake', '~> 12.1'
26
+ gem.add_development_dependency 'rake'
27
27
  gem.add_development_dependency 'rspec', '>= 2.12.0', '< 4.0'
28
- gem.add_development_dependency 'appsignal', '~> 2.3', '>= 2.3.1'
28
+ gem.add_development_dependency 'appsignal', '>= 2.3.1'
29
+ gem.add_development_dependency 'delayed_job_active_record'
30
+ gem.add_development_dependency 'sqlite3'
31
+ gem.add_development_dependency 'timecop'
29
32
  end
@@ -1,17 +1,6 @@
1
- require 'roqua/core_ext/activerecord/uniq_find_or_create'
1
+ require 'spec_helper'
2
2
 
3
- module ActiveRecord
4
- class Base
5
- def self.find_by(attributes)
6
- end
7
- end
8
-
9
- class RecordNotUnique < StandardError
10
- end
11
-
12
- class RecordInvalid < StandardError
13
- end
14
- end
3
+ require 'roqua/core_ext/activerecord/uniq_find_or_create'
15
4
 
16
5
  describe ActiveRecord::Base do
17
6
  let(:attributes) { double('attributes') }
@@ -32,14 +21,14 @@ describe ActiveRecord::Base do
32
21
  it 'returns a concurrenlty created record' do
33
22
  allow(ActiveRecord::Base).to receive(:find_by).with(attributes).and_return record
34
23
  allow(ActiveRecord::Base).to receive(:find_or_create_by).with(attributes, &block)
35
- .and_raise ActiveRecord::RecordNotUnique
24
+ .and_raise ActiveRecord::RecordNotUnique.new('')
36
25
  expect(ActiveRecord::Base.uniq_find_or_create_by attributes, &block).to eq(record)
37
26
  end
38
27
 
39
28
  it 'raises when a concurrent record is detected by the database but could not be queried for unknown reasons' do
40
29
  allow(ActiveRecord::Base).to receive(:find_by).with(attributes).and_return nil
41
30
  allow(ActiveRecord::Base).to receive(:find_or_create_by).with(attributes, &block)
42
- .and_raise ActiveRecord::RecordNotUnique
31
+ .and_raise ActiveRecord::RecordNotUnique.new('')
43
32
  expect do
44
33
  ActiveRecord::Base.uniq_find_or_create_by attributes, &block
45
34
  end.to raise_error ActiveRecord::RecordNotUnique
@@ -66,21 +55,21 @@ describe ActiveRecord::Base do
66
55
  it 'returns a concurrenlty created record' do
67
56
  allow(ActiveRecord::Base).to receive(:find_by).with(attributes).and_return record
68
57
  allow(ActiveRecord::Base).to receive(:find_or_create_by!).with(attributes, &block)
69
- .and_raise ActiveRecord::RecordNotUnique
58
+ .and_raise ActiveRecord::RecordNotUnique.new('')
70
59
  expect(ActiveRecord::Base.uniq_find_or_create_by! attributes, &block).to eq(record)
71
60
  end
72
61
 
73
62
  it 'raises when a concurrent record is detected by the database but could not be queried for unknown reasons' do
74
63
  allow(ActiveRecord::Base).to receive(:find_by).with(attributes).and_return nil
75
64
  allow(ActiveRecord::Base).to receive(:find_or_create_by!).with(attributes, &block)
76
- .and_raise ActiveRecord::RecordNotUnique
65
+ .and_raise ActiveRecord::RecordNotUnique.new('')
77
66
  expect do
78
67
  ActiveRecord::Base.uniq_find_or_create_by! attributes, &block
79
68
  end.to raise_error ActiveRecord::RecordNotUnique
80
69
  end
81
70
 
82
71
  it 'raises when creating a new record causes validation failures not due to concurrency' do
83
- exception = ActiveRecord::RecordInvalid.new 'some_validation_error'
72
+ exception = StandardError.new('some_validation_error')
84
73
  allow(ActiveRecord::Base).to receive(:find_or_create_by!).with(attributes, &block).and_raise exception
85
74
  expect { ActiveRecord::Base.uniq_find_or_create_by! attributes, &block }.to raise_error(exception)
86
75
  end
@@ -0,0 +1,51 @@
1
+ require 'spec_helper'
2
+ require 'delayed_job_active_record'
3
+ require 'timecop'
4
+
5
+ require 'roqua/probes/delayed_job_probe'
6
+
7
+ describe Roqua::Probes::DelayedJobProbe do
8
+ before { Timecop.freeze }
9
+ after { Timecop.return }
10
+ subject(:probe) { Roqua::Probes::DelayedJobProbe.new }
11
+
12
+ describe 'backlog_count' do
13
+ context 'if a single job unlocked job exists that has a run_at in the past' do
14
+ def create_jobs
15
+ Delayed::Job.create!(run_at: 1.second.ago)
16
+ 2.times { Delayed::Job.create!(run_at: 1.second.ago, locked_at: Time.zone.now) }
17
+ Delayed::Job.create!(run_at: Time.zone.now)
18
+ Delayed::Job.create!(run_at: 1.second.from_now)
19
+ end
20
+
21
+ it 'returns 1' do
22
+ expect { create_jobs }.to change { probe.backlog_count }.from(0).to(1)
23
+ end
24
+ end
25
+ end
26
+
27
+ describe 'call' do
28
+ it 'sends the correct metric to Appsignal' do
29
+ expect(probe).to receive(:backlog_count).and_return(12)
30
+ expect(Appsignal).to receive(:set_gauge).with('delayed_job_backlog_count', 12)
31
+ probe.call
32
+ end
33
+ end
34
+
35
+ context '.enable' do
36
+ before { Appsignal::Minutely.probes.clear }
37
+ after { Appsignal::Minutely.probes.clear }
38
+
39
+ it 'adds our custom probes to Appsignal' do
40
+ expect { Roqua::Probes::DelayedJobProbe.enable }
41
+ .to change { Appsignal::Minutely.probes.count }.by(1)
42
+
43
+ expect(Appsignal::Minutely.probes.map(&:class)).to include(Roqua::Probes::DelayedJobProbe)
44
+ end
45
+
46
+ it 'will not add the same probe twice if called multiple times' do
47
+ expect { 2.times { Roqua::Probes::DelayedJobProbe.enable } }
48
+ .to change { Appsignal::Minutely.probes.count }.by(1)
49
+ end
50
+ end
51
+ end
data/spec/spec_helper.rb CHANGED
@@ -1,3 +1,5 @@
1
+ ENV['RAILS_ENV'] = 'test'
2
+
1
3
  require 'rubygems'
2
4
  require 'bundler/setup'
3
5
 
@@ -7,3 +9,29 @@ Combustion.initialize! :action_controller
7
9
 
8
10
  require 'appsignal'
9
11
  require 'rspec/rails'
12
+
13
+ require 'delayed_job_active_record'
14
+
15
+ Delayed::Worker.logger = Logger.new(Tempfile.new('roqua-support-delayed-job.log'))
16
+
17
+ ActiveRecord::Base.establish_connection :adapter => 'sqlite3', :database => ':memory:'
18
+ ActiveRecord::Base.logger = Delayed::Worker.logger
19
+ ActiveRecord::Migration.verbose = false
20
+
21
+ ActiveRecord::Schema.define do
22
+ create_table :delayed_jobs, :force => true do |t|
23
+ t.integer :priority, :default => 0
24
+ t.integer :attempts, :default => 0
25
+ t.text :handler
26
+ t.text :last_error
27
+ t.datetime :run_at
28
+ t.datetime :locked_at
29
+ t.datetime :failed_at
30
+ t.string :locked_by
31
+ t.string :queue
32
+ t.string :cron
33
+ t.timestamps null: false
34
+ end
35
+
36
+ add_index :delayed_jobs, [:priority, :run_at], :name => 'delayed_jobs_priority'
37
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: roqua-support
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.25
4
+ version: 0.1.26
5
5
  platform: ruby
6
6
  authors:
7
7
  - Marten Veldthuis
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-11-08 00:00:00.000000000 Z
11
+ date: 2018-03-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -76,16 +76,16 @@ dependencies:
76
76
  name: rake
77
77
  requirement: !ruby/object:Gem::Requirement
78
78
  requirements:
79
- - - "~>"
79
+ - - ">="
80
80
  - !ruby/object:Gem::Version
81
- version: '12.1'
81
+ version: '0'
82
82
  type: :development
83
83
  prerelease: false
84
84
  version_requirements: !ruby/object:Gem::Requirement
85
85
  requirements:
86
- - - "~>"
86
+ - - ">="
87
87
  - !ruby/object:Gem::Version
88
- version: '12.1'
88
+ version: '0'
89
89
  - !ruby/object:Gem::Dependency
90
90
  name: rspec
91
91
  requirement: !ruby/object:Gem::Requirement
@@ -110,22 +110,58 @@ dependencies:
110
110
  name: appsignal
111
111
  requirement: !ruby/object:Gem::Requirement
112
112
  requirements:
113
- - - "~>"
113
+ - - ">="
114
114
  - !ruby/object:Gem::Version
115
- version: '2.3'
115
+ version: 2.3.1
116
+ type: :development
117
+ prerelease: false
118
+ version_requirements: !ruby/object:Gem::Requirement
119
+ requirements:
116
120
  - - ">="
117
121
  - !ruby/object:Gem::Version
118
122
  version: 2.3.1
123
+ - !ruby/object:Gem::Dependency
124
+ name: delayed_job_active_record
125
+ requirement: !ruby/object:Gem::Requirement
126
+ requirements:
127
+ - - ">="
128
+ - !ruby/object:Gem::Version
129
+ version: '0'
119
130
  type: :development
120
131
  prerelease: false
121
132
  version_requirements: !ruby/object:Gem::Requirement
122
133
  requirements:
123
- - - "~>"
134
+ - - ">="
124
135
  - !ruby/object:Gem::Version
125
- version: '2.3'
136
+ version: '0'
137
+ - !ruby/object:Gem::Dependency
138
+ name: sqlite3
139
+ requirement: !ruby/object:Gem::Requirement
140
+ requirements:
126
141
  - - ">="
127
142
  - !ruby/object:Gem::Version
128
- version: 2.3.1
143
+ version: '0'
144
+ type: :development
145
+ prerelease: false
146
+ version_requirements: !ruby/object:Gem::Requirement
147
+ requirements:
148
+ - - ">="
149
+ - !ruby/object:Gem::Version
150
+ version: '0'
151
+ - !ruby/object:Gem::Dependency
152
+ name: timecop
153
+ requirement: !ruby/object:Gem::Requirement
154
+ requirements:
155
+ - - ">="
156
+ - !ruby/object:Gem::Version
157
+ version: '0'
158
+ type: :development
159
+ prerelease: false
160
+ version_requirements: !ruby/object:Gem::Requirement
161
+ requirements:
162
+ - - ">="
163
+ - !ruby/object:Gem::Version
164
+ version: '0'
129
165
  description: 'Logging backend, freedom patches, '
130
166
  email: marten@roqua.nl
131
167
  executables: []
@@ -159,6 +195,8 @@ files:
159
195
  - lib/roqua/core_ext/enumerable/sort_by_alphanum.rb
160
196
  - lib/roqua/core_ext/fabrication/singleton.rb
161
197
  - lib/roqua/core_ext/fixnum/clamp.rb
198
+ - lib/roqua/probes/base_probe.rb
199
+ - lib/roqua/probes/delayed_job_probe.rb
162
200
  - lib/roqua/responders/active_interaction_aware_responder.rb
163
201
  - lib/roqua/responders/api_errors_responder.rb
164
202
  - lib/roqua/support.rb
@@ -179,6 +217,7 @@ files:
179
217
  - spec/roqua/core_ext/enumerable/sort_by_alphanum_spec.rb
180
218
  - spec/roqua/core_ext/fabrication/singleton_spec.rb
181
219
  - spec/roqua/core_ext/fixnum/clamp_spec.rb
220
+ - spec/roqua/probes/delayed_job_probe_spec.rb
182
221
  - spec/roqua/responders/active_interaction_aware_responder_spec.rb
183
222
  - spec/roqua/responders/api_errors_responder_spec.rb
184
223
  - spec/roqua/support/errors_spec.rb
@@ -210,7 +249,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
210
249
  version: '0'
211
250
  requirements: []
212
251
  rubyforge_project:
213
- rubygems_version: 2.5.2
252
+ rubygems_version: 2.5.2.2
214
253
  signing_key:
215
254
  specification_version: 4
216
255
  summary: Helper objects and proxies used by a lot of RoQua applications
@@ -223,6 +262,7 @@ test_files:
223
262
  - spec/roqua/core_ext/enumerable/sort_by_alphanum_spec.rb
224
263
  - spec/roqua/core_ext/fabrication/singleton_spec.rb
225
264
  - spec/roqua/core_ext/fixnum/clamp_spec.rb
265
+ - spec/roqua/probes/delayed_job_probe_spec.rb
226
266
  - spec/roqua/responders/active_interaction_aware_responder_spec.rb
227
267
  - spec/roqua/responders/api_errors_responder_spec.rb
228
268
  - spec/roqua/support/errors_spec.rb