sidekiq 6.0.0.pre1 → 6.0.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of sidekiq might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/.gitignore +0 -2
- data/6.0-Upgrade.md +15 -3
- data/Changes.md +10 -0
- data/Ent-2.0-Upgrade.md +37 -0
- data/Ent-Changes.md +12 -0
- data/Gemfile.lock +196 -0
- data/Pro-5.0-Upgrade.md +25 -0
- data/Pro-Changes.md +12 -3
- data/README.md +16 -30
- data/bin/sidekiqload +26 -22
- data/bin/sidekiqmon +9 -0
- data/lib/generators/sidekiq/templates/worker_test.rb.erb +1 -1
- data/lib/sidekiq.rb +2 -2
- data/lib/sidekiq/api.rb +8 -8
- data/lib/sidekiq/cli.rb +12 -25
- data/lib/sidekiq/client.rb +3 -3
- data/lib/sidekiq/launcher.rb +3 -6
- data/lib/sidekiq/manager.rb +1 -1
- data/lib/sidekiq/middleware/chain.rb +1 -1
- data/lib/sidekiq/{ctl.rb → monitor.rb} +4 -3
- data/lib/sidekiq/processor.rb +11 -5
- data/lib/sidekiq/rails.rb +25 -7
- data/lib/sidekiq/redis_connection.rb +2 -2
- data/lib/sidekiq/testing.rb +1 -1
- data/lib/sidekiq/util.rb +3 -3
- data/lib/sidekiq/version.rb +1 -1
- data/lib/sidekiq/web.rb +5 -5
- data/lib/sidekiq/web/action.rb +3 -3
- data/lib/sidekiq/web/application.rb +2 -2
- data/lib/sidekiq/web/helpers.rb +1 -1
- data/lib/sidekiq/worker.rb +114 -86
- data/sidekiq.gemspec +13 -13
- data/web/assets/javascripts/dashboard.js +2 -21
- data/web/locales/ja.yml +2 -1
- metadata +17 -15
- data/.travis.yml +0 -14
- data/bin/sidekiqctl +0 -11
@@ -12,7 +12,7 @@ module Sidekiq
|
|
12
12
|
options[key.to_sym] = options.delete(key)
|
13
13
|
end
|
14
14
|
|
15
|
-
options[:id] = "Sidekiq-#{Sidekiq.server? ? "server" : "client"}-PID-#{
|
15
|
+
options[:id] = "Sidekiq-#{Sidekiq.server? ? "server" : "client"}-PID-#{::Process.pid}" unless options.key?(:id)
|
16
16
|
options[:url] ||= determine_redis_provider
|
17
17
|
|
18
18
|
size = if options[:size]
|
@@ -124,8 +124,8 @@ module Sidekiq
|
|
124
124
|
REDIS_PROVIDER should be set to the name of the variable which contains the Redis URL, not a URL itself.
|
125
125
|
Platforms like Heroku will sell addons that publish a *_URL variable. You need to tell Sidekiq with REDIS_PROVIDER, e.g.:
|
126
126
|
|
127
|
-
REDIS_PROVIDER=REDISTOGO_URL
|
128
127
|
REDISTOGO_URL=redis://somehost.example.com:6379/4
|
128
|
+
REDIS_PROVIDER=REDISTOGO_URL
|
129
129
|
EOM
|
130
130
|
end
|
131
131
|
|
data/lib/sidekiq/testing.rb
CHANGED
data/lib/sidekiq/util.rb
CHANGED
@@ -22,7 +22,7 @@ module Sidekiq
|
|
22
22
|
|
23
23
|
def safe_thread(name, &block)
|
24
24
|
Thread.new do
|
25
|
-
Thread.current
|
25
|
+
Thread.current.name = name
|
26
26
|
watchdog(name, &block)
|
27
27
|
end
|
28
28
|
end
|
@@ -44,11 +44,11 @@ module Sidekiq
|
|
44
44
|
end
|
45
45
|
|
46
46
|
def process_nonce
|
47
|
-
|
47
|
+
@@process_nonce ||= SecureRandom.hex(6)
|
48
48
|
end
|
49
49
|
|
50
50
|
def identity
|
51
|
-
|
51
|
+
@@identity ||= "#{hostname}:#{::Process.pid}:#{process_nonce}"
|
52
52
|
end
|
53
53
|
|
54
54
|
def fire_event(event, options = {})
|
data/lib/sidekiq/version.rb
CHANGED
data/lib/sidekiq/web.rb
CHANGED
@@ -65,11 +65,11 @@ module Sidekiq
|
|
65
65
|
end
|
66
66
|
|
67
67
|
def enable(*opts)
|
68
|
-
opts.each {|key| set(key, true) }
|
68
|
+
opts.each { |key| set(key, true) }
|
69
69
|
end
|
70
70
|
|
71
71
|
def disable(*opts)
|
72
|
-
opts.each {|key| set(key, false) }
|
72
|
+
opts.each { |key| set(key, false) }
|
73
73
|
end
|
74
74
|
|
75
75
|
# Helper for the Sinatra syntax: Sidekiq::Web.set(:session_secret, Rails.application.secrets...)
|
@@ -114,11 +114,11 @@ module Sidekiq
|
|
114
114
|
end
|
115
115
|
|
116
116
|
def enable(*opts)
|
117
|
-
opts.each {|key| set(key, true) }
|
117
|
+
opts.each { |key| set(key, true) }
|
118
118
|
end
|
119
119
|
|
120
120
|
def disable(*opts)
|
121
|
-
opts.each {|key| set(key, false) }
|
121
|
+
opts.each { |key| set(key, false) }
|
122
122
|
end
|
123
123
|
|
124
124
|
def set(attribute, value)
|
@@ -187,7 +187,7 @@ module Sidekiq
|
|
187
187
|
end
|
188
188
|
end
|
189
189
|
|
190
|
-
middlewares.each {|middleware, block| use(*middleware, &block) }
|
190
|
+
middlewares.each { |middleware, block| use(*middleware, &block) }
|
191
191
|
|
192
192
|
run WebApplication.new(klass)
|
193
193
|
end
|
data/lib/sidekiq/web/action.rb
CHANGED
@@ -23,10 +23,10 @@ module Sidekiq
|
|
23
23
|
end
|
24
24
|
|
25
25
|
def params
|
26
|
-
indifferent_hash = Hash.new {|hash, key| hash[key.to_s] if Symbol === key }
|
26
|
+
indifferent_hash = Hash.new { |hash, key| hash[key.to_s] if Symbol === key }
|
27
27
|
|
28
28
|
indifferent_hash.merge! request.params
|
29
|
-
route_params.each {|k, v| indifferent_hash[k.to_s] = v }
|
29
|
+
route_params.each { |k, v| indifferent_hash[k.to_s] = v }
|
30
30
|
|
31
31
|
indifferent_hash
|
32
32
|
end
|
@@ -81,7 +81,7 @@ module Sidekiq
|
|
81
81
|
private
|
82
82
|
|
83
83
|
def _erb(file, locals)
|
84
|
-
locals&.each {|k, v| define_singleton_method(k) { v } unless singleton_methods.include? k}
|
84
|
+
locals&.each { |k, v| define_singleton_method(k) { v } unless singleton_methods.include? k }
|
85
85
|
|
86
86
|
if file.is_a?(String)
|
87
87
|
ERB.new(file).result(binding)
|
@@ -257,7 +257,7 @@ module Sidekiq
|
|
257
257
|
|
258
258
|
get "/stats" do
|
259
259
|
sidekiq_stats = Sidekiq::Stats.new
|
260
|
-
redis_stats
|
260
|
+
redis_stats = redis_info.select { |k, v| REDIS_KEYS.include? k }
|
261
261
|
json(
|
262
262
|
sidekiq: {
|
263
263
|
processed: sidekiq_stats.processed,
|
@@ -342,7 +342,7 @@ module Sidekiq
|
|
342
342
|
|
343
343
|
def self.run_hooks(hooks, app, action)
|
344
344
|
hooks.select { |p, _| !p || p =~ action.env[WebRouter::PATH_INFO] }
|
345
|
-
.each {|_, b| action.instance_exec(action.env, app, &b) }
|
345
|
+
.each { |_, b| action.instance_exec(action.env, app, &b) }
|
346
346
|
end
|
347
347
|
|
348
348
|
def self.befores
|
data/lib/sidekiq/web/helpers.rb
CHANGED
@@ -84,7 +84,7 @@ module Sidekiq
|
|
84
84
|
languages = env["HTTP_ACCEPT_LANGUAGE"]
|
85
85
|
languages.to_s.downcase.gsub(/\s+/, "").split(",").map { |language|
|
86
86
|
locale, quality = language.split(";q=", 2)
|
87
|
-
locale
|
87
|
+
locale = nil if locale == "*" # Ignore wildcards
|
88
88
|
quality = quality ? quality.to_f : 1.0
|
89
89
|
[locale, quality]
|
90
90
|
}.sort { |(_, left), (_, right)|
|
data/lib/sidekiq/worker.rb
CHANGED
@@ -21,15 +21,124 @@ module Sidekiq
|
|
21
21
|
#
|
22
22
|
# Note that perform_async is a class method, perform is an instance method.
|
23
23
|
module Worker
|
24
|
+
##
|
25
|
+
# The Options module is extracted so we can include it in ActiveJob::Base
|
26
|
+
# and allow native AJs to configure Sidekiq features/internals.
|
27
|
+
module Options
|
28
|
+
def self.included(base)
|
29
|
+
base.extend(ClassMethods)
|
30
|
+
base.sidekiq_class_attribute :sidekiq_options_hash
|
31
|
+
base.sidekiq_class_attribute :sidekiq_retry_in_block
|
32
|
+
base.sidekiq_class_attribute :sidekiq_retries_exhausted_block
|
33
|
+
end
|
34
|
+
|
35
|
+
module ClassMethods
|
36
|
+
ACCESSOR_MUTEX = Mutex.new
|
37
|
+
|
38
|
+
##
|
39
|
+
# Allows customization for this type of Worker.
|
40
|
+
# Legal options:
|
41
|
+
#
|
42
|
+
# queue - name of queue to use for this job type, default *default*
|
43
|
+
# retry - enable retries for this Worker in case of error during execution,
|
44
|
+
# *true* to use the default or *Integer* count
|
45
|
+
# backtrace - whether to save any error backtrace in the retry payload to display in web UI,
|
46
|
+
# can be true, false or an integer number of lines to save, default *false*
|
47
|
+
#
|
48
|
+
# In practice, any option is allowed. This is the main mechanism to configure the
|
49
|
+
# options for a specific job.
|
50
|
+
def sidekiq_options(opts = {})
|
51
|
+
opts = Hash[opts.map { |k, v| [k.to_s, v] }] # stringify
|
52
|
+
self.sidekiq_options_hash = get_sidekiq_options.merge(Hash[opts.map { |k, v| [k.to_s, v] }])
|
53
|
+
end
|
54
|
+
|
55
|
+
def sidekiq_retry_in(&block)
|
56
|
+
self.sidekiq_retry_in_block = block
|
57
|
+
end
|
58
|
+
|
59
|
+
def sidekiq_retries_exhausted(&block)
|
60
|
+
self.sidekiq_retries_exhausted_block = block
|
61
|
+
end
|
62
|
+
|
63
|
+
def get_sidekiq_options # :nodoc:
|
64
|
+
self.sidekiq_options_hash ||= Sidekiq.default_worker_options
|
65
|
+
end
|
66
|
+
|
67
|
+
def sidekiq_class_attribute(*attrs)
|
68
|
+
instance_reader = true
|
69
|
+
instance_writer = true
|
70
|
+
|
71
|
+
attrs.each do |name|
|
72
|
+
synchronized_getter = "__synchronized_#{name}"
|
73
|
+
|
74
|
+
singleton_class.instance_eval do
|
75
|
+
undef_method(name) if method_defined?(name) || private_method_defined?(name)
|
76
|
+
end
|
77
|
+
|
78
|
+
define_singleton_method(synchronized_getter) { nil }
|
79
|
+
singleton_class.class_eval do
|
80
|
+
private(synchronized_getter)
|
81
|
+
end
|
82
|
+
|
83
|
+
define_singleton_method(name) { ACCESSOR_MUTEX.synchronize { send synchronized_getter } }
|
84
|
+
|
85
|
+
ivar = "@#{name}"
|
86
|
+
|
87
|
+
singleton_class.instance_eval do
|
88
|
+
m = "#{name}="
|
89
|
+
undef_method(m) if method_defined?(m) || private_method_defined?(m)
|
90
|
+
end
|
91
|
+
define_singleton_method("#{name}=") do |val|
|
92
|
+
singleton_class.class_eval do
|
93
|
+
ACCESSOR_MUTEX.synchronize do
|
94
|
+
undef_method(synchronized_getter) if method_defined?(synchronized_getter) || private_method_defined?(synchronized_getter)
|
95
|
+
define_method(synchronized_getter) { val }
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
if singleton_class?
|
100
|
+
class_eval do
|
101
|
+
undef_method(name) if method_defined?(name) || private_method_defined?(name)
|
102
|
+
define_method(name) do
|
103
|
+
if instance_variable_defined? ivar
|
104
|
+
instance_variable_get ivar
|
105
|
+
else
|
106
|
+
singleton_class.send name
|
107
|
+
end
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
111
|
+
val
|
112
|
+
end
|
113
|
+
|
114
|
+
if instance_reader
|
115
|
+
undef_method(name) if method_defined?(name) || private_method_defined?(name)
|
116
|
+
define_method(name) do
|
117
|
+
if instance_variable_defined?(ivar)
|
118
|
+
instance_variable_get ivar
|
119
|
+
else
|
120
|
+
self.class.public_send name
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
124
|
+
|
125
|
+
if instance_writer
|
126
|
+
m = "#{name}="
|
127
|
+
undef_method(m) if method_defined?(m) || private_method_defined?(m)
|
128
|
+
attr_writer name
|
129
|
+
end
|
130
|
+
end
|
131
|
+
end
|
132
|
+
end
|
133
|
+
end
|
134
|
+
|
24
135
|
attr_accessor :jid
|
25
136
|
|
26
137
|
def self.included(base)
|
27
|
-
raise ArgumentError, "
|
138
|
+
raise ArgumentError, "Sidekiq::Worker cannot be included in an ActiveJob: #{base.name}" if base.ancestors.any? { |c| c.name == "ActiveJob::Base" }
|
28
139
|
|
140
|
+
base.include(Options)
|
29
141
|
base.extend(ClassMethods)
|
30
|
-
base.sidekiq_class_attribute :sidekiq_options_hash
|
31
|
-
base.sidekiq_class_attribute :sidekiq_retry_in_block
|
32
|
-
base.sidekiq_class_attribute :sidekiq_retries_exhausted_block
|
33
142
|
end
|
34
143
|
|
35
144
|
def logger
|
@@ -71,8 +180,6 @@ module Sidekiq
|
|
71
180
|
end
|
72
181
|
|
73
182
|
module ClassMethods
|
74
|
-
ACCESSOR_MUTEX = Mutex.new
|
75
|
-
|
76
183
|
def delay(*args)
|
77
184
|
raise ArgumentError, "Do not call .delay on a Sidekiq::Worker class, call .perform_async"
|
78
185
|
end
|
@@ -123,20 +230,7 @@ module Sidekiq
|
|
123
230
|
# In practice, any option is allowed. This is the main mechanism to configure the
|
124
231
|
# options for a specific job.
|
125
232
|
def sidekiq_options(opts = {})
|
126
|
-
|
127
|
-
self.sidekiq_options_hash = get_sidekiq_options.merge(Hash[opts.map {|k, v| [k.to_s, v]}])
|
128
|
-
end
|
129
|
-
|
130
|
-
def sidekiq_retry_in(&block)
|
131
|
-
self.sidekiq_retry_in_block = block
|
132
|
-
end
|
133
|
-
|
134
|
-
def sidekiq_retries_exhausted(&block)
|
135
|
-
self.sidekiq_retries_exhausted_block = block
|
136
|
-
end
|
137
|
-
|
138
|
-
def get_sidekiq_options # :nodoc:
|
139
|
-
self.sidekiq_options_hash ||= Sidekiq.default_worker_options
|
233
|
+
super
|
140
234
|
end
|
141
235
|
|
142
236
|
def client_push(item) # :nodoc:
|
@@ -148,72 +242,6 @@ module Sidekiq
|
|
148
242
|
|
149
243
|
Sidekiq::Client.new(pool).push(item)
|
150
244
|
end
|
151
|
-
|
152
|
-
def sidekiq_class_attribute(*attrs)
|
153
|
-
instance_reader = true
|
154
|
-
instance_writer = true
|
155
|
-
|
156
|
-
attrs.each do |name|
|
157
|
-
synchronized_getter = "__synchronized_#{name}"
|
158
|
-
|
159
|
-
singleton_class.instance_eval do
|
160
|
-
undef_method(name) if method_defined?(name) || private_method_defined?(name)
|
161
|
-
end
|
162
|
-
|
163
|
-
define_singleton_method(synchronized_getter) { nil }
|
164
|
-
singleton_class.class_eval do
|
165
|
-
private(synchronized_getter)
|
166
|
-
end
|
167
|
-
|
168
|
-
define_singleton_method(name) { ACCESSOR_MUTEX.synchronize { send synchronized_getter } }
|
169
|
-
|
170
|
-
ivar = "@#{name}"
|
171
|
-
|
172
|
-
singleton_class.instance_eval do
|
173
|
-
m = "#{name}="
|
174
|
-
undef_method(m) if method_defined?(m) || private_method_defined?(m)
|
175
|
-
end
|
176
|
-
define_singleton_method("#{name}=") do |val|
|
177
|
-
singleton_class.class_eval do
|
178
|
-
ACCESSOR_MUTEX.synchronize do
|
179
|
-
undef_method(synchronized_getter) if method_defined?(synchronized_getter) || private_method_defined?(synchronized_getter)
|
180
|
-
define_method(synchronized_getter) { val }
|
181
|
-
end
|
182
|
-
end
|
183
|
-
|
184
|
-
if singleton_class?
|
185
|
-
class_eval do
|
186
|
-
undef_method(name) if method_defined?(name) || private_method_defined?(name)
|
187
|
-
define_method(name) do
|
188
|
-
if instance_variable_defined? ivar
|
189
|
-
instance_variable_get ivar
|
190
|
-
else
|
191
|
-
singleton_class.send name
|
192
|
-
end
|
193
|
-
end
|
194
|
-
end
|
195
|
-
end
|
196
|
-
val
|
197
|
-
end
|
198
|
-
|
199
|
-
if instance_reader
|
200
|
-
undef_method(name) if method_defined?(name) || private_method_defined?(name)
|
201
|
-
define_method(name) do
|
202
|
-
if instance_variable_defined?(ivar)
|
203
|
-
instance_variable_get ivar
|
204
|
-
else
|
205
|
-
self.class.public_send name
|
206
|
-
end
|
207
|
-
end
|
208
|
-
end
|
209
|
-
|
210
|
-
if instance_writer
|
211
|
-
m = "#{name}="
|
212
|
-
undef_method(m) if method_defined?(m) || private_method_defined?(m)
|
213
|
-
attr_writer name
|
214
|
-
end
|
215
|
-
end
|
216
|
-
end
|
217
245
|
end
|
218
246
|
end
|
219
247
|
end
|
data/sidekiq.gemspec
CHANGED
@@ -1,21 +1,21 @@
|
|
1
1
|
require_relative "lib/sidekiq/version"
|
2
2
|
|
3
3
|
Gem::Specification.new do |gem|
|
4
|
-
gem.authors
|
5
|
-
gem.email
|
6
|
-
gem.summary
|
7
|
-
gem.description
|
8
|
-
gem.homepage
|
9
|
-
gem.license
|
4
|
+
gem.authors = ["Mike Perham"]
|
5
|
+
gem.email = ["mperham@gmail.com"]
|
6
|
+
gem.summary = "Simple, efficient background processing for Ruby"
|
7
|
+
gem.description = "Simple, efficient background processing for Ruby."
|
8
|
+
gem.homepage = "http://sidekiq.org"
|
9
|
+
gem.license = "LGPL-3.0"
|
10
10
|
|
11
|
-
gem.executables
|
12
|
-
gem.files
|
13
|
-
gem.name
|
14
|
-
gem.version
|
11
|
+
gem.executables = ["sidekiq"]
|
12
|
+
gem.files = `git ls-files | grep -Ev '^(test|myapp|examples)'`.split("\n")
|
13
|
+
gem.name = "sidekiq"
|
14
|
+
gem.version = Sidekiq::VERSION
|
15
15
|
gem.required_ruby_version = ">= 2.5.0"
|
16
16
|
|
17
|
-
gem.add_dependency "redis", ">= 4.0
|
17
|
+
gem.add_dependency "redis", ">= 4.1.0"
|
18
18
|
gem.add_dependency "connection_pool", ">= 2.2.2"
|
19
|
-
gem.add_dependency "rack", ">=
|
20
|
-
gem.add_dependency "rack-protection", ">=
|
19
|
+
gem.add_dependency "rack", ">= 2.0.0"
|
20
|
+
gem.add_dependency "rack-protection", ">= 2.0.0"
|
21
21
|
end
|
@@ -16,10 +16,8 @@ var gridSize=(this.orientation=="right"?1:-1)*this.graph.width;this.graph.vis.ap
|
|
16
16
|
var nodes=vis.selectAll("path").data(series.stack.filter(function(d){return d.y!==null})).enter().append("svg:rect").attr("x",function(d){return graph.x(d.x)+barXOffset}).attr("y",function(d){return graph.y(d.y0+Math.abs(d.y))*(d.y<0?-1:1)}).attr("width",seriesBarWidth).attr("height",function(d){return graph.y.magnitude(Math.abs(d.y))}).attr("opacity",series.opacity).attr("transform",transform);Array.prototype.forEach.call(nodes[0],function(n){n.setAttribute("fill",series.color)});if(this.unstack)barXOffset+=seriesBarWidth},this)},_frequentInterval:function(data){var intervalCounts={};for(var i=0;i<data.length-1;i++){var interval=data[i+1].x-data[i].x;intervalCounts[interval]=intervalCounts[interval]||0;intervalCounts[interval]++}var frequentInterval={count:0,magnitude:1};var keysSorted=Rickshaw.keys(intervalCounts).sort(function asc(a,b){return Number(a)-Number(b)});keysSorted.forEach(function(i){if(frequentInterval.count<intervalCounts[i]){frequentInterval={count:intervalCounts[i],magnitude:i}}});return frequentInterval}});Rickshaw.namespace("Rickshaw.Graph.Renderer.Area");Rickshaw.Graph.Renderer.Area=Rickshaw.Class.create(Rickshaw.Graph.Renderer,{name:"area",defaults:function($super){return Rickshaw.extend($super(),{unstack:false,fill:false,stroke:false})},seriesPathFactory:function(){var graph=this.graph;var factory=d3.svg.area().x(function(d){return graph.x(d.x)}).y0(function(d){return graph.y(d.y0)}).y1(function(d){return graph.y(d.y+d.y0)}).interpolate(graph.interpolation).tension(this.tension);factory.defined&&factory.defined(function(d){return d.y!==null});return factory},seriesStrokeFactory:function(){var graph=this.graph;var factory=d3.svg.line().x(function(d){return graph.x(d.x)}).y(function(d){return graph.y(d.y+d.y0)}).interpolate(graph.interpolation).tension(this.tension);factory.defined&&factory.defined(function(d){return d.y!==null});return factory},render:function(args){args=args||{};var graph=this.graph;var series=args.series||graph.series;var vis=args.vis||graph.vis;vis.selectAll("*").remove();var method=this.unstack?"append":"insert";var data=series.filter(function(s){return!s.disabled}).map(function(s){return s.stack});var nodes=vis.selectAll("path").data(data).enter()[method]("svg:g","g");nodes.append("svg:path").attr("d",this.seriesPathFactory()).attr("class","area");if(this.stroke){nodes.append("svg:path").attr("d",this.seriesStrokeFactory()).attr("class","line")}var i=0;series.forEach(function(series){if(series.disabled)return;series.path=nodes[0][i++];this._styleSeries(series)},this)},_styleSeries:function(series){if(!series.path)return;d3.select(series.path).select(".area").attr("fill",series.color);if(this.stroke){d3.select(series.path).select(".line").attr("fill","none").attr("stroke",series.stroke||d3.interpolateRgb(series.color,"black")(.125)).attr("stroke-width",this.strokeWidth)}if(series.className){series.path.setAttribute("class",series.className)}}});Rickshaw.namespace("Rickshaw.Graph.Renderer.ScatterPlot");Rickshaw.Graph.Renderer.ScatterPlot=Rickshaw.Class.create(Rickshaw.Graph.Renderer,{name:"scatterplot",defaults:function($super){return Rickshaw.extend($super(),{unstack:true,fill:true,stroke:false,padding:{top:.01,right:.01,bottom:.01,left:.01},dotSize:4})},initialize:function($super,args){$super(args)},render:function(args){args=args||{};var graph=this.graph;var series=args.series||graph.series;var vis=args.vis||graph.vis;var dotSize=this.dotSize;vis.selectAll("*").remove();series.forEach(function(series){if(series.disabled)return;var opacity=series.opacity?series.opacity:1;var nodes=vis.selectAll("path").data(series.stack.filter(function(d){return d.y!==null})).enter().append("svg:circle").attr("cx",function(d){return graph.x(d.x)}).attr("cy",function(d){return graph.y(d.y)}).attr("r",function(d){return"r"in d?d.r:dotSize}).attr("opacity",function(d){return"opacity"in d?d.opacity:opacity});if(series.className){nodes.classed(series.className,true)}Array.prototype.forEach.call(nodes[0],function(n){n.setAttribute("fill",series.color)})},this)}});Rickshaw.namespace("Rickshaw.Graph.Renderer.Multi");Rickshaw.Graph.Renderer.Multi=Rickshaw.Class.create(Rickshaw.Graph.Renderer,{name:"multi",initialize:function($super,args){$super(args)},defaults:function($super){return Rickshaw.extend($super(),{unstack:true,fill:false,stroke:true})},configure:function($super,args){args=args||{};this.config=args;$super(args)},domain:function($super){this.graph.stackData();var domains=[];var groups=this._groups();this._stack(groups);groups.forEach(function(group){var data=group.series.filter(function(s){return!s.disabled}).map(function(s){return s.stack});if(!data.length)return;var domain=null;if(group.renderer&&group.renderer.domain){domain=group.renderer.domain(data)}else{domain=$super(data)}domains.push(domain)});var xMin=d3.min(domains.map(function(d){return d.x[0]}));var xMax=d3.max(domains.map(function(d){return d.x[1]}));var yMin=d3.min(domains.map(function(d){return d.y[0]}));var yMax=d3.max(domains.map(function(d){return d.y[1]}));return{x:[xMin,xMax],y:[yMin,yMax]}},_groups:function(){var graph=this.graph;var renderGroups={};graph.series.forEach(function(series){if(series.disabled)return;if(!renderGroups[series.renderer]){var ns="http://www.w3.org/2000/svg";var vis=document.createElementNS(ns,"g");graph.vis[0][0].appendChild(vis);var renderer=graph._renderers[series.renderer];var config={};var defaults=[this.defaults(),renderer.defaults(),this.config,this.graph];defaults.forEach(function(d){Rickshaw.extend(config,d)});renderer.configure(config);renderGroups[series.renderer]={renderer:renderer,series:[],vis:d3.select(vis)}}renderGroups[series.renderer].series.push(series)},this);var groups=[];Object.keys(renderGroups).forEach(function(key){var group=renderGroups[key];groups.push(group)});return groups},_stack:function(groups){groups.forEach(function(group){var series=group.series.filter(function(series){return!series.disabled});var data=series.map(function(series){return series.stack});if(!group.renderer.unstack){var layout=d3.layout.stack();var stackedData=Rickshaw.clone(layout(data));series.forEach(function(series,index){series._stack=Rickshaw.clone(stackedData[index])})}},this);return groups},render:function(){this.graph.series.forEach(function(series){if(!series.renderer){throw new Error("Each series needs a renderer for graph 'multi' renderer")}});this.graph.vis.selectAll("*").remove();var groups=this._groups();groups=this._stack(groups);groups.forEach(function(group){var series=group.series.filter(function(series){return!series.disabled});series.active=function(){return series};group.renderer.render({series:series,vis:group.vis});series.forEach(function(s){s.stack=s._stack||s.stack||s.data})})}});Rickshaw.namespace("Rickshaw.Graph.Renderer.LinePlot");Rickshaw.Graph.Renderer.LinePlot=Rickshaw.Class.create(Rickshaw.Graph.Renderer,{name:"lineplot",defaults:function($super){return Rickshaw.extend($super(),{unstack:true,fill:false,stroke:true,padding:{top:.01,right:.01,bottom:.01,left:.01},dotSize:3,strokeWidth:2})},seriesPathFactory:function(){var graph=this.graph;var factory=d3.svg.line().x(function(d){return graph.x(d.x)}).y(function(d){return graph.y(d.y)}).interpolate(this.graph.interpolation).tension(this.tension);factory.defined&&factory.defined(function(d){return d.y!==null});return factory},render:function(args){args=args||{};var graph=this.graph;var series=args.series||graph.series;var vis=args.vis||graph.vis;var dotSize=this.dotSize;vis.selectAll("*").remove();var data=series.filter(function(s){return!s.disabled}).map(function(s){return s.stack});var nodes=vis.selectAll("path").data(data).enter().append("svg:path").attr("d",this.seriesPathFactory());var i=0;series.forEach(function(series){if(series.disabled)return;series.path=nodes[0][i++];this._styleSeries(series)},this);series.forEach(function(series){if(series.disabled)return;var nodes=vis.selectAll("x").data(series.stack.filter(function(d){return d.y!==null})).enter().append("svg:circle").attr("cx",function(d){return graph.x(d.x)}).attr("cy",function(d){return graph.y(d.y)}).attr("r",function(d){return"r"in d?d.r:dotSize});Array.prototype.forEach.call(nodes[0],function(n){if(!n)return;n.setAttribute("data-color",series.color);n.setAttribute("fill","white");n.setAttribute("stroke",series.color);n.setAttribute("stroke-width",this.strokeWidth)}.bind(this))},this)}});Rickshaw.namespace("Rickshaw.Graph.Smoother");Rickshaw.Graph.Smoother=Rickshaw.Class.create({initialize:function(args){this.graph=args.graph;this.element=args.element;this.aggregationScale=1;this.build();this.graph.stackData.hooks.data.push({name:"smoother",orderPosition:50,f:this.transformer.bind(this)})},build:function(){var self=this;var $=jQuery;if(this.element){$(function(){$(self.element).slider({min:1,max:100,slide:function(event,ui){self.setScale(ui.value)}})})}},setScale:function(scale){if(scale<1){throw"scale out of range: "+scale}this.aggregationScale=scale;this.graph.update()},transformer:function(data){if(this.aggregationScale==1)return data;var aggregatedData=[];data.forEach(function(seriesData){var aggregatedSeriesData=[];while(seriesData.length){var avgX=0,avgY=0;var slice=seriesData.splice(0,this.aggregationScale);slice.forEach(function(d){avgX+=d.x/slice.length;avgY+=d.y/slice.length});aggregatedSeriesData.push({x:avgX,y:avgY})}aggregatedData.push(aggregatedSeriesData)}.bind(this));return aggregatedData}});Rickshaw.namespace("Rickshaw.Graph.Socketio");Rickshaw.Graph.Socketio=Rickshaw.Class.create(Rickshaw.Graph.Ajax,{request:function(){var socket=io.connect(this.dataURL);var self=this;socket.on("rickshaw",function(data){self.success(data)})}});Rickshaw.namespace("Rickshaw.Series");Rickshaw.Series=Rickshaw.Class.create(Array,{initialize:function(data,palette,options){options=options||{};this.palette=new Rickshaw.Color.Palette(palette);this.timeBase=typeof options.timeBase==="undefined"?Math.floor((new Date).getTime()/1e3):options.timeBase;var timeInterval=typeof options.timeInterval=="undefined"?1e3:options.timeInterval;this.setTimeInterval(timeInterval);if(data&&typeof data=="object"&&Array.isArray(data)){data.forEach(function(item){this.addItem(item)},this)}},addItem:function(item){if(typeof item.name==="undefined"){throw"addItem() needs a name"}item.color=item.color||this.palette.color(item.name);item.data=item.data||[];if(item.data.length===0&&this.length&&this.getIndex()>0){this[0].data.forEach(function(plot){item.data.push({x:plot.x,y:0})})}else if(item.data.length===0){item.data.push({x:this.timeBase-(this.timeInterval||0),y:0})}this.push(item);if(this.legend){this.legend.addLine(this.itemByName(item.name))}},addData:function(data,x){var index=this.getIndex();Rickshaw.keys(data).forEach(function(name){if(!this.itemByName(name)){this.addItem({name:name})}},this);this.forEach(function(item){item.data.push({x:x||(index*this.timeInterval||1)+this.timeBase,y:data[item.name]||0})},this)},getIndex:function(){return this[0]&&this[0].data&&this[0].data.length?this[0].data.length:0},itemByName:function(name){for(var i=0;i<this.length;i++){if(this[i].name==name)return this[i]}},setTimeInterval:function(iv){this.timeInterval=iv/1e3},setTimeBase:function(t){this.timeBase=t},dump:function(){var data={timeBase:this.timeBase,timeInterval:this.timeInterval,items:[]};this.forEach(function(item){var newItem={color:item.color,name:item.name,data:[]};item.data.forEach(function(plot){newItem.data.push({x:plot.x,y:plot.y})});data.items.push(newItem)});return data},load:function(data){if(data.timeInterval){this.timeInterval=data.timeInterval}if(data.timeBase){this.timeBase=data.timeBase}if(data.items){data.items.forEach(function(item){this.push(item);if(this.legend){this.legend.addLine(this.itemByName(item.name))}},this)}}});Rickshaw.Series.zeroFill=function(series){Rickshaw.Series.fill(series,0)};Rickshaw.Series.fill=function(series,fill){var x;var i=0;var data=series.map(function(s){return s.data});while(i<Math.max.apply(null,data.map(function(d){return d.length}))){x=Math.min.apply(null,data.filter(function(d){return d[i]}).map(function(d){return d[i].x}));data.forEach(function(d){if(!d[i]||d[i].x!=x){d.splice(i,0,{x:x,y:fill})}});i++}};Rickshaw.namespace("Rickshaw.Series.FixedDuration");Rickshaw.Series.FixedDuration=Rickshaw.Class.create(Rickshaw.Series,{initialize:function(data,palette,options){options=options||{};if(typeof options.timeInterval==="undefined"){throw new Error("FixedDuration series requires timeInterval")}if(typeof options.maxDataPoints==="undefined"){throw new Error("FixedDuration series requires maxDataPoints")}this.palette=new Rickshaw.Color.Palette(palette);this.timeBase=typeof options.timeBase==="undefined"?Math.floor((new Date).getTime()/1e3):options.timeBase;this.setTimeInterval(options.timeInterval);if(this[0]&&this[0].data&&this[0].data.length){this.currentSize=this[0].data.length;this.currentIndex=this[0].data.length}else{this.currentSize=0;this.currentIndex=0}this.maxDataPoints=options.maxDataPoints;if(data&&typeof data=="object"&&Array.isArray(data)){data.forEach(function(item){this.addItem(item)},this);this.currentSize+=1;this.currentIndex+=1}this.timeBase-=(this.maxDataPoints-this.currentSize)*this.timeInterval;if(typeof this.maxDataPoints!=="undefined"&&this.currentSize<this.maxDataPoints){for(var i=this.maxDataPoints-this.currentSize-1;i>1;i--){this.currentSize+=1;this.currentIndex+=1;this.forEach(function(item){item.data.unshift({x:((i-1)*this.timeInterval||1)+this.timeBase,y:0,i:i})},this)}}},addData:function($super,data,x){$super(data,x);this.currentSize+=1;this.currentIndex+=1;if(this.maxDataPoints!==undefined){while(this.currentSize>this.maxDataPoints){this.dropData()}}},dropData:function(){this.forEach(function(item){item.data.splice(0,1)});this.currentSize-=1},getIndex:function(){return this.currentIndex}});return Rickshaw});
|
17
17
|
|
18
18
|
var poller;
|
19
|
-
|
20
19
|
var realtimeGraph = function(updatePath) {
|
21
20
|
var timeInterval = parseInt(localStorage.timeInterval || '5000');
|
22
|
-
|
23
21
|
var graphElement = document.getElementById("realtime");
|
24
22
|
|
25
23
|
var graph = new Rickshaw.Graph( {
|
@@ -30,8 +28,8 @@ var realtimeGraph = function(updatePath) {
|
|
30
28
|
interpolation: 'linear',
|
31
29
|
|
32
30
|
series: new Rickshaw.Series.FixedDuration([{ name: graphElement.dataset.failedLabel, color: '#B1003E' }, { name: graphElement.dataset.processedLabel, color: '#006f68' }], undefined, {
|
33
|
-
|
34
|
-
|
31
|
+
timeInterval: timeInterval,
|
32
|
+
maxDataPoints: 100,
|
35
33
|
})
|
36
34
|
});
|
37
35
|
|
@@ -46,7 +44,6 @@ var realtimeGraph = function(updatePath) {
|
|
46
44
|
var legend = document.querySelector('#realtime-legend');
|
47
45
|
var Hover = Rickshaw.Class.create(Rickshaw.Graph.HoverDetail, {
|
48
46
|
render: function(args) {
|
49
|
-
|
50
47
|
legend.innerHTML = "";
|
51
48
|
|
52
49
|
var timestamp = document.createElement('div');
|
@@ -68,7 +65,6 @@ var realtimeGraph = function(updatePath) {
|
|
68
65
|
|
69
66
|
line.appendChild(swatch);
|
70
67
|
line.appendChild(label);
|
71
|
-
|
72
68
|
legend.appendChild(line);
|
73
69
|
|
74
70
|
var dot = document.createElement('div');
|
@@ -77,11 +73,8 @@ var realtimeGraph = function(updatePath) {
|
|
77
73
|
dot.style.borderColor = d.series.color;
|
78
74
|
|
79
75
|
this.element.appendChild(dot);
|
80
|
-
|
81
76
|
dot.className = 'dot active';
|
82
|
-
|
83
77
|
this.show();
|
84
|
-
|
85
78
|
}, this );
|
86
79
|
}
|
87
80
|
});
|
@@ -90,7 +83,6 @@ var realtimeGraph = function(updatePath) {
|
|
90
83
|
var i = 0;
|
91
84
|
poller = setInterval(function() {
|
92
85
|
$.getJSON($("#history").data("update-url"), function(data) {
|
93
|
-
|
94
86
|
if (i === 0) {
|
95
87
|
var processed = data.sidekiq.processed;
|
96
88
|
var failed = data.sidekiq.failed;
|
@@ -144,7 +136,6 @@ var historyGraph = function() {
|
|
144
136
|
]
|
145
137
|
} );
|
146
138
|
var x_axis = new Rickshaw.Graph.Axis.Time( { graph: graph } );
|
147
|
-
|
148
139
|
var y_axis = new Rickshaw.Graph.Axis.Y({
|
149
140
|
graph: graph,
|
150
141
|
tickFormat: Rickshaw.Fixtures.Number.formatKMBT,
|
@@ -156,7 +147,6 @@ var historyGraph = function() {
|
|
156
147
|
var legend = document.querySelector('#history-legend');
|
157
148
|
var Hover = Rickshaw.Class.create(Rickshaw.Graph.HoverDetail, {
|
158
149
|
render: function(args) {
|
159
|
-
|
160
150
|
legend.innerHTML = "";
|
161
151
|
|
162
152
|
var timestamp = document.createElement('div');
|
@@ -178,7 +168,6 @@ var historyGraph = function() {
|
|
178
168
|
|
179
169
|
line.appendChild(swatch);
|
180
170
|
line.appendChild(label);
|
181
|
-
|
182
171
|
legend.appendChild(line);
|
183
172
|
|
184
173
|
var dot = document.createElement('div');
|
@@ -187,11 +176,8 @@ var historyGraph = function() {
|
|
187
176
|
dot.style.borderColor = d.series.color;
|
188
177
|
|
189
178
|
this.element.appendChild(dot);
|
190
|
-
|
191
179
|
dot.className = 'dot active';
|
192
|
-
|
193
180
|
this.show();
|
194
|
-
|
195
181
|
}, this );
|
196
182
|
}
|
197
183
|
});
|
@@ -216,7 +202,6 @@ var updateStatsSummary = function(data) {
|
|
216
202
|
$('ul.summary li.retries span.count').html(data.retries.numberWithDelimiter())
|
217
203
|
$('ul.summary li.enqueued span.count').html(data.enqueued.numberWithDelimiter())
|
218
204
|
$('ul.summary li.dead span.count').html(data.dead.numberWithDelimiter())
|
219
|
-
|
220
205
|
}
|
221
206
|
|
222
207
|
var updateRedisStats = function(data) {
|
@@ -277,7 +262,6 @@ $(function(){
|
|
277
262
|
$(document).on('mousemove', 'div.interval-slider input', function(){
|
278
263
|
setSliderLabel($(this).val());
|
279
264
|
});
|
280
|
-
|
281
265
|
});
|
282
266
|
|
283
267
|
// Reset graphs
|
@@ -300,13 +284,10 @@ var debounce = function(fn, timeout)
|
|
300
284
|
|
301
285
|
window.onresize = function() {
|
302
286
|
var prevWidth = window.innerWidth;
|
303
|
-
|
304
287
|
return debounce(function () {
|
305
288
|
var currWidth = window.innerWidth;
|
306
|
-
|
307
289
|
if (prevWidth !== currWidth) {
|
308
290
|
prevWidth = currWidth;
|
309
|
-
|
310
291
|
clearInterval(poller);
|
311
292
|
resetGraphs();
|
312
293
|
renderGraphs();
|