From ee69b841c0bc3eacebb818152b0c498a9510c54d Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Mon, 25 Jan 2010 02:06:46 -0800 Subject: [PATCH 01/28] mention namespace options in the readme --- README.markdown | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) diff --git a/README.markdown b/README.markdown index 66dc0e494..bf8615ad0 100644 --- a/README.markdown +++ b/README.markdown @@ -609,7 +609,7 @@ can re-use the existing connection. String: `Resque.redis = 'localhost:6379'` -Redis: `Redus.redis = $redis` +Redis: `Resque.redis = $redis` For our rails app we have a `config/initializers/resque.rb` file where we load `config/resque.yml` by hand and set the Redis information @@ -639,6 +639,25 @@ this way we can tell our Sinatra app about the config file: Now everyone is on the same page. +Namespaces +---------- + +If you're running multiple, separate instances of Resque you may want +to namespace the keyspaces so they do not overlap. This is not unlike +the approach taken by many memcached clients. + +This feature is provided by the [redis-namespace][rs] library, which +Resque uses by default to separate the keys it manages from other keys +in your Redis server. + +Simply use the `Resque.redis.namespace` accessor: + + Resque.redis.namespace = "resque:GitHub" + +We recommend sticking this in your initializer somewhere after Redis +is configured. + + Demo ---- @@ -734,3 +753,4 @@ Chris Wanstrath :: chris@ozmm.org :: @defunkt [1]: http://help.github.com/forking/ [2]: http://github.com/defunkt/resque/issues [sv]: http://semver.org/ +[rs]: http://github.com/defunkt/redis-namespace From 386216f2918ebe7edf64ee03978e9710b7928cae Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Mon, 25 Jan 2010 02:10:43 -0800 Subject: [PATCH 02/28] Fallback when unable to bind QUIT and USR1 for Windows and JRuby --- HISTORY.md | 4 ++++ lib/resque/worker.rb | 6 +++++- 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index d256c1336..3993cdd66 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,3 +1,7 @@ +## 1.4.0 (2010-??-??) + +* Fallback when unable to bind QUIT and USR1 for Windows and JRuby. + ## 1.3.1 (2010-01-11) * Vegas bugfix: Don't error without a config diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index d7af2bce3..e52886306 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -221,10 +221,14 @@ def enable_gc_optimizations def register_signal_handlers trap('TERM') { shutdown! } trap('INT') { shutdown! } - unless defined? JRUBY_VERSION + + begin trap('QUIT') { shutdown } trap('USR1') { kill_child } + rescue ArgumentError + warn "Signals QUIT and USR1 not supported." end + log! "Registered signals" end From 95e760ef3d0232475a74a12315079263b04abad6 Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Mon, 25 Jan 2010 09:49:35 -0800 Subject: [PATCH 03/28] IronyRuby doesn't support Kernel.fork --- HISTORY.md | 1 + lib/resque/worker.rb | 7 ++++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index 3993cdd66..0f93dd714 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,6 +1,7 @@ ## 1.4.0 (2010-??-??) * Fallback when unable to bind QUIT and USR1 for Windows and JRuby. +* Fallback when no `Kernel.fork` is provided (for IronRuby). ## 1.3.1 (2010-01-11) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index e52886306..1935794c5 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -189,7 +189,12 @@ def fork return if @cant_fork begin - Kernel.fork + # IronRuby doesn't support `Kernel.fork` yet + if Kernel.respond_to?(:fork) + Kernel.fork + else + raise NotImplementedError + end rescue NotImplementedError @cant_fork = true nil From 19364b9b2170fc5afd003bdd83a8c9f866171669 Mon Sep 17 00:00:00 2001 From: gravis Date: Thu, 4 Feb 2010 22:41:58 +0800 Subject: [PATCH 04/28] Round tabs in firefox too (not only Safari/Webkit) --- lib/resque/server/public/style.css | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/resque/server/public/style.css b/lib/resque/server/public/style.css index f71e74efb..195e813b0 100644 --- a/lib/resque/server/public/style.css +++ b/lib/resque/server/public/style.css @@ -4,7 +4,7 @@ body { padding:0; margin:0; } .header { background:#000; padding:8px 5% 0 5%; border-bottom:1px solid #444;border-bottom:5px solid #ce1212;} .header h1 { color:#333; font-size:90%; font-weight:bold; margin-bottom:6px;} .header ul li { display:inline;} -.header ul li a { color:#fff; text-decoration:none; margin-right:10px; display:inline-block; padding:8px; -webkit-border-top-right-radius:6px; -webkit-border-top-left-radius:6px; } +.header ul li a { color:#fff; text-decoration:none; margin-right:10px; display:inline-block; padding:8px; -webkit-border-top-right-radius:6px; -webkit-border-top-left-radius:6px; -moz-border-radius-topleft:6px; -moz-border-radius-topright:6px; } .header ul li a:hover { background:#333;} .header ul li.current a { background:#ce1212; font-weight:bold; color:#fff;} @@ -72,4 +72,4 @@ body { padding:0; margin:0; } #main p.pagination a.less { float:left;} #main p.pagination a.more { float:right;} -#main form.clear-failed {float:right; margin-top:-10px;} \ No newline at end of file +#main form.clear-failed {float:right; margin-top:-10px;} From a4047095deb39f49b6b38f89d87f9157e2448492 Mon Sep 17 00:00:00 2001 From: Matt Duncan Date: Sun, 31 Jan 2010 03:09:31 +0800 Subject: [PATCH 05/28] Fix typo and cleanup docs for Worker#work --- lib/resque/worker.rb | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index 1935794c5..d339c2fa4 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -92,14 +92,14 @@ def validate_queues # # The following events occur during a worker's life cycle: # - # 1. startup: Signals are registered, dead workers are pruned, - # and this worker is registered. - # 2. work loop: Jobs are pulled from a queue and processed - # 3. teardown: This worker is unregistered. + # 1. Startup: Signals are registered, dead workers are pruned, + # and this worker is registered. + # 2. Work loop: Jobs are pulled from a queue and processed. + # 3. Teardown: This worker is unregistered. # - # Can be passed an integered representing the polling - # frequency. The default is 5 seconds, but for a semi-active site - # you may want to use a smaller value. + # Can be passed an integer representing the polling frequency. + # The default is 5 seconds, but for a semi-active site you may + # want to use a smaller value. # # Also accepts a block which will be passed the job as soon as it # has completed processing. Useful for testing. From 565b733431c98664ea4c588edc90eb3dae395f46 Mon Sep 17 00:00:00 2001 From: Matt Duncan Date: Sun, 31 Jan 2010 06:39:15 +0800 Subject: [PATCH 06/28] Fixing typo in Worker#prune_dead_workers docs --- lib/resque/worker.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index d339c2fa4..669414a4e 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -269,7 +269,7 @@ def kill_child # # This is a form of garbage collection. If a server is killed by a # hard shutdown, power failure, or something else beyond our - # control, the Resque workers will not die gracefully and therefor + # control, the Resque workers will not die gracefully and therefore # will leave stale state information in Redis. # # By checking the current Redis state against the actual From 2e3efdd00b7329c57b39ddb1ea4306c3f4483371 Mon Sep 17 00:00:00 2001 From: Matt Duncan Date: Sun, 31 Jan 2010 06:51:11 +0800 Subject: [PATCH 07/28] Cutting down system calls in Worker#prune_dead_workers --- lib/resque/worker.rb | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index 669414a4e..f4417530e 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -275,10 +275,12 @@ def kill_child # By checking the current Redis state against the actual # environment, we can determine if Redis is old and clean it up a bit. def prune_dead_workers - Worker.all.each do |worker| + all_workers = Worker.all + known_workers = worker_pids unless all_workers.empty? + all_workers.each do |worker| host, pid, queues = worker.id.split(':') next unless host == hostname - next if worker_pids.include?(pid) + next if known_workers.include?(pid) log! "Pruning dead worker: #{worker}" worker.unregister_worker end From 18e4e9a7db612bee768ddb5d256a70164aa90877 Mon Sep 17 00:00:00 2001 From: Masatomo Nakano Date: Tue, 2 Feb 2010 07:53:47 +0800 Subject: [PATCH 08/28] enable switching db-id in an redis server from config --- lib/resque.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/resque.rb b/lib/resque.rb index 01784a778..26888d561 100644 --- a/lib/resque.rb +++ b/lib/resque.rb @@ -24,8 +24,8 @@ module Resque def redis=(server) case server when String - host, port = server.split(':') - redis = Redis.new(:host => host, :port => port, :thread_safe => true) + host, port, dbid = server.split(':') + redis = Redis.new(:host => host, :port => port, :thread_safe => true, :db=>dbid || 0) @redis = Redis::Namespace.new(:resque, :redis => redis) when Redis @redis = Redis::Namespace.new(:resque, :redis => server) From de04a9c37e5f3feb6f4727973ad3ad24406eb358 Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Tue, 9 Feb 2010 00:25:21 -0700 Subject: [PATCH 09/28] redis-rb will handle the `to_i` for us --- lib/resque.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/resque.rb b/lib/resque.rb index 26888d561..5165fbb18 100644 --- a/lib/resque.rb +++ b/lib/resque.rb @@ -25,7 +25,7 @@ def redis=(server) case server when String host, port, dbid = server.split(':') - redis = Redis.new(:host => host, :port => port, :thread_safe => true, :db=>dbid || 0) + redis = Redis.new(:host => host, :port => port, :thread_safe => true, :db=>dbid) @redis = Redis::Namespace.new(:resque, :redis => redis) when Redis @redis = Redis::Namespace.new(:resque, :redis => server) From eb7f3380b4f6c974c2def28eec0639bcdf4f4676 Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Mon, 8 Feb 2010 23:34:48 -0800 Subject: [PATCH 10/28] update history --- HISTORY.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/HISTORY.md b/HISTORY.md index 0f93dd714..24a9b887a 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -2,6 +2,9 @@ * Fallback when unable to bind QUIT and USR1 for Windows and JRuby. * Fallback when no `Kernel.fork` is provided (for IronRuby). +* Web: Rounded corners in Firefox +* Cut down system calls in `Worker#prune_dead_workers` +* Enable switching DB in a Redis server from config ## 1.3.1 (2010-01-11) From 1d033dc2417866ea2fe80786be5051886a2d95e5 Mon Sep 17 00:00:00 2001 From: Matt Palmer Date: Tue, 2 Feb 2010 13:42:10 +0800 Subject: [PATCH 11/28] Handle USR2/CONT signals, to pause and unpause workers --- HISTORY.md | 1 + README.markdown | 6 ++++++ lib/resque/worker.rb | 23 ++++++++++++++++++++--- 3 files changed, 27 insertions(+), 3 deletions(-) diff --git a/HISTORY.md b/HISTORY.md index 0f93dd714..f973ce8b3 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -2,6 +2,7 @@ * Fallback when unable to bind QUIT and USR1 for Windows and JRuby. * Fallback when no `Kernel.fork` is provided (for IronRuby). +* Support USR2 and CONT to stop and start job processing. ## 1.3.1 (2010-01-11) diff --git a/README.markdown b/README.markdown index bf8615ad0..dd3414a3e 100644 --- a/README.markdown +++ b/README.markdown @@ -365,6 +365,8 @@ Resque workers respond to a few different signals: * `QUIT` - Wait for child to finish processing then exit * `TERM` / `INT` - Immediately kill child then exit * `USR1` - Immediately kill child but don't exit +* `USR2` - Don't start to process any new jobs +* `CONT` - Start to process new jobs again after a USR2 If you want to gracefully shutdown a Resque worker, use `QUIT`. @@ -374,6 +376,10 @@ Resque assumes the parent process is in a bad state and shuts down. If you want to kill a stale or stuck child and shutdown, use `TERM` +If you want to stop processing jobs, but want to leave the worker running +(for example, to temporarily alleviate load), use `USR2` to stop processing, +then `CONT` to start it again. + ### Mysql::Error: MySQL server has gone away If your workers remain idle for too long they may lose their MySQL diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index f4417530e..c8fc9f163 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -110,7 +110,7 @@ def work(interval = 5, &block) loop do break if @shutdown - if job = reserve + if not @paused and job = reserve log "got: #{job.inspect}" if @child = fork @@ -131,7 +131,7 @@ def work(interval = 5, &block) else break if interval.to_i == 0 log! "Sleeping for #{interval.to_i}" - $0 = "resque: Waiting for #{@queues.join(',')}" + $0 = @paused ? "resque: Paused" : "resque: Waiting for #{@queues.join(',')}" sleep interval.to_i end end @@ -223,6 +223,8 @@ def enable_gc_optimizations # INT: Shutdown immediately, stop processing jobs. # QUIT: Shutdown after the current job has finished processing. # USR1: Kill the forked child immediately, continue processing jobs. + # USR2: Don't process any new jobs + # CONT: Start processing jobs again after a USR2 def register_signal_handlers trap('TERM') { shutdown! } trap('INT') { shutdown! } @@ -230,8 +232,10 @@ def register_signal_handlers begin trap('QUIT') { shutdown } trap('USR1') { kill_child } + trap('USR2') { pause_processing } + trap('CONT') { unpause_processing } rescue ArgumentError - warn "Signals QUIT and USR1 not supported." + warn "Signals QUIT, USR1, USR2, and/or CONT not supported." end log! "Registered signals" @@ -264,6 +268,19 @@ def kill_child end end + # Stop processing jobs after the current one has completed (if we're + # currently running one). + def pause_processing + log "USR2 received; pausing job processing" + @paused = true + end + + # Start processing jobs again after a pause + def unpause_processing + log "CONT received; resuming job processing" + @paused = false + end + # Looks for any workers which should be running on this server # and, if they're not, removes them from Redis. # From 565e076933ecead63623924e82ad1abf7fe1ddde Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Tue, 9 Feb 2010 00:03:58 -0800 Subject: [PATCH 12/28] 2spaces --- lib/resque/worker.rb | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index c8fc9f163..072fd274e 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -271,14 +271,14 @@ def kill_child # Stop processing jobs after the current one has completed (if we're # currently running one). def pause_processing - log "USR2 received; pausing job processing" - @paused = true + log "USR2 received; pausing job processing" + @paused = true end - + # Start processing jobs again after a pause def unpause_processing - log "CONT received; resuming job processing" - @paused = false + log "CONT received; resuming job processing" + @paused = false end # Looks for any workers which should be running on this server From ca74af006d24cf3b8f22001b07d1b451088c414d Mon Sep 17 00:00:00 2001 From: Christos Trochalakis Date: Tue, 2 Feb 2010 23:48:58 +0800 Subject: [PATCH 13/28] Worker#unregister_worker shouldn't call done_working unregister_worker faulty increments Stat[:processed] by calling done_working --- lib/resque/worker.rb | 2 -- test/worker_test.rb | 7 +++++++ 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index 072fd274e..3c0db6955 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -312,8 +312,6 @@ def register_worker # Unregisters ourself as a worker. Useful when shutting down. def unregister_worker - done_working - redis.srem(:workers, self) redis.del("worker:#{self}:started") diff --git a/test/worker_test.rb b/test/worker_test.rb index 91af47ad6..d83b5a6e0 100644 --- a/test/worker_test.rb +++ b/test/worker_test.rb @@ -226,4 +226,11 @@ assert_equal 1, Resque.workers.size end end + + test "Pprocessed jobs count" do + @worker.work(0) + assert_equal 1, Resque.info[:processed] + end + + end From b4fabda6cea819febd47b47b57e9960daa992cf7 Mon Sep 17 00:00:00 2001 From: Roman Heinrich Date: Thu, 28 Jan 2010 18:38:13 +0800 Subject: [PATCH 14/28] installing redis with PREFIX works now --- tasks/redis.rake | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/tasks/redis.rake b/tasks/redis.rake index cc306366e..2385d59ca 100644 --- a/tasks/redis.rake +++ b/tasks/redis.rake @@ -29,7 +29,8 @@ class RedisRunner def self.start puts 'Detach with Ctrl+\ Re-attach with rake redis:attach' sleep 1 - exec "dtach -A #{dtach_socket} redis-server #{redisconfdir}" + command = "dtach -A #{dtach_socket} redis-server #{redisconfdir}" + sh command end def self.attach @@ -80,8 +81,9 @@ namespace :redis do puts "Installed redis-benchmark, redis-cli and redis-server to #{bin_dir}" ENV['PREFIX'] and conf_dir = "#{ENV['PREFIX']}/etc" or conf_dir = '/etc' - unless File.exists?("#{conf_dir}") - sh "cp /tmp/redis/redis.conf #{conf_dir}" + unless File.exists?("#{conf_dir}/redis.conf") + sh "mkdir #{conf_dir}" unless File.exists?("#{conf_dir}") + sh "cp /tmp/redis/redis.conf #{conf_dir}/redis.conf" puts "Installed redis.conf to #{conf_dir} \n You should look at this file!" end end From b1504933f61fae3705d8220ad5fa2f934ad57239 Mon Sep 17 00:00:00 2001 From: Roman Heinrich Date: Thu, 28 Jan 2010 18:39:16 +0800 Subject: [PATCH 15/28] example for a failing job, RESQUE *assumes* failure :) --- examples/demo/app.rb | 11 +++++++++++ examples/demo/job.rb | 10 ++++++++++ 2 files changed, 21 insertions(+) diff --git a/examples/demo/app.rb b/examples/demo/app.rb index 36f9fc3ec..feeffc49b 100644 --- a/examples/demo/app.rb +++ b/examples/demo/app.rb @@ -15,6 +15,12 @@ class App < Sinatra::Base out << '' out << '  View Resque' out << '' + + out << "
" + out << '' + out << '  View Resque' + out << '
' + out << "" out end @@ -23,5 +29,10 @@ class App < Sinatra::Base Resque.enqueue(Job, params) redirect "/" end + + post '/failing' do + Resque.enqueue(FailingJob, params) + redirect "/" + end end end diff --git a/examples/demo/job.rb b/examples/demo/job.rb index 3742c88d4..357d94394 100644 --- a/examples/demo/job.rb +++ b/examples/demo/job.rb @@ -9,4 +9,14 @@ def self.perform(params) puts "Processed a job!" end end + + module FailingJob + @queue = :failing + + def self.perform(params) + sleep 1 + raise 'not processable!' + puts "Processed a job!" + end + end end From a76a8a2423de334bcf6d3c8f011ea251c288516b Mon Sep 17 00:00:00 2001 From: Roman Heinrich Date: Thu, 28 Jan 2010 18:48:06 +0800 Subject: [PATCH 16/28] button more descriptive --- examples/demo/app.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/demo/app.rb b/examples/demo/app.rb index feeffc49b..db7f48745 100644 --- a/examples/demo/app.rb +++ b/examples/demo/app.rb @@ -17,7 +17,7 @@ class App < Sinatra::Base out << '' out << "
" - out << '' + out << '' out << '  View Resque' out << '
' From 66f78133a97b6e215e959ea8cc5ef502bf5ee636 Mon Sep 17 00:00:00 2001 From: Christos Trochalakis Date: Tue, 2 Feb 2010 17:48:58 +0200 Subject: [PATCH 17/28] Worker#unregister_worker shouldn't call done_working unregister_worker faulty increments Stat[:processed] by calling done_working --- lib/resque/worker.rb | 2 -- test/worker_test.rb | 5 +++++ 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/lib/resque/worker.rb b/lib/resque/worker.rb index 072fd274e..3c0db6955 100644 --- a/lib/resque/worker.rb +++ b/lib/resque/worker.rb @@ -312,8 +312,6 @@ def register_worker # Unregisters ourself as a worker. Useful when shutting down. def unregister_worker - done_working - redis.srem(:workers, self) redis.del("worker:#{self}:started") diff --git a/test/worker_test.rb b/test/worker_test.rb index 91af47ad6..8a5097be3 100644 --- a/test/worker_test.rb +++ b/test/worker_test.rb @@ -226,4 +226,9 @@ assert_equal 1, Resque.workers.size end end + + test "Processed jobs count" do + @worker.work(0) + assert_equal 1, Resque.info[:processed] + end end From 32a6e6d0f28ae23c193b77eb5c12b940a6aaadc8 Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Tue, 9 Feb 2010 00:08:31 -0800 Subject: [PATCH 18/28] update history --- HISTORY.md | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/HISTORY.md b/HISTORY.md index 71debaf81..5e29e5897 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -2,13 +2,12 @@ * Fallback when unable to bind QUIT and USR1 for Windows and JRuby. * Fallback when no `Kernel.fork` is provided (for IronRuby). -<<<<<<< HEAD * Web: Rounded corners in Firefox * Cut down system calls in `Worker#prune_dead_workers` * Enable switching DB in a Redis server from config -======= * Support USR2 and CONT to stop and start job processing. ->>>>>>> 1d033dc2417866ea2fe80786be5051886a2d95e5 +* Web: Add example failing job +* Bugfix: `Worker#unregister_worker` shouldn't call `done_working` ## 1.3.1 (2010-01-11) From 0c4635bd7ab0f4c1105696c3ffa0e9b3522b2627 Mon Sep 17 00:00:00 2001 From: Daniel Ceballos Date: Wed, 3 Feb 2010 08:16:50 +0800 Subject: [PATCH 19/28] Adding missing remove_worker for resque command line tool --- lib/resque.rb | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/lib/resque.rb b/lib/resque.rb index 5165fbb18..79fb80278 100644 --- a/lib/resque.rb +++ b/lib/resque.rb @@ -160,6 +160,12 @@ def working Worker.working end + # A shortcut to unregister_worker + # useful for command line tool + def remove_worker(worker_id) + worker = Resque::Worker.find(worker_id) + worker.unregister_worker + end # # stats From 39b99ff32fc97c711963e100e9c99b035960aaea Mon Sep 17 00:00:00 2001 From: Daniel Ceballos Date: Wed, 3 Feb 2010 08:21:15 +0800 Subject: [PATCH 20/28] Adding missing remove_worker for resque command line tool --- lib/resque.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/resque.rb b/lib/resque.rb index 79fb80278..75767547d 100644 --- a/lib/resque.rb +++ b/lib/resque.rb @@ -163,7 +163,7 @@ def working # A shortcut to unregister_worker # useful for command line tool def remove_worker(worker_id) - worker = Resque::Worker.find(worker_id) + worker = Worker.find(worker_id) worker.unregister_worker end From 8774b9908bdbc2fec311dd9a6367686d4ca7ad96 Mon Sep 17 00:00:00 2001 From: Daniel Ceballos Date: Wed, 10 Feb 2010 03:23:42 +0800 Subject: [PATCH 21/28] adding test for Resque.remove_worker --- lib/resque.rb | 2 +- test/worker_test.rb | 8 ++++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/lib/resque.rb b/lib/resque.rb index 75767547d..79fb80278 100644 --- a/lib/resque.rb +++ b/lib/resque.rb @@ -163,7 +163,7 @@ def working # A shortcut to unregister_worker # useful for command line tool def remove_worker(worker_id) - worker = Worker.find(worker_id) + worker = Resque::Worker.find(worker_id) worker.unregister_worker end diff --git a/test/worker_test.rb b/test/worker_test.rb index 8a5097be3..718b1011f 100644 --- a/test/worker_test.rb +++ b/test/worker_test.rb @@ -114,6 +114,14 @@ assert_equal [], Resque.workers end + test "removes worker with stringified id" do + @worker.work(0) do + worker_id = Resque.workers[0].to_s + Resque.remove_worker(worker_id) + assert_equal [], Resque.workers + end + end + test "records what it is working on" do @worker.work(0) do task = @worker.job From 95bc4f1fe13306602f5d924e3b22dc9568c1693e Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Thu, 11 Feb 2010 02:35:04 -0800 Subject: [PATCH 22/28] Document `Resque.redis=` better --- lib/resque.rb | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/lib/resque.rb b/lib/resque.rb index 79fb80278..fa18df3fb 100644 --- a/lib/resque.rb +++ b/lib/resque.rb @@ -20,12 +20,16 @@ module Resque include Helpers extend self - # Accepts a 'hostname:port' string or a Redis server. + # Accepts: + # 1. A 'hostname:port' string + # 2. A 'hostname:port:db' string (to select the Redis db) + # 3. An instance of `Redis` def redis=(server) case server when String - host, port, dbid = server.split(':') - redis = Redis.new(:host => host, :port => port, :thread_safe => true, :db=>dbid) + host, port, db = server.split(':') + redis = Redis.new(:host => host, :port => port, + :thread_safe => true, :db => db) @redis = Redis::Namespace.new(:resque, :redis => redis) when Redis @redis = Redis::Namespace.new(:resque, :redis => server) From 6947afe90b714726a8785dc28729b7a3c2cb2b69 Mon Sep 17 00:00:00 2001 From: Mike Mangino Date: Wed, 10 Feb 2010 07:47:43 +0800 Subject: [PATCH 23/28] Update to use new hoptoad api --- lib/resque/failure/hoptoad.rb | 72 ++++++++++++++++++++++++++--------- 1 file changed, 53 insertions(+), 19 deletions(-) diff --git a/lib/resque/failure/hoptoad.rb b/lib/resque/failure/hoptoad.rb index 7c8323c1f..754e0d80f 100644 --- a/lib/resque/failure/hoptoad.rb +++ b/lib/resque/failure/hoptoad.rb @@ -1,4 +1,5 @@ require 'net/http' +require 'builder' module Resque module Failure @@ -12,6 +13,9 @@ module Failure # config.subdomain = 'your_hoptoad_subdomain' # end class Hoptoad < Base + #from the hoptoad plugin + INPUT_FORMAT = %r{^([^:]+):(\d+)(?::in `([^']+)')?$}.freeze + class << self attr_accessor :secure, :api_key, :subdomain end @@ -31,38 +35,25 @@ def self.configure Resque::Failure.backend = self end - def save - data = { - :api_key => api_key, - :error_class => exception.class.name, - :error_message => "#{exception.class.name}: #{exception.message}", - :backtrace => exception.backtrace, - :environment => {}, - :session => {}, - :request => { - :params => payload.merge(:worker => worker.to_s, :queue => queue.to_s) - } - } + - send_to_hoptoad(:notice => data) - end - - def send_to_hoptoad(data) + def save http = use_ssl? ? :https : :http - url = URI.parse("#{http}://hoptoadapp.com/notices/") + url = URI.parse("#{http}://hoptoadapp.com/notifier_api/v2/notices") http = Net::HTTP.new(url.host, url.port) headers = { - 'Content-type' => 'application/json', + 'Content-type' => 'text/xml', 'Accept' => 'text/xml, application/xml' } http.read_timeout = 5 # seconds http.open_timeout = 2 # seconds + http.use_ssl = use_ssl? begin - response = http.post(url.path, Resque.encode(data), headers) + response = http.post(url.path, xml, headers) rescue TimeoutError => e log "Timeout while contacting the Hoptoad server." end @@ -75,6 +66,49 @@ def send_to_hoptoad(data) log "Hoptoad Failure: #{response.class}\n#{body}" end end + + def xml + x = Builder::XmlMarkup.new + x.instruct! + x.notice :version=>"2.0" do + x.tag! "api-key", api_key + x.notifier do + x.name "Resqueue" + x.version "0.1" + x.url "http://github.com/defunkt/resque" + end + x.error do + x.class exception.class.name + x.message "#{exception.class.name}: #{exception.message}" + x.backtrace do + fill_in_backtrace_lines(x) + end + end + x.request do + x.url queue.to_s + x.component worker.to_s + x.params do + x.var :key=>"payload_class" do + x.text! payload["class"].to_s + end + x.var :key=>"payload_args" do + x.text! payload["args"].to_s + end + end + end + x.tag!("server-environment") do + x.tag!("environment-name",RAILS_ENV) + end + + end + end + + def fill_in_backtrace_lines(x) + exception.backtrace.each do |unparsed_line| + _, file, number, method = unparsed_line.match(INPUT_FORMAT).to_a + x.line :file=>file,:number=>number + end + end def use_ssl? self.class.secure From 3dfe1f55f4edca2ce840fbc1a56c8e54813e6fcb Mon Sep 17 00:00:00 2001 From: Mike Mangino Date: Wed, 10 Feb 2010 08:10:03 +0800 Subject: [PATCH 24/28] Add a backend to allow multiple error backends --- lib/resque/failure/multiple.rb | 44 ++++++++++++++++++++++++++++++++++ 1 file changed, 44 insertions(+) create mode 100644 lib/resque/failure/multiple.rb diff --git a/lib/resque/failure/multiple.rb b/lib/resque/failure/multiple.rb new file mode 100644 index 000000000..dccabd1c2 --- /dev/null +++ b/lib/resque/failure/multiple.rb @@ -0,0 +1,44 @@ +module Resque + module Failure + # A Failure backend that uses multiple backends + # delegates all queries to the first backend + class Multiple < Base + + class << self + attr_accessor :classes + end + + def self.configure + yield self + Resque::Failure.backend = self + end + + def initialize(*args) + @backends = self.class.backend_classes.map {|klass| klass.new(*args)} + end + def save + @backends.each(&:save) + end + + # The number of failures. + def self.count + classes.first.count + end + + # Returns a paginated array of failure objects. + def self.all(start = 0, count = 1) + classes.first.all(start,count) + end + + # A URL where someone can go to view failures. + def self.url + classes.first.url + end + + # Clear all failure objects + def self.clear + classes.first.clear + end + end + end +end \ No newline at end of file From ba477f3c3a30e0f2decca890516368c071f1a62c Mon Sep 17 00:00:00 2001 From: Mike Mangino Date: Wed, 10 Feb 2010 08:15:37 +0800 Subject: [PATCH 25/28] Fix typo in multiple backend --- lib/resque/failure/multiple.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/resque/failure/multiple.rb b/lib/resque/failure/multiple.rb index dccabd1c2..98bacc0dc 100644 --- a/lib/resque/failure/multiple.rb +++ b/lib/resque/failure/multiple.rb @@ -14,7 +14,7 @@ def self.configure end def initialize(*args) - @backends = self.class.backend_classes.map {|klass| klass.new(*args)} + @backends = self.class.classes.map {|klass| klass.new(*args)} end def save @backends.each(&:save) From 992057edca312d9f8a94f2dbbc98d1a5164df311 Mon Sep 17 00:00:00 2001 From: Mike Mangino Date: Wed, 10 Feb 2010 21:45:57 +0800 Subject: [PATCH 26/28] fix god config to restart resque instead of killing env --- examples/god/resque.god | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/examples/god/resque.god b/examples/god/resque.god index ea1ce6788..d28c90088 100644 --- a/examples/god/resque.god +++ b/examples/god/resque.god @@ -7,7 +7,8 @@ num_workers.times do |num| w.name = "resque-#{num}" w.group = 'resque' w.interval = 30.seconds - w.start = "env QUEUE=critical,high,low /usr/bin/rake -f #{rails_root}/Rakefile #{rails_env} resque:work" + w.env = {"QUEUE"=>"critical,high,low", "RAILS_ENV"=>rails_env} + w.start = "/usr/bin/rake -f #{rails_root}/Rakefile environment resque:work" w.uid = 'git' w.gid = 'git' From 7a03c6823b5c5046ffbd5f32dd0a9bd062bb6cf4 Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Thu, 11 Feb 2010 02:45:37 -0800 Subject: [PATCH 27/28] update history --- HISTORY.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/HISTORY.md b/HISTORY.md index 5e29e5897..12483c964 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -8,6 +8,9 @@ * Support USR2 and CONT to stop and start job processing. * Web: Add example failing job * Bugfix: `Worker#unregister_worker` shouldn't call `done_working` +* Bugfix: Example god config now restarts Resque properly. +* Multiple failure backends now permitted. +* Hoptoad failure backend updated to new API ## 1.3.1 (2010-01-11) From 4c43b04e2a387352f15c504b8fedb6b8deecd43a Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Thu, 11 Feb 2010 02:48:32 -0800 Subject: [PATCH 28/28] 1.4.0 --- HISTORY.md | 2 +- lib/resque/version.rb | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/HISTORY.md b/HISTORY.md index 12483c964..2e57f7de4 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,4 +1,4 @@ -## 1.4.0 (2010-??-??) +## 1.4.0 (2010-02-11) * Fallback when unable to bind QUIT and USR1 for Windows and JRuby. * Fallback when no `Kernel.fork` is provided (for IronRuby). diff --git a/lib/resque/version.rb b/lib/resque/version.rb index 0eb1b512d..a57291409 100644 --- a/lib/resque/version.rb +++ b/lib/resque/version.rb @@ -1,3 +1,3 @@ module Resque - Version = '1.3.1' + Version = '1.4.0' end