micro_q 0.9.2 → 0.9.4
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 +4 -4
- data/.rspec +1 -1
- data/README.md +48 -0
- data/bin/microq +11 -0
- data/lib/micro_q/cli.rb +60 -0
- data/lib/micro_q/config.rb +15 -0
- data/lib/micro_q/fetchers/sqs.rb +37 -0
- data/lib/micro_q/inspect.rb +17 -0
- data/lib/micro_q/manager/default.rb +9 -1
- data/lib/micro_q/queue/sqs.rb +85 -0
- data/lib/micro_q/queue.rb +1 -0
- data/lib/micro_q/sqs_client.rb +47 -0
- data/lib/micro_q/version.rb +1 -1
- data/lib/micro_q.rb +7 -1
- data/micro_q.gemspec +3 -0
- data/spec/helpers/queues_examples.rb +1 -1
- data/spec/lib/config_spec.rb +47 -0
- data/spec/lib/fetchers/sqs_spec.rb +81 -0
- data/spec/lib/manager/default_spec.rb +69 -0
- data/spec/lib/queue/redis_spec.rb +0 -5
- data/spec/lib/queue/sqs_spec.rb +206 -0
- data/spec/lib/sqs_client_spec.rb +166 -0
- data/spec/spec_helper.rb +19 -5
- metadata +58 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f8736323665ab0facb37dfc92fd2463077cfe0f0
|
4
|
+
data.tar.gz: e7f7022cd9c3c74efbb68f68d85f49270436ca8c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: aeeea9df0091afbb6593457b7664b36e21edd7800f1e5dc3cd6d71b6a92ecba6c9e7540413b75d18bf89020b6f65efa033097de0f1372e5ac68ff6bd604d4161
|
7
|
+
data.tar.gz: e2ebf0f5f4c4e116c432979276e0d0c436fad69cbc6f6b0475d7e240a0d3b46c824e4ae85c79cea797e8d9f2f06ac3976451dc88e3311152cd43ce29e5634735
|
data/.rspec
CHANGED
@@ -1,2 +1,2 @@
|
|
1
1
|
--color
|
2
|
-
--format
|
2
|
+
--format Fuubar
|
data/README.md
CHANGED
@@ -49,6 +49,9 @@ MyWorker.update_async(:user_id => user.id)
|
|
49
49
|
|
50
50
|
Safely using an ActiveRecord instance via the [Custom Loader](https://github.com/bnorton/micro_q/wiki/Loaders) API
|
51
51
|
```ruby
|
52
|
+
# config/initializers/micro_q
|
53
|
+
require 'micro_q/methods/active_record'
|
54
|
+
|
52
55
|
# app/models/user.rb
|
53
56
|
class User < Activerecord::Base
|
54
57
|
def update_social_data
|
@@ -63,6 +66,51 @@ def update
|
|
63
66
|
end
|
64
67
|
```
|
65
68
|
|
69
|
+
##Queues
|
70
|
+
By default the queue is an in-memory queue meaning that messages are shared per-process
|
71
|
+
and any unprocessed messages are saved to a file when shutdown occurs.
|
72
|
+
|
73
|
+
The **Redis queue** requires some configuration in your gemfile to keep the runtime dependencies to a minimum
|
74
|
+
```ruby
|
75
|
+
# Gemfile
|
76
|
+
gem 'redis'
|
77
|
+
gem 'micro_q'
|
78
|
+
|
79
|
+
# config/initializers/micro_q.rb
|
80
|
+
require 'redis'
|
81
|
+
require 'micro_q'
|
82
|
+
|
83
|
+
# when MicroQ starts simply use the redis queue
|
84
|
+
MicroQ.configure do |config|
|
85
|
+
config.queue = MicroQ::Queue::Redis
|
86
|
+
end
|
87
|
+
```
|
88
|
+
|
89
|
+
The **Amazon SQS (coming soon) queue** require some extra configuration in your gemfile.
|
90
|
+
```ruby
|
91
|
+
# Gemfile
|
92
|
+
gem 'aws-sdk'
|
93
|
+
gem 'micro_q'
|
94
|
+
|
95
|
+
# config/initializers/micro_q.rb
|
96
|
+
require 'aws-sdk'
|
97
|
+
require 'micro_q'
|
98
|
+
|
99
|
+
# when MicroQ starts simply use the sqs queue
|
100
|
+
# this will take care of all other switchover for the system
|
101
|
+
MicroQ.configure do |config|
|
102
|
+
config.queue = MicroQ::Queue::Sqs
|
103
|
+
config.aws = { :key => 'YOUR KEY', :secret => 'YOUR SECRET' }
|
104
|
+
end
|
105
|
+
|
106
|
+
**Note that when using the SQS Queue only the MicroQ's started via command-line will actually process messages**
|
107
|
+
|
108
|
+
# Then just use the queues in your workers
|
109
|
+
class SomeWorker
|
110
|
+
worker :queue => :critical
|
111
|
+
end
|
112
|
+
```
|
113
|
+
|
66
114
|
## Contributing
|
67
115
|
|
68
116
|
1. Fork it
|
data/bin/microq
ADDED
data/lib/micro_q/cli.rb
ADDED
@@ -0,0 +1,60 @@
|
|
1
|
+
require 'slop'
|
2
|
+
require 'micro_q'
|
3
|
+
|
4
|
+
module MicroQ
|
5
|
+
class CLI
|
6
|
+
def self.run
|
7
|
+
@cli ||= new
|
8
|
+
@cli.parse
|
9
|
+
@cli.verify!
|
10
|
+
@cli.setup
|
11
|
+
end
|
12
|
+
|
13
|
+
def parse
|
14
|
+
opts = Slop.parse do
|
15
|
+
banner 'Usage: microq [options]'
|
16
|
+
|
17
|
+
on 'r=', 'The path to the rails application'
|
18
|
+
on 'require=', 'The path to the rails application'
|
19
|
+
on 'w=', 'The number of worker threads'
|
20
|
+
on 'workers=', 'The number of worker threads'
|
21
|
+
end
|
22
|
+
|
23
|
+
@workers = opts[:workers] || opts[:w]
|
24
|
+
@require = opts[:require] || opts[:r]
|
25
|
+
end
|
26
|
+
|
27
|
+
def verify!
|
28
|
+
raise "Need a valid path to a rails application, you gave us #{@require}\n" unless /environment\.rb/ === @require || File.exist?("#{@require}/config/application.rb")
|
29
|
+
end
|
30
|
+
|
31
|
+
def setup
|
32
|
+
puts 'Requiring rails...'
|
33
|
+
require 'rails'
|
34
|
+
|
35
|
+
puts 'Requiring rails application...'
|
36
|
+
if File.directory?(@require)
|
37
|
+
require File.expand_path("#{@require}/config/environment.rb")
|
38
|
+
else
|
39
|
+
require @require
|
40
|
+
end
|
41
|
+
|
42
|
+
aws_keys = MicroQ.config.aws.try(:keys) || []
|
43
|
+
raise 'SQS mode requires an aws :key and :secret see https://github.com/bnorton/micro_q/wiki/Named-Queues' unless aws_keys.include?(:key) && aws_keys.include?(:secret)
|
44
|
+
|
45
|
+
MicroQ.configure do |config|
|
46
|
+
config.queue = MicroQ::Queue::Sqs # set workers after since this must set workers=0 internally
|
47
|
+
config.workers = @workers.to_i if @workers
|
48
|
+
config['worker_mode?'] = true
|
49
|
+
end
|
50
|
+
|
51
|
+
puts "Running micro_q in SQS mode with #{MicroQ.config.workers} workers... Hit ctl+c to stop...\n"
|
52
|
+
MicroQ.start
|
53
|
+
|
54
|
+
sleep
|
55
|
+
rescue Interrupt
|
56
|
+
puts 'Exiting via interrupt'
|
57
|
+
exit(1)
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
data/lib/micro_q/config.rb
CHANGED
@@ -13,11 +13,13 @@ module MicroQ
|
|
13
13
|
'workers' => 5,
|
14
14
|
'timeout' => 120,
|
15
15
|
'interval' => 5,
|
16
|
+
'env' => defined?(Rails) ? Rails.env : 'development',
|
16
17
|
'middleware' => Middleware::Chain.new,
|
17
18
|
'manager' => Manager::Default,
|
18
19
|
'worker' => Worker::Standard,
|
19
20
|
'queue' => Queue::Default,
|
20
21
|
'statistics' => Statistics::Default,
|
22
|
+
'aws' => {},
|
21
23
|
'redis_pool' => { :size => 15, :timeout => 1 },
|
22
24
|
'redis' => { :host => 'localhost', :port => 6379 }
|
23
25
|
}
|
@@ -31,6 +33,19 @@ module MicroQ
|
|
31
33
|
@data[key.to_s]
|
32
34
|
end
|
33
35
|
|
36
|
+
def queue=(q)
|
37
|
+
if q == Queue::Sqs
|
38
|
+
require 'aws-sdk'
|
39
|
+
|
40
|
+
@data['sqs?'] = true
|
41
|
+
@data['workers'] = 0
|
42
|
+
end
|
43
|
+
|
44
|
+
@data['queue'] = q
|
45
|
+
rescue LoadError
|
46
|
+
raise "Looks you need `gem 'aws-sdk'` in your Gemfile to use the SQS queue."
|
47
|
+
end
|
48
|
+
|
34
49
|
def method_missing(method, *args)
|
35
50
|
case method
|
36
51
|
when /(.+)=$/ then @data[$1] = args.first
|
@@ -0,0 +1,37 @@
|
|
1
|
+
module MicroQ
|
2
|
+
module Fetcher
|
3
|
+
class Sqs
|
4
|
+
include Celluloid
|
5
|
+
attr_reader :name
|
6
|
+
|
7
|
+
def initialize(name, manager)
|
8
|
+
@name = name.to_s
|
9
|
+
@manager = manager
|
10
|
+
end
|
11
|
+
|
12
|
+
def start
|
13
|
+
defer do
|
14
|
+
client.messages.tap do |messages|
|
15
|
+
@manager.receive_messages!(messages) if messages.any?
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
after(2) { start }
|
20
|
+
end
|
21
|
+
|
22
|
+
def add_message(message, time=nil)
|
23
|
+
message['run_at'] = time.to_f if time
|
24
|
+
|
25
|
+
defer do
|
26
|
+
client.messages_create(message)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
private
|
31
|
+
|
32
|
+
def client
|
33
|
+
@client ||= MicroQ::SqsClient.new(name)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module MicroQ
|
2
|
+
module Inspect
|
3
|
+
def self.included(base)
|
4
|
+
base.send(:include, InstanceMethods)
|
5
|
+
end
|
6
|
+
|
7
|
+
module InstanceMethods
|
8
|
+
def inspect
|
9
|
+
"#<#{self.class.name}: #{self.object_id}>"
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
['Worker::Standard', 'Queue::Default', 'Queue::Redis', 'Queue::Sqs', 'Manager::Default', 'Fetcher::Sqs'].each do |postfix|
|
16
|
+
MicroQ::Util.constantize("MicroQ::#{postfix}").send(:include, MicroQ::Inspect)
|
17
|
+
end
|
@@ -23,6 +23,8 @@ module MicroQ
|
|
23
23
|
attr_reader :queue, :workers
|
24
24
|
|
25
25
|
def start
|
26
|
+
return if queue_only?
|
27
|
+
|
26
28
|
count = workers.size
|
27
29
|
|
28
30
|
if (messages = queue.dequeue(count)).any?
|
@@ -53,6 +55,7 @@ module MicroQ
|
|
53
55
|
end
|
54
56
|
|
55
57
|
@busy ||= []
|
58
|
+
@workers ||= []
|
56
59
|
|
57
60
|
build_missing_workers
|
58
61
|
end
|
@@ -61,9 +64,10 @@ module MicroQ
|
|
61
64
|
|
62
65
|
# Don't shrink the pool if the config changes
|
63
66
|
def build_missing_workers
|
64
|
-
|
67
|
+
return if queue_only?
|
65
68
|
|
66
69
|
workers.select!(&:alive?)
|
70
|
+
@busy.select!(&:alive?)
|
67
71
|
|
68
72
|
missing_worker_count.times do
|
69
73
|
workers << MicroQ.config.worker.new_link(current_actor)
|
@@ -78,6 +82,10 @@ module MicroQ
|
|
78
82
|
(@workers + @busy).each {|w| w.terminate if w.alive? }
|
79
83
|
end
|
80
84
|
|
85
|
+
def queue_only?
|
86
|
+
@queue_only ||= MicroQ.config.sqs? && !MicroQ.config.worker_mode?
|
87
|
+
end
|
88
|
+
|
81
89
|
def self.shutdown?
|
82
90
|
!!@shutdown
|
83
91
|
end
|
@@ -0,0 +1,85 @@
|
|
1
|
+
module MicroQ
|
2
|
+
module Queue
|
3
|
+
class Sqs
|
4
|
+
include Celluloid
|
5
|
+
|
6
|
+
exit_handler :build_missing_fetchers
|
7
|
+
|
8
|
+
attr_accessor :messages
|
9
|
+
attr_reader :fetchers, :entries, :later
|
10
|
+
|
11
|
+
def initialize
|
12
|
+
@lock = Mutex.new
|
13
|
+
|
14
|
+
@messages, @entries, @later = [], [], []
|
15
|
+
@fetcher_map = {}
|
16
|
+
|
17
|
+
build_missing_fetchers
|
18
|
+
end
|
19
|
+
|
20
|
+
def push(item)
|
21
|
+
async.sync_push(item)
|
22
|
+
end
|
23
|
+
|
24
|
+
def sync_push(item, options={})
|
25
|
+
item, options = MicroQ::Util.stringify(item, options)
|
26
|
+
item['class'] = item['class'].to_s
|
27
|
+
|
28
|
+
MicroQ.middleware.client.call(item, options) do
|
29
|
+
args, queue_name = [item], verify_queue(item['queue'].to_s)
|
30
|
+
|
31
|
+
if (time = options['when'])
|
32
|
+
args << time.to_f
|
33
|
+
end
|
34
|
+
|
35
|
+
@fetcher_map[queue_name].add_message(*args)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
def receive_messages(*items)
|
40
|
+
@lock.synchronize do
|
41
|
+
(@messages += items).flatten!
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def dequeue(limit=30)
|
46
|
+
return [] unless limit > 0 && messages.any?
|
47
|
+
|
48
|
+
@lock.synchronize do
|
49
|
+
limit.times.collect do
|
50
|
+
messages.pop
|
51
|
+
end.compact
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
def verify_queue(name)
|
56
|
+
QUEUES_KEYS.include?(name) ? name : 'default'
|
57
|
+
end
|
58
|
+
|
59
|
+
def self.shutdown!
|
60
|
+
@shutdown = true
|
61
|
+
end
|
62
|
+
|
63
|
+
private
|
64
|
+
|
65
|
+
def self.shutdown?
|
66
|
+
@shutdown
|
67
|
+
end
|
68
|
+
|
69
|
+
def build_missing_fetchers(*)
|
70
|
+
return if self.class.shutdown?
|
71
|
+
|
72
|
+
@fetchers = QUEUES_KEYS.map do |name|
|
73
|
+
((existing = @fetcher_map[name]) && existing.alive? && existing) ||
|
74
|
+
MicroQ::Fetcher::Sqs.new_link(name, current_actor).tap do |fetcher|
|
75
|
+
@fetcher_map[name] = fetcher
|
76
|
+
fetcher.start!
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
QUEUES = { 'low' => 1, 'default' => 3, 'critical' => 5 }
|
82
|
+
QUEUES_KEYS = QUEUES.keys
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
data/lib/micro_q/queue.rb
CHANGED
@@ -0,0 +1,47 @@
|
|
1
|
+
module MicroQ
|
2
|
+
class SqsClient
|
3
|
+
attr_reader :url
|
4
|
+
|
5
|
+
def initialize(name)
|
6
|
+
@name = "#{MicroQ.config.env}_#{name}"
|
7
|
+
@url = client.create_queue(:queue_name => @name)[:queue_url]
|
8
|
+
end
|
9
|
+
|
10
|
+
def messages
|
11
|
+
response = client.receive_message(
|
12
|
+
:queue_url => url,
|
13
|
+
:wait_time_seconds => 10,
|
14
|
+
:max_number_of_messages => 10,
|
15
|
+
:visibility_timeout => 5 * 60
|
16
|
+
)
|
17
|
+
|
18
|
+
((response && response[:messages]) || []).collect do |message|
|
19
|
+
JSON.parse(message[:body]).merge(
|
20
|
+
'sqs_id' => message[:message_id],
|
21
|
+
'sqs_handle' => message[:receipt_handle],
|
22
|
+
'sqs_queue' => url
|
23
|
+
)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def messages_create(message)
|
28
|
+
attrs = {
|
29
|
+
:queue_url => url,
|
30
|
+
:message_body => message.to_json
|
31
|
+
}
|
32
|
+
|
33
|
+
attrs[:delay_seconds] = (message['run_at'].to_i - Time.now.to_i) if message.key?('run_at')
|
34
|
+
|
35
|
+
client.send_message(attrs)[:message_id]
|
36
|
+
end
|
37
|
+
|
38
|
+
private
|
39
|
+
|
40
|
+
def client
|
41
|
+
@client ||= AWS::SQS::Client.new(
|
42
|
+
:access_key_id => MicroQ.config.aws[:key],
|
43
|
+
:secret_access_key => MicroQ.config.aws[:secret]
|
44
|
+
)
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
data/lib/micro_q/version.rb
CHANGED
data/lib/micro_q.rb
CHANGED
@@ -6,6 +6,8 @@ require 'micro_q/util'
|
|
6
6
|
require 'micro_q/config'
|
7
7
|
require 'micro_q/manager'
|
8
8
|
|
9
|
+
Celluloid.logger = nil
|
10
|
+
|
9
11
|
module MicroQ
|
10
12
|
def self.config
|
11
13
|
@config ||= Config.new
|
@@ -51,17 +53,20 @@ require 'micro_q/proxies'
|
|
51
53
|
require 'micro_q/dsl'
|
52
54
|
require 'micro_q/worker'
|
53
55
|
require 'micro_q/queue'
|
56
|
+
require 'micro_q/sqs_client'
|
54
57
|
|
58
|
+
require 'micro_q/fetchers/sqs'
|
55
59
|
require 'micro_q/redis'
|
60
|
+
require 'micro_q/inspect'
|
56
61
|
|
57
62
|
require 'micro_q/wrappers/action_mailer'
|
58
63
|
|
64
|
+
|
59
65
|
# add Class and Instance methods first then
|
60
66
|
# override with additional extensions
|
61
67
|
|
62
68
|
require 'micro_q/methods/class'
|
63
69
|
require 'micro_q/methods/instance'
|
64
|
-
require 'micro_q/methods/active_record'
|
65
70
|
require 'micro_q/methods/action_mailer'
|
66
71
|
|
67
72
|
require 'micro_q/statistics/base'
|
@@ -71,4 +76,5 @@ require 'micro_q/statistics/redis'
|
|
71
76
|
# There is a better way coming soon 2/18/13
|
72
77
|
at_exit do
|
73
78
|
MicroQ::Manager::Default.shutdown!
|
79
|
+
MicroQ::Queue::Sqs.shutdown!
|
74
80
|
end
|
data/micro_q.gemspec
CHANGED
@@ -19,7 +19,9 @@ Gem::Specification.new do |gem|
|
|
19
19
|
|
20
20
|
gem.add_dependency "celluloid", '~> 0.12.0'
|
21
21
|
gem.add_dependency "connection_pool"
|
22
|
+
gem.add_dependency "slop"
|
22
23
|
gem.add_development_dependency "rake"
|
24
|
+
gem.add_development_dependency "fuubar"
|
23
25
|
gem.add_development_dependency "rspec"
|
24
26
|
gem.add_development_dependency "timecop"
|
25
27
|
gem.add_development_dependency "psych"
|
@@ -27,4 +29,5 @@ Gem::Specification.new do |gem|
|
|
27
29
|
gem.add_development_dependency "actionmailer", "> 3.2.0"
|
28
30
|
gem.add_development_dependency "sqlite3-ruby"
|
29
31
|
gem.add_development_dependency "mock_redis"
|
32
|
+
gem.add_development_dependency "aws-sdk"
|
30
33
|
end
|
data/spec/lib/config_spec.rb
CHANGED
@@ -36,6 +36,14 @@ describe MicroQ::Config do
|
|
36
36
|
subject.timeout.should == 120
|
37
37
|
end
|
38
38
|
|
39
|
+
it 'should have the default env' do
|
40
|
+
subject.env.should == 'development'
|
41
|
+
end
|
42
|
+
|
43
|
+
it 'should not be in sqs mode' do
|
44
|
+
subject.should_not be_sqs
|
45
|
+
end
|
46
|
+
|
39
47
|
it 'should have middleware chain' do
|
40
48
|
subject.middleware.class.should == MicroQ::Middleware::Chain
|
41
49
|
end
|
@@ -68,4 +76,43 @@ describe MicroQ::Config do
|
|
68
76
|
subject.statistics.should == MicroQ::Statistics::Default
|
69
77
|
end
|
70
78
|
end
|
79
|
+
|
80
|
+
describe 'when rails is defined' do
|
81
|
+
before do
|
82
|
+
module Rails end
|
83
|
+
def Rails.env; 'the-env' end
|
84
|
+
end
|
85
|
+
|
86
|
+
it 'should have the rails env' do
|
87
|
+
subject.env.should == 'the-env'
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
describe '#queue=' do
|
92
|
+
before do
|
93
|
+
subject.queue = 'blah-blah'
|
94
|
+
end
|
95
|
+
|
96
|
+
it 'should have the given queue' do
|
97
|
+
subject.queue.should == 'blah-blah'
|
98
|
+
end
|
99
|
+
|
100
|
+
describe 'when setting the SQS queue' do
|
101
|
+
before do
|
102
|
+
subject.queue = MicroQ::Queue::Sqs
|
103
|
+
end
|
104
|
+
|
105
|
+
it 'should have the given queue' do
|
106
|
+
subject.queue.should == MicroQ::Queue::Sqs
|
107
|
+
end
|
108
|
+
|
109
|
+
it 'should enable sqs mode' do
|
110
|
+
subject.sqs?.should == true
|
111
|
+
end
|
112
|
+
|
113
|
+
it 'should have zero workers' do
|
114
|
+
subject.workers.should == 0
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
71
118
|
end
|
@@ -0,0 +1,81 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe MicroQ::Fetcher::Sqs do
|
4
|
+
let(:queue) { mock(MicroQ::Queue::Sqs, :receive_messages! => nil) }
|
5
|
+
|
6
|
+
subject { MicroQ::Fetcher::Sqs.new(:low, queue) }
|
7
|
+
|
8
|
+
before do
|
9
|
+
@client = mock(MicroQ::SqsClient, :messages => [])
|
10
|
+
MicroQ::SqsClient.stub(:new => @client)
|
11
|
+
end
|
12
|
+
|
13
|
+
describe '.new' do
|
14
|
+
it 'should have the queue name' do
|
15
|
+
subject.name.should == 'low'
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe '#start' do
|
20
|
+
it 'should create an sqs client' do
|
21
|
+
MicroQ::SqsClient.should_receive(:new).with('low').and_return(@client)
|
22
|
+
|
23
|
+
subject.start
|
24
|
+
end
|
25
|
+
|
26
|
+
describe 'when called again' do
|
27
|
+
it 'should create an sqs client' do
|
28
|
+
MicroQ::SqsClient.should_receive(:new).and_return(@client)
|
29
|
+
subject.start
|
30
|
+
|
31
|
+
MicroQ::SqsClient.rspec_verify
|
32
|
+
MicroQ::SqsClient.rspec_reset
|
33
|
+
|
34
|
+
MicroQ::SqsClient.should_not_receive(:new)
|
35
|
+
|
36
|
+
subject.start
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'should request messages from the queue' do
|
41
|
+
@client.should_receive(:messages)
|
42
|
+
|
43
|
+
subject.start
|
44
|
+
end
|
45
|
+
|
46
|
+
describe 'when there are messages in the queue' do
|
47
|
+
let(:messages) { 2.times.map {|i| mock("message_#{i}") }}
|
48
|
+
|
49
|
+
before do
|
50
|
+
@client.stub(:messages).and_return(messages)
|
51
|
+
end
|
52
|
+
|
53
|
+
it 'should hand of the messages to the manager' do
|
54
|
+
queue.should_receive(:receive_messages!).with(messages)
|
55
|
+
|
56
|
+
subject.start
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
describe '#add_message' do
|
62
|
+
let(:message) { {'class' => 'FooBar'} }
|
63
|
+
let(:add_message) { subject.add_message(message) }
|
64
|
+
|
65
|
+
it 'should create the message' do
|
66
|
+
@client.should_receive(:messages_create).with(message)
|
67
|
+
|
68
|
+
add_message
|
69
|
+
end
|
70
|
+
|
71
|
+
describe 'when the message has an associated time' do
|
72
|
+
let(:add_message) { subject.add_message(message, Time.now.to_i) }
|
73
|
+
|
74
|
+
it 'should send the time' do
|
75
|
+
@client.should_receive(:messages_create).with(message.merge('run_at' => Time.now.to_i))
|
76
|
+
|
77
|
+
add_message
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
@@ -82,6 +82,38 @@ describe MicroQ::Manager::Default do
|
|
82
82
|
|
83
83
|
subject.start
|
84
84
|
end
|
85
|
+
|
86
|
+
describe 'when the manager is in SQS mode' do
|
87
|
+
before do
|
88
|
+
MicroQ.config['sqs?'] = true
|
89
|
+
end
|
90
|
+
|
91
|
+
it 'should not perform the items' do
|
92
|
+
@queue.should_not_receive(:dequeue)
|
93
|
+
[@worker1, @worker2].each {|w| w.should_not_receive(:perform!) }
|
94
|
+
|
95
|
+
subject.start
|
96
|
+
end
|
97
|
+
|
98
|
+
describe 'when in worker mode' do
|
99
|
+
before do
|
100
|
+
MicroQ.config['worker_mode?'] = true
|
101
|
+
end
|
102
|
+
|
103
|
+
it 'should dequeue the number of free workers' do
|
104
|
+
@queue.should_receive(:dequeue).with(2)
|
105
|
+
|
106
|
+
subject.start
|
107
|
+
end
|
108
|
+
|
109
|
+
it 'should perform the items' do
|
110
|
+
@worker1.should_receive(:perform!).with(@other_item)
|
111
|
+
@worker2.should_receive(:perform!).with(@item)
|
112
|
+
|
113
|
+
subject.start
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
85
117
|
end
|
86
118
|
end
|
87
119
|
|
@@ -144,6 +176,43 @@ describe MicroQ::Manager::Default do
|
|
144
176
|
|
145
177
|
subject.workers.should == [@worker1, @new_worker2]
|
146
178
|
end
|
179
|
+
|
180
|
+
describe 'when a busy worker has died' do
|
181
|
+
before do
|
182
|
+
subject.wrapped_object.instance_variable_set(:@busy, [@worker2])
|
183
|
+
end
|
184
|
+
|
185
|
+
it 'should restart the dead worker' do
|
186
|
+
MicroQ::Worker::Standard.should_receive(:new_link).and_return(@new_worker2)
|
187
|
+
|
188
|
+
death.call
|
189
|
+
end
|
190
|
+
|
191
|
+
it 'should remove the worker from the busy list' do
|
192
|
+
death.call
|
193
|
+
|
194
|
+
subject.wrapped_object.instance_variable_get(:@busy).should == []
|
195
|
+
end
|
196
|
+
|
197
|
+
it 'should have the new worker' do
|
198
|
+
death.call
|
199
|
+
|
200
|
+
subject.workers.should == [@worker1, @new_worker2]
|
201
|
+
end
|
202
|
+
end
|
203
|
+
|
204
|
+
describe 'when in SQS mode' do
|
205
|
+
before do
|
206
|
+
MicroQ.config['sqs?'] = true
|
207
|
+
end
|
208
|
+
|
209
|
+
it 'should have the original items' do
|
210
|
+
death.call
|
211
|
+
|
212
|
+
subject.queue.should == @queue
|
213
|
+
subject.workers.should == [@worker1, @worker2]
|
214
|
+
end
|
215
|
+
end
|
147
216
|
end
|
148
217
|
end
|
149
218
|
end
|
@@ -0,0 +1,206 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe MicroQ::Queue::Sqs do
|
4
|
+
let(:item) { { 'class' => 'MyWorker', 'args' => [4] } }
|
5
|
+
|
6
|
+
before do
|
7
|
+
@fetcher = mock('fetcher', :start! => true)
|
8
|
+
MicroQ::Fetcher::Sqs.stub(:new_link).and_return(@fetcher)
|
9
|
+
end
|
10
|
+
|
11
|
+
describe '.new' do
|
12
|
+
it 'should create three fetchers' do
|
13
|
+
MicroQ::Fetcher::Sqs.should_receive(:new_link).exactly(3).and_return(@fetcher)
|
14
|
+
|
15
|
+
subject
|
16
|
+
end
|
17
|
+
|
18
|
+
it 'should send the current actor along too' do
|
19
|
+
MicroQ::Fetcher::Sqs.should_receive(:new_link).exactly(3).with(anything, subject).and_return(@fetcher)
|
20
|
+
|
21
|
+
subject
|
22
|
+
end
|
23
|
+
|
24
|
+
it 'should start the fetcher' do
|
25
|
+
@fetcher.should_receive(:start!)
|
26
|
+
|
27
|
+
subject
|
28
|
+
end
|
29
|
+
|
30
|
+
it 'should have the fetchers' do
|
31
|
+
subject.fetchers.uniq.should == [@fetcher]
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
describe '#receive_messages' do
|
36
|
+
let(:messages) { 3.times.map {|i| mock("message_#{i}")} }
|
37
|
+
|
38
|
+
it 'should have no messages' do
|
39
|
+
subject.messages.should == []
|
40
|
+
end
|
41
|
+
|
42
|
+
describe 'when messages have given back' do
|
43
|
+
before do
|
44
|
+
subject.receive_messages(messages.first(1))
|
45
|
+
end
|
46
|
+
|
47
|
+
it 'should have the messages' do
|
48
|
+
subject.messages.should == [messages.first]
|
49
|
+
end
|
50
|
+
|
51
|
+
describe 'when more messages have been received' do
|
52
|
+
before do
|
53
|
+
subject.receive_messages(messages.last(2))
|
54
|
+
end
|
55
|
+
|
56
|
+
it 'should have the messages' do
|
57
|
+
subject.messages.should == messages
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
describe '#sync_push' do
|
64
|
+
before do
|
65
|
+
@fetchers = [:low, :default, :critical].collect do |name|
|
66
|
+
mock('MicroQ::Fetcher::Sqs : ' + name.to_s, :start! => nil).tap do |fetcher|
|
67
|
+
MicroQ::Fetcher::Sqs.stub(:new_link).with(name.to_s, anything).and_return(fetcher)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
it 'should add to the entries' do
|
73
|
+
@fetchers[1].should_receive(:add_message).with(item)
|
74
|
+
|
75
|
+
subject.sync_push(item)
|
76
|
+
end
|
77
|
+
|
78
|
+
it 'should stringify the class' do
|
79
|
+
@fetchers[1].should_receive(:add_message).with(hash_including('class' => 'MyWorker'))
|
80
|
+
|
81
|
+
subject.sync_push(:class => MyWorker)
|
82
|
+
end
|
83
|
+
|
84
|
+
[:low, :default, :critical].each_with_index do |name, i|
|
85
|
+
describe "when the message has a queue named #{name}" do
|
86
|
+
before do
|
87
|
+
item['queue'] = name
|
88
|
+
end
|
89
|
+
|
90
|
+
it 'should create the message on the right queue' do
|
91
|
+
@fetchers[i].should_receive(:add_message).with(item)
|
92
|
+
|
93
|
+
subject.sync_push(item)
|
94
|
+
end
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
98
|
+
describe 'when given the \'when\' key' do
|
99
|
+
let(:worker) { [item, { 'when' => (Time.now + 100).to_i }] }
|
100
|
+
|
101
|
+
it 'should schedule the item for later' do
|
102
|
+
@fetchers[1].should_receive(:add_message).with(item, (Time.now + 100).to_i)
|
103
|
+
|
104
|
+
subject.sync_push(*worker)
|
105
|
+
end
|
106
|
+
|
107
|
+
it 'should process the middleware chain' do
|
108
|
+
MicroQ.middleware.client.should_receive(:call) do |payload, options|
|
109
|
+
payload['class'].should == 'MyWorker'
|
110
|
+
payload['args'].should == [4]
|
111
|
+
options['when'].should == (Time.now + 100).to_i
|
112
|
+
end
|
113
|
+
|
114
|
+
subject.sync_push(*worker)
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
describe 'when given the symbol :when key' do
|
119
|
+
let(:worker) { [item, { :when => (Time.now + 100).to_i }] }
|
120
|
+
|
121
|
+
it 'should schedule the item for later' do
|
122
|
+
@fetchers[1].should_receive(:add_message).with(item, (Time.now + 100).to_i)
|
123
|
+
|
124
|
+
subject.sync_push(*worker)
|
125
|
+
end
|
126
|
+
end
|
127
|
+
|
128
|
+
describe 'client middleware' do
|
129
|
+
it 'should process the middleware chain' do
|
130
|
+
MicroQ.middleware.client.should_receive(:call) do |payload, opts|
|
131
|
+
payload['class'].should == 'MyWorker'
|
132
|
+
payload['args'].should == [4]
|
133
|
+
|
134
|
+
opts['when'].should == 'now'
|
135
|
+
end
|
136
|
+
|
137
|
+
subject.sync_push(item, 'when' => 'now')
|
138
|
+
end
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
describe '#push' do
|
143
|
+
before do
|
144
|
+
@async = mock(Celluloid::ActorProxy)
|
145
|
+
subject.stub(:async).and_return(@async)
|
146
|
+
end
|
147
|
+
|
148
|
+
it 'should asynchronously push the item' do
|
149
|
+
@async.should_receive(:sync_push).with(item)
|
150
|
+
|
151
|
+
subject.push(item)
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
describe '#dequeue' do
|
156
|
+
let(:items) { 2.times.map {|i| { 'class' => 'SqsWorker', 'args' => [i] }} }
|
157
|
+
let(:item) { items.first }
|
158
|
+
|
159
|
+
class SqsWorker
|
160
|
+
def perform(*)
|
161
|
+
end
|
162
|
+
end
|
163
|
+
|
164
|
+
describe 'when there are messages' do
|
165
|
+
before do
|
166
|
+
subject.messages = items.map(&:dup)
|
167
|
+
end
|
168
|
+
|
169
|
+
it 'should return the limited number of items' do
|
170
|
+
subject.dequeue(1).should == [items.last]
|
171
|
+
end
|
172
|
+
|
173
|
+
it 'should remove the item from the list' do
|
174
|
+
subject.dequeue.should == items.reverse
|
175
|
+
|
176
|
+
subject.messages.should == []
|
177
|
+
end
|
178
|
+
end
|
179
|
+
|
180
|
+
describe 'when there are many messages' do
|
181
|
+
let(:messages) do
|
182
|
+
5.times.collect {|i|
|
183
|
+
item.dup.tap {|it| it['args'] = [i]}
|
184
|
+
}
|
185
|
+
end
|
186
|
+
|
187
|
+
before do
|
188
|
+
subject.messages = messages.map(&:dup)
|
189
|
+
end
|
190
|
+
|
191
|
+
it 'should return up to the limit number of items' do
|
192
|
+
subject.dequeue(4).should == messages.last(4).reverse
|
193
|
+
|
194
|
+
subject.messages.should include(messages.first)
|
195
|
+
subject.dequeue.should == messages.first(1)
|
196
|
+
end
|
197
|
+
|
198
|
+
it 'should remove the items' do
|
199
|
+
subject.dequeue.should == messages.reverse
|
200
|
+
subject.dequeue.should == []
|
201
|
+
|
202
|
+
subject.messages.should == []
|
203
|
+
end
|
204
|
+
end
|
205
|
+
end
|
206
|
+
end
|
@@ -0,0 +1,166 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe MicroQ::SqsClient, :aws => true do
|
4
|
+
let(:url) { 'http://the.queue/' }
|
5
|
+
|
6
|
+
subject { MicroQ::SqsClient.new('low') }
|
7
|
+
|
8
|
+
before do
|
9
|
+
MicroQ.config.env = 'dev-env'
|
10
|
+
|
11
|
+
@client = mock(AWS::SQS::Client, :receive_message => {}, :create_queue => {:queue_url => url})
|
12
|
+
AWS::SQS::Client.stub(:new).and_return(@client)
|
13
|
+
end
|
14
|
+
|
15
|
+
describe '.new' do
|
16
|
+
it 'should create the queue' do
|
17
|
+
@client.should_receive(:create_queue).and_return({})
|
18
|
+
|
19
|
+
subject
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'should prefix the name with the environment' do
|
23
|
+
@client.should_receive(:create_queue).with(
|
24
|
+
:queue_name => 'dev-env_low'
|
25
|
+
).and_return({})
|
26
|
+
|
27
|
+
subject
|
28
|
+
end
|
29
|
+
|
30
|
+
it 'should have the url' do
|
31
|
+
subject.url.should == url
|
32
|
+
end
|
33
|
+
|
34
|
+
describe 'when the call fails' do
|
35
|
+
before do
|
36
|
+
@client.stub(:create_queue).and_raise
|
37
|
+
end
|
38
|
+
|
39
|
+
it 'should error' do
|
40
|
+
expect {
|
41
|
+
subject
|
42
|
+
}.to raise_error
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
describe '#messages' do
|
48
|
+
let(:messages) { subject.messages }
|
49
|
+
|
50
|
+
it 'should be an empty' do
|
51
|
+
messages.should == []
|
52
|
+
end
|
53
|
+
|
54
|
+
it 'should connect to the api for reading messages' do
|
55
|
+
@client.should_receive(:receive_message)
|
56
|
+
|
57
|
+
messages
|
58
|
+
end
|
59
|
+
|
60
|
+
it 'should have the queue url' do
|
61
|
+
@client.should_receive(:receive_message).with(hash_including(:queue_url => url))
|
62
|
+
|
63
|
+
messages
|
64
|
+
end
|
65
|
+
|
66
|
+
it 'should timeout after 10 seconds' do
|
67
|
+
@client.should_receive(:receive_message).with(hash_including(:wait_time_seconds => 10))
|
68
|
+
|
69
|
+
messages
|
70
|
+
end
|
71
|
+
|
72
|
+
it 'should request 10 items' do
|
73
|
+
@client.should_receive(:receive_message).with(hash_including(:max_number_of_messages => 10))
|
74
|
+
|
75
|
+
messages
|
76
|
+
end
|
77
|
+
|
78
|
+
it 'should make message available again after 5 minutes' do
|
79
|
+
@client.should_receive(:receive_message).with(hash_including(:visibility_timeout => 5 * 60))
|
80
|
+
|
81
|
+
messages
|
82
|
+
end
|
83
|
+
|
84
|
+
describe 'when messages are returned (body as json)' do
|
85
|
+
let(:response) do
|
86
|
+
{ :messages => 3.times.map {|i|
|
87
|
+
{
|
88
|
+
:body => {:id => i}.to_json,
|
89
|
+
:message_id => "id:#{i*5}",
|
90
|
+
:receipt_handle => "hand:#{i+10}"
|
91
|
+
}
|
92
|
+
}}
|
93
|
+
end
|
94
|
+
|
95
|
+
before do
|
96
|
+
@client.stub(:receive_message).and_return(response)
|
97
|
+
end
|
98
|
+
|
99
|
+
it 'should return the messages' do
|
100
|
+
messages.map {|m| m['id']}.should == [0, 1, 2]
|
101
|
+
end
|
102
|
+
|
103
|
+
it 'should merge in the message id' do
|
104
|
+
messages.map {|m| m['sqs_id']}.should == ['id:0', 'id:5', 'id:10']
|
105
|
+
end
|
106
|
+
|
107
|
+
it 'should merge in the message id' do
|
108
|
+
messages.map {|m| m['sqs_handle']}.should == ['hand:10', 'hand:11', 'hand:12']
|
109
|
+
end
|
110
|
+
|
111
|
+
it 'should merge in the queue url' do
|
112
|
+
messages.map {|m| m['sqs_queue']}.uniq.should == [url]
|
113
|
+
end
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
describe '#messages_create' do
|
118
|
+
let(:message) { {:class => 'MyWorker', :args => ['hi']} }
|
119
|
+
let(:send_message) { subject.messages_create(message) }
|
120
|
+
|
121
|
+
before do
|
122
|
+
@response = {:message_id => '10'}
|
123
|
+
@client.stub(:send_message).and_return(@response)
|
124
|
+
end
|
125
|
+
|
126
|
+
it 'should send the message' do
|
127
|
+
@client.should_receive(:send_message).and_return(@response)
|
128
|
+
|
129
|
+
send_message
|
130
|
+
end
|
131
|
+
|
132
|
+
it 'should send it for the queue' do
|
133
|
+
@client.should_receive(:send_message).with(hash_including(:queue_url => url)).and_return(@response)
|
134
|
+
|
135
|
+
send_message
|
136
|
+
end
|
137
|
+
|
138
|
+
it 'should send it for the queue' do
|
139
|
+
@client.should_receive(:send_message).with(hash_including(:message_body => message.to_json)).and_return(@response)
|
140
|
+
|
141
|
+
send_message
|
142
|
+
end
|
143
|
+
|
144
|
+
it 'should not delay the message' do
|
145
|
+
@client.should_receive(:send_message).with(hash_excluding(:delay_seconds)).and_return(@response)
|
146
|
+
|
147
|
+
send_message
|
148
|
+
end
|
149
|
+
|
150
|
+
it 'should return the message id' do
|
151
|
+
send_message.should == '10'
|
152
|
+
end
|
153
|
+
|
154
|
+
describe 'when the message is to be run later' do
|
155
|
+
before do
|
156
|
+
message['run_at'] = (Time.now + 60 * 60)
|
157
|
+
end
|
158
|
+
|
159
|
+
it 'should set the delay for sqs' do
|
160
|
+
@client.should_receive(:send_message).with(hash_including(:delay_seconds => 60*60)).and_return(@response)
|
161
|
+
|
162
|
+
send_message
|
163
|
+
end
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
data/spec/spec_helper.rb
CHANGED
@@ -13,17 +13,34 @@ silence_warnings do
|
|
13
13
|
Redis = MockRedis
|
14
14
|
end
|
15
15
|
|
16
|
+
class MyWorker; end
|
17
|
+
|
16
18
|
RSpec.configure do |config|
|
17
19
|
config.treat_symbols_as_metadata_keys_with_true_values = true
|
18
20
|
config.run_all_when_everything_filtered = true
|
19
21
|
|
20
22
|
config.order = 'default'
|
21
23
|
|
24
|
+
config.before :all do
|
25
|
+
GC.disable
|
26
|
+
end
|
27
|
+
|
22
28
|
config.before :each do
|
23
29
|
MicroQ.send :clear
|
24
30
|
MicroQ.redis {|r| r.flushdb }
|
25
31
|
end
|
26
32
|
|
33
|
+
config.before :each, :aws => true do
|
34
|
+
require 'aws-sdk'
|
35
|
+
end
|
36
|
+
|
37
|
+
config.before :each, :middleware => true do
|
38
|
+
class WorkerClass; end
|
39
|
+
|
40
|
+
@worker = WorkerClass.new
|
41
|
+
@payload = { 'class' => 'WorkerClass', 'args' => [1, 2], 'queue' => 'a-queue'}
|
42
|
+
end
|
43
|
+
|
27
44
|
config.before :each, :active_record => true do
|
28
45
|
require 'active_record'
|
29
46
|
require 'sqlite3' # https://github.com/luislavena/sqlite3-ruby
|
@@ -52,11 +69,8 @@ RSpec.configure do |config|
|
|
52
69
|
@_db.rollback
|
53
70
|
end
|
54
71
|
|
55
|
-
config.
|
56
|
-
|
57
|
-
|
58
|
-
@worker = WorkerClass.new
|
59
|
-
@payload = { 'class' => 'WorkerClass', 'args' => [1, 2], 'queue' => 'a-queue'}
|
72
|
+
config.after :all do
|
73
|
+
GC.enable
|
60
74
|
end
|
61
75
|
end
|
62
76
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: micro_q
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.9.
|
4
|
+
version: 0.9.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brian Norton
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-03-
|
11
|
+
date: 2013-03-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: celluloid
|
@@ -38,6 +38,20 @@ dependencies:
|
|
38
38
|
- - '>='
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: slop
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - '>='
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0'
|
48
|
+
type: :runtime
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - '>='
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
41
55
|
- !ruby/object:Gem::Dependency
|
42
56
|
name: rake
|
43
57
|
requirement: !ruby/object:Gem::Requirement
|
@@ -52,6 +66,20 @@ dependencies:
|
|
52
66
|
- - '>='
|
53
67
|
- !ruby/object:Gem::Version
|
54
68
|
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: fuubar
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - '>='
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - '>='
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '0'
|
55
83
|
- !ruby/object:Gem::Dependency
|
56
84
|
name: rspec
|
57
85
|
requirement: !ruby/object:Gem::Requirement
|
@@ -150,9 +178,24 @@ dependencies:
|
|
150
178
|
- - '>='
|
151
179
|
- !ruby/object:Gem::Version
|
152
180
|
version: '0'
|
181
|
+
- !ruby/object:Gem::Dependency
|
182
|
+
name: aws-sdk
|
183
|
+
requirement: !ruby/object:Gem::Requirement
|
184
|
+
requirements:
|
185
|
+
- - '>='
|
186
|
+
- !ruby/object:Gem::Version
|
187
|
+
version: '0'
|
188
|
+
type: :development
|
189
|
+
prerelease: false
|
190
|
+
version_requirements: !ruby/object:Gem::Requirement
|
191
|
+
requirements:
|
192
|
+
- - '>='
|
193
|
+
- !ruby/object:Gem::Version
|
194
|
+
version: '0'
|
153
195
|
description: ''
|
154
196
|
email: brian.nort@gmail.com
|
155
|
-
executables:
|
197
|
+
executables:
|
198
|
+
- microq
|
156
199
|
extensions: []
|
157
200
|
extra_rdoc_files: []
|
158
201
|
files:
|
@@ -164,9 +207,13 @@ files:
|
|
164
207
|
- LICENSE
|
165
208
|
- README.md
|
166
209
|
- Rakefile
|
210
|
+
- bin/microq
|
167
211
|
- lib/micro_q.rb
|
212
|
+
- lib/micro_q/cli.rb
|
168
213
|
- lib/micro_q/config.rb
|
169
214
|
- lib/micro_q/dsl.rb
|
215
|
+
- lib/micro_q/fetchers/sqs.rb
|
216
|
+
- lib/micro_q/inspect.rb
|
170
217
|
- lib/micro_q/manager.rb
|
171
218
|
- lib/micro_q/manager/default.rb
|
172
219
|
- lib/micro_q/methods/action_mailer.rb
|
@@ -189,7 +236,9 @@ files:
|
|
189
236
|
- lib/micro_q/queue.rb
|
190
237
|
- lib/micro_q/queue/default.rb
|
191
238
|
- lib/micro_q/queue/redis.rb
|
239
|
+
- lib/micro_q/queue/sqs.rb
|
192
240
|
- lib/micro_q/redis.rb
|
241
|
+
- lib/micro_q/sqs_client.rb
|
193
242
|
- lib/micro_q/statistics/base.rb
|
194
243
|
- lib/micro_q/statistics/default.rb
|
195
244
|
- lib/micro_q/statistics/redis.rb
|
@@ -203,6 +252,7 @@ files:
|
|
203
252
|
- spec/helpers/queues_examples.rb
|
204
253
|
- spec/lib/config_spec.rb
|
205
254
|
- spec/lib/dsl_spec.rb
|
255
|
+
- spec/lib/fetchers/sqs_spec.rb
|
206
256
|
- spec/lib/manager/default_spec.rb
|
207
257
|
- spec/lib/methods/action_mailer_spec.rb
|
208
258
|
- spec/lib/methods/active_record_spec.rb
|
@@ -221,6 +271,8 @@ files:
|
|
221
271
|
- spec/lib/proxies/instance_spec.rb
|
222
272
|
- spec/lib/queue/default_spec.rb
|
223
273
|
- spec/lib/queue/redis_spec.rb
|
274
|
+
- spec/lib/queue/sqs_spec.rb
|
275
|
+
- spec/lib/sqs_client_spec.rb
|
224
276
|
- spec/lib/statistics/default_spec.rb
|
225
277
|
- spec/lib/statistics/redis_spec.rb
|
226
278
|
- spec/lib/util_spec.rb
|
@@ -255,6 +307,7 @@ test_files:
|
|
255
307
|
- spec/helpers/queues_examples.rb
|
256
308
|
- spec/lib/config_spec.rb
|
257
309
|
- spec/lib/dsl_spec.rb
|
310
|
+
- spec/lib/fetchers/sqs_spec.rb
|
258
311
|
- spec/lib/manager/default_spec.rb
|
259
312
|
- spec/lib/methods/action_mailer_spec.rb
|
260
313
|
- spec/lib/methods/active_record_spec.rb
|
@@ -273,6 +326,8 @@ test_files:
|
|
273
326
|
- spec/lib/proxies/instance_spec.rb
|
274
327
|
- spec/lib/queue/default_spec.rb
|
275
328
|
- spec/lib/queue/redis_spec.rb
|
329
|
+
- spec/lib/queue/sqs_spec.rb
|
330
|
+
- spec/lib/sqs_client_spec.rb
|
276
331
|
- spec/lib/statistics/default_spec.rb
|
277
332
|
- spec/lib/statistics/redis_spec.rb
|
278
333
|
- spec/lib/util_spec.rb
|