grockit-resque 1.5.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (61) hide show
  1. data/.gitignore +2 -0
  2. data/.kick +26 -0
  3. data/CONTRIBUTORS +14 -0
  4. data/HISTORY.md +78 -0
  5. data/LICENSE +20 -0
  6. data/README.markdown +762 -0
  7. data/Rakefile +67 -0
  8. data/bin/resque +57 -0
  9. data/bin/resque-web +18 -0
  10. data/config.ru +14 -0
  11. data/deps.rip +6 -0
  12. data/examples/async_helper.rb +31 -0
  13. data/examples/demo/README.markdown +71 -0
  14. data/examples/demo/Rakefile +3 -0
  15. data/examples/demo/app.rb +38 -0
  16. data/examples/demo/config.ru +19 -0
  17. data/examples/demo/job.rb +22 -0
  18. data/examples/god/resque.god +53 -0
  19. data/examples/god/stale.god +26 -0
  20. data/examples/instance.rb +11 -0
  21. data/examples/simple.rb +30 -0
  22. data/init.rb +1 -0
  23. data/lib/resque.rb +247 -0
  24. data/lib/resque/errors.rb +7 -0
  25. data/lib/resque/failure.rb +63 -0
  26. data/lib/resque/failure/base.rb +58 -0
  27. data/lib/resque/failure/hoptoad.rb +122 -0
  28. data/lib/resque/failure/multiple.rb +44 -0
  29. data/lib/resque/failure/redis.rb +33 -0
  30. data/lib/resque/helpers.rb +57 -0
  31. data/lib/resque/job.rb +158 -0
  32. data/lib/resque/server.rb +182 -0
  33. data/lib/resque/server/public/idle.png +0 -0
  34. data/lib/resque/server/public/jquery-1.3.2.min.js +19 -0
  35. data/lib/resque/server/public/jquery.relatize_date.js +95 -0
  36. data/lib/resque/server/public/poll.png +0 -0
  37. data/lib/resque/server/public/ranger.js +24 -0
  38. data/lib/resque/server/public/reset.css +48 -0
  39. data/lib/resque/server/public/style.css +75 -0
  40. data/lib/resque/server/public/working.png +0 -0
  41. data/lib/resque/server/views/error.erb +1 -0
  42. data/lib/resque/server/views/failed.erb +35 -0
  43. data/lib/resque/server/views/key.erb +17 -0
  44. data/lib/resque/server/views/layout.erb +38 -0
  45. data/lib/resque/server/views/next_more.erb +10 -0
  46. data/lib/resque/server/views/overview.erb +4 -0
  47. data/lib/resque/server/views/queues.erb +46 -0
  48. data/lib/resque/server/views/stats.erb +62 -0
  49. data/lib/resque/server/views/workers.erb +78 -0
  50. data/lib/resque/server/views/working.erb +69 -0
  51. data/lib/resque/stat.rb +53 -0
  52. data/lib/resque/tasks.rb +39 -0
  53. data/lib/resque/version.rb +3 -0
  54. data/lib/resque/worker.rb +442 -0
  55. data/tasks/redis.rake +135 -0
  56. data/tasks/resque.rake +2 -0
  57. data/test/redis-test.conf +132 -0
  58. data/test/resque_test.rb +227 -0
  59. data/test/test_helper.rb +96 -0
  60. data/test/worker_test.rb +243 -0
  61. metadata +172 -0
@@ -0,0 +1,96 @@
1
+ dir = File.dirname(File.expand_path(__FILE__))
2
+ $LOAD_PATH.unshift dir + '/../lib'
3
+ $TESTING = true
4
+ require 'test/unit'
5
+ require 'rubygems'
6
+ require 'resque'
7
+
8
+
9
+ #
10
+ # make sure we can run redis
11
+ #
12
+
13
+ if !system("which redis-server")
14
+ puts '', "** can't find `redis-server` in your path"
15
+ puts "** try running `sudo rake install`"
16
+ abort ''
17
+ end
18
+
19
+
20
+ #
21
+ # start our own redis when the tests start,
22
+ # kill it when they end
23
+ #
24
+
25
+ at_exit do
26
+ next if $!
27
+
28
+ if defined?(MiniTest)
29
+ exit_code = MiniTest::Unit.new.run(ARGV)
30
+ else
31
+ exit_code = Test::Unit::AutoRunner.run
32
+ end
33
+
34
+ pid = `ps -e -o pid,command | grep [r]edis-test`.split(" ")[0]
35
+ puts "Killing test redis server..."
36
+ `rm -f #{dir}/dump.rdb`
37
+ Process.kill("KILL", pid.to_i)
38
+ exit exit_code
39
+ end
40
+
41
+ puts "Starting redis for testing at localhost:9736..."
42
+ `redis-server #{dir}/redis-test.conf`
43
+ Resque.redis = 'localhost:9736'
44
+
45
+
46
+ ##
47
+ # test/spec/mini 3
48
+ # http://gist.github.com/25455
49
+ # chris@ozmm.org
50
+ #
51
+ def context(*args, &block)
52
+ return super unless (name = args.first) && block
53
+ require 'test/unit'
54
+ klass = Class.new(defined?(ActiveSupport::TestCase) ? ActiveSupport::TestCase : Test::Unit::TestCase) do
55
+ def self.test(name, &block)
56
+ define_method("test_#{name.gsub(/\W/,'_')}", &block) if block
57
+ end
58
+ def self.xtest(*args) end
59
+ def self.setup(&block) define_method(:setup, &block) end
60
+ def self.teardown(&block) define_method(:teardown, &block) end
61
+ end
62
+ (class << klass; self end).send(:define_method, :name) { name.gsub(/\W/,'_') }
63
+ klass.class_eval &block
64
+ end
65
+
66
+
67
+ #
68
+ # fixture classes
69
+ #
70
+
71
+ class SomeJob
72
+ def self.perform(repo_id, path)
73
+ end
74
+ end
75
+
76
+ class SomeIvarJob < SomeJob
77
+ @queue = :ivar
78
+ end
79
+
80
+ class SomeMethodJob < SomeJob
81
+ def self.queue
82
+ :method
83
+ end
84
+ end
85
+
86
+ class BadJob
87
+ def self.perform
88
+ raise "Bad job!"
89
+ end
90
+ end
91
+
92
+ class GoodJob
93
+ def self.perform(name)
94
+ "Good job, #{name}"
95
+ end
96
+ end
@@ -0,0 +1,243 @@
1
+ require File.dirname(__FILE__) + '/test_helper'
2
+
3
+ context "Resque::Worker" do
4
+ setup do
5
+ Resque.redis.flush_all
6
+
7
+ @worker = Resque::Worker.new(:jobs)
8
+ Resque::Job.create(:jobs, SomeJob, 20, '/tmp')
9
+ end
10
+
11
+ test "can fail jobs" do
12
+ Resque::Job.create(:jobs, BadJob)
13
+ @worker.work(0)
14
+ assert_equal 1, Resque::Failure.count
15
+ end
16
+
17
+ test "can peek at failed jobs" do
18
+ 10.times { Resque::Job.create(:jobs, BadJob) }
19
+ @worker.work(0)
20
+ assert_equal 10, Resque::Failure.count
21
+
22
+ assert_equal 10, Resque::Failure.all(0, 20).size
23
+ end
24
+
25
+ test "can clear failed jobs" do
26
+ Resque::Job.create(:jobs, BadJob)
27
+ @worker.work(0)
28
+ assert_equal 1, Resque::Failure.count
29
+ Resque::Failure.clear
30
+ assert_equal 0, Resque::Failure.count
31
+ end
32
+
33
+ test "catches exceptional jobs" do
34
+ Resque::Job.create(:jobs, BadJob)
35
+ Resque::Job.create(:jobs, BadJob)
36
+ @worker.process
37
+ @worker.process
38
+ @worker.process
39
+ assert_equal 2, Resque::Failure.count
40
+ end
41
+
42
+ test "can work on multiple queues" do
43
+ Resque::Job.create(:high, GoodJob)
44
+ Resque::Job.create(:critical, GoodJob)
45
+
46
+ worker = Resque::Worker.new(:critical, :high)
47
+
48
+ worker.process
49
+ assert_equal 1, Resque.size(:high)
50
+ assert_equal 0, Resque.size(:critical)
51
+
52
+ worker.process
53
+ assert_equal 0, Resque.size(:high)
54
+ end
55
+
56
+ test "can work on all queues" do
57
+ Resque::Job.create(:high, GoodJob)
58
+ Resque::Job.create(:critical, GoodJob)
59
+ Resque::Job.create(:blahblah, GoodJob)
60
+
61
+ worker = Resque::Worker.new("*")
62
+
63
+ worker.work(0)
64
+ assert_equal 0, Resque.size(:high)
65
+ assert_equal 0, Resque.size(:critical)
66
+ assert_equal 0, Resque.size(:blahblah)
67
+ end
68
+
69
+ test "processes * queues in alphabetical order" do
70
+ Resque::Job.create(:high, GoodJob)
71
+ Resque::Job.create(:critical, GoodJob)
72
+ Resque::Job.create(:blahblah, GoodJob)
73
+
74
+ worker = Resque::Worker.new("*")
75
+ processed_queues = []
76
+
77
+ worker.work(0) do |job|
78
+ processed_queues << job.queue
79
+ end
80
+
81
+ assert_equal %w( jobs high critical blahblah ).sort, processed_queues
82
+ end
83
+
84
+ test "has a unique id" do
85
+ assert_equal "#{`hostname`.chomp}:#{$$}:jobs", @worker.to_s
86
+ end
87
+
88
+ test "complains if no queues are given" do
89
+ assert_raise Resque::NoQueueError do
90
+ Resque::Worker.new
91
+ end
92
+ end
93
+
94
+ test "fails if a job class has no `perform` method" do
95
+ worker = Resque::Worker.new(:perform_less)
96
+ Resque::Job.create(:perform_less, Object)
97
+
98
+ assert_equal 0, Resque::Failure.count
99
+ worker.work(0)
100
+ assert_equal 1, Resque::Failure.count
101
+ end
102
+
103
+ test "inserts itself into the 'workers' list on startup" do
104
+ @worker.work(0) do
105
+ assert_equal @worker, Resque.workers[0]
106
+ end
107
+ end
108
+
109
+ test "removes itself from the 'workers' list on shutdown" do
110
+ @worker.work(0) do
111
+ assert_equal @worker, Resque.workers[0]
112
+ end
113
+
114
+ assert_equal [], Resque.workers
115
+ end
116
+
117
+ test "removes worker with stringified id" do
118
+ @worker.work(0) do
119
+ worker_id = Resque.workers[0].to_s
120
+ Resque.remove_worker(worker_id)
121
+ assert_equal [], Resque.workers
122
+ end
123
+ end
124
+
125
+ test "records what it is working on" do
126
+ @worker.work(0) do
127
+ task = @worker.job
128
+ assert_equal({"args"=>[20, "/tmp"], "class"=>"SomeJob"}, task['payload'])
129
+ assert task['run_at']
130
+ assert_equal 'jobs', task['queue']
131
+ end
132
+ end
133
+
134
+ test "clears its status when not working on anything" do
135
+ @worker.work(0)
136
+ assert_equal Hash.new, @worker.job
137
+ end
138
+
139
+ test "knows when it is working" do
140
+ @worker.work(0) do
141
+ assert @worker.working?
142
+ end
143
+ end
144
+
145
+ test "knows when it is idle" do
146
+ @worker.work(0)
147
+ assert @worker.idle?
148
+ end
149
+
150
+ test "knows who is working" do
151
+ @worker.work(0) do
152
+ assert_equal [@worker], Resque.working
153
+ end
154
+ end
155
+
156
+ test "keeps track of how many jobs it has processed" do
157
+ Resque::Job.create(:jobs, BadJob)
158
+ Resque::Job.create(:jobs, BadJob)
159
+
160
+ 3.times do
161
+ job = @worker.reserve
162
+ @worker.process job
163
+ end
164
+ assert_equal 3, @worker.processed
165
+ end
166
+
167
+ test "keeps track of how many failures it has seen" do
168
+ Resque::Job.create(:jobs, BadJob)
169
+ Resque::Job.create(:jobs, BadJob)
170
+
171
+ 3.times do
172
+ job = @worker.reserve
173
+ @worker.process job
174
+ end
175
+ assert_equal 2, @worker.failed
176
+ end
177
+
178
+ test "stats are erased when the worker goes away" do
179
+ @worker.work(0)
180
+ assert_equal 0, @worker.processed
181
+ assert_equal 0, @worker.failed
182
+ end
183
+
184
+ test "knows when it started" do
185
+ time = Time.now
186
+ @worker.work(0) do
187
+ assert_equal time.to_s, @worker.started.to_s
188
+ end
189
+ end
190
+
191
+ test "knows whether it exists or not" do
192
+ @worker.work(0) do
193
+ assert Resque::Worker.exists?(@worker)
194
+ assert !Resque::Worker.exists?('blah-blah')
195
+ end
196
+ end
197
+
198
+ test "sets $0 while working" do
199
+ @worker.work(0) do
200
+ ver = Resque::Version
201
+ assert_equal "resque-#{ver}: Processing jobs since #{Time.now.to_i}", $0
202
+ end
203
+ end
204
+
205
+ test "can be found" do
206
+ @worker.work(0) do
207
+ found = Resque::Worker.find(@worker.to_s)
208
+ assert_equal @worker.to_s, found.to_s
209
+ assert found.working?
210
+ assert_equal @worker.job, found.job
211
+ end
212
+ end
213
+
214
+ test "doesn't find fakes" do
215
+ @worker.work(0) do
216
+ found = Resque::Worker.find('blah-blah')
217
+ assert_equal nil, found
218
+ end
219
+ end
220
+
221
+ test "cleans up dead worker info on start (crash recovery)" do
222
+ # first we fake out two dead workers
223
+ workerA = Resque::Worker.new(:jobs)
224
+ workerA.instance_variable_set(:@to_s, "#{`hostname`.chomp}:1:jobs")
225
+ workerA.register_worker
226
+
227
+ workerB = Resque::Worker.new(:high, :low)
228
+ workerB.instance_variable_set(:@to_s, "#{`hostname`.chomp}:2:high,low")
229
+ workerB.register_worker
230
+
231
+ assert_equal 2, Resque.workers.size
232
+
233
+ # then we prune them
234
+ @worker.work(0) do
235
+ assert_equal 1, Resque.workers.size
236
+ end
237
+ end
238
+
239
+ test "Processed jobs count" do
240
+ @worker.work(0)
241
+ assert_equal 1, Resque.info[:processed]
242
+ end
243
+ end
metadata ADDED
@@ -0,0 +1,172 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: grockit-resque
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.5.0
5
+ platform: ruby
6
+ authors:
7
+ - Grockit
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2010-02-18 00:00:00 -08:00
13
+ default_executable:
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: redis
17
+ type: :runtime
18
+ version_requirement:
19
+ version_requirements: !ruby/object:Gem::Requirement
20
+ requirements:
21
+ - - ">="
22
+ - !ruby/object:Gem::Version
23
+ version: "0"
24
+ version:
25
+ - !ruby/object:Gem::Dependency
26
+ name: redis-namespace
27
+ type: :runtime
28
+ version_requirement:
29
+ version_requirements: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: "0"
34
+ version:
35
+ - !ruby/object:Gem::Dependency
36
+ name: vegas
37
+ type: :runtime
38
+ version_requirement:
39
+ version_requirements: !ruby/object:Gem::Requirement
40
+ requirements:
41
+ - - ">="
42
+ - !ruby/object:Gem::Version
43
+ version: 0.1.2
44
+ version:
45
+ - !ruby/object:Gem::Dependency
46
+ name: sinatra
47
+ type: :runtime
48
+ version_requirement:
49
+ version_requirements: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - ">="
52
+ - !ruby/object:Gem::Version
53
+ version: 0.9.2
54
+ version:
55
+ - !ruby/object:Gem::Dependency
56
+ name: jeweler
57
+ type: :development
58
+ version_requirement:
59
+ version_requirements: !ruby/object:Gem::Requirement
60
+ requirements:
61
+ - - ">="
62
+ - !ruby/object:Gem::Version
63
+ version: "0"
64
+ version:
65
+ description: ""
66
+ email: mmol@grockit.com
67
+ executables:
68
+ - resque
69
+ - resque-web
70
+ extensions: []
71
+
72
+ extra_rdoc_files:
73
+ - LICENSE
74
+ - README.markdown
75
+ files:
76
+ - .gitignore
77
+ - .kick
78
+ - CONTRIBUTORS
79
+ - HISTORY.md
80
+ - LICENSE
81
+ - README.markdown
82
+ - Rakefile
83
+ - bin/resque
84
+ - bin/resque-web
85
+ - config.ru
86
+ - deps.rip
87
+ - examples/async_helper.rb
88
+ - examples/demo/README.markdown
89
+ - examples/demo/Rakefile
90
+ - examples/demo/app.rb
91
+ - examples/demo/config.ru
92
+ - examples/demo/job.rb
93
+ - examples/god/resque.god
94
+ - examples/god/stale.god
95
+ - examples/instance.rb
96
+ - examples/simple.rb
97
+ - init.rb
98
+ - lib/resque.rb
99
+ - lib/resque/errors.rb
100
+ - lib/resque/failure.rb
101
+ - lib/resque/failure/base.rb
102
+ - lib/resque/failure/hoptoad.rb
103
+ - lib/resque/failure/multiple.rb
104
+ - lib/resque/failure/redis.rb
105
+ - lib/resque/helpers.rb
106
+ - lib/resque/job.rb
107
+ - lib/resque/server.rb
108
+ - lib/resque/server/public/idle.png
109
+ - lib/resque/server/public/jquery-1.3.2.min.js
110
+ - lib/resque/server/public/jquery.relatize_date.js
111
+ - lib/resque/server/public/poll.png
112
+ - lib/resque/server/public/ranger.js
113
+ - lib/resque/server/public/reset.css
114
+ - lib/resque/server/public/style.css
115
+ - lib/resque/server/public/working.png
116
+ - lib/resque/server/views/error.erb
117
+ - lib/resque/server/views/failed.erb
118
+ - lib/resque/server/views/key.erb
119
+ - lib/resque/server/views/layout.erb
120
+ - lib/resque/server/views/next_more.erb
121
+ - lib/resque/server/views/overview.erb
122
+ - lib/resque/server/views/queues.erb
123
+ - lib/resque/server/views/stats.erb
124
+ - lib/resque/server/views/workers.erb
125
+ - lib/resque/server/views/working.erb
126
+ - lib/resque/stat.rb
127
+ - lib/resque/tasks.rb
128
+ - lib/resque/version.rb
129
+ - lib/resque/worker.rb
130
+ - tasks/redis.rake
131
+ - tasks/resque.rake
132
+ - test/redis-test.conf
133
+ - test/resque_test.rb
134
+ - test/test_helper.rb
135
+ - test/worker_test.rb
136
+ has_rdoc: true
137
+ homepage: http://github.com/grockit/resque
138
+ licenses: []
139
+
140
+ post_install_message:
141
+ rdoc_options:
142
+ - --charset=UTF-8
143
+ require_paths:
144
+ - lib
145
+ required_ruby_version: !ruby/object:Gem::Requirement
146
+ requirements:
147
+ - - ">="
148
+ - !ruby/object:Gem::Version
149
+ version: "0"
150
+ version:
151
+ required_rubygems_version: !ruby/object:Gem::Requirement
152
+ requirements:
153
+ - - ">="
154
+ - !ruby/object:Gem::Version
155
+ version: "0"
156
+ version:
157
+ requirements: []
158
+
159
+ rubyforge_project:
160
+ rubygems_version: 1.3.5
161
+ signing_key:
162
+ specification_version: 3
163
+ summary: ""
164
+ test_files:
165
+ - test/resque_test.rb
166
+ - test/test_helper.rb
167
+ - test/worker_test.rb
168
+ - examples/async_helper.rb
169
+ - examples/demo/app.rb
170
+ - examples/demo/job.rb
171
+ - examples/instance.rb
172
+ - examples/simple.rb