fleck 1.0.1 → 2.0.0

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.
Files changed (37) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +11 -10
  3. data/CHANGELOG.md +89 -74
  4. data/Gemfile +6 -4
  5. data/examples/actions.rb +59 -53
  6. data/examples/blocking_consumer.rb +42 -42
  7. data/examples/consumer_initialization.rb +44 -42
  8. data/examples/deprecation.rb +50 -57
  9. data/examples/example.rb +76 -74
  10. data/examples/expired.rb +72 -76
  11. data/examples/fanout.rb +62 -64
  12. data/fleck.gemspec +37 -36
  13. data/lib/fleck/client.rb +124 -124
  14. data/lib/fleck/configuration.rb +149 -144
  15. data/lib/fleck/consumer.rb +7 -287
  16. data/lib/fleck/core/consumer/action_param.rb +106 -0
  17. data/lib/fleck/core/consumer/actions.rb +76 -0
  18. data/lib/fleck/core/consumer/base.rb +111 -0
  19. data/lib/fleck/core/consumer/configuration.rb +69 -0
  20. data/lib/fleck/core/consumer/decorators.rb +77 -0
  21. data/lib/fleck/core/consumer/helpers_definers.rb +55 -0
  22. data/lib/fleck/core/consumer/logger.rb +88 -0
  23. data/lib/fleck/core/consumer/request.rb +89 -0
  24. data/lib/fleck/core/consumer/response.rb +77 -0
  25. data/lib/fleck/core/consumer/response_helpers.rb +81 -0
  26. data/lib/fleck/core/consumer/validation.rb +163 -0
  27. data/lib/fleck/core/consumer.rb +166 -0
  28. data/lib/fleck/core.rb +9 -0
  29. data/lib/fleck/loggable.rb +15 -10
  30. data/lib/fleck/{hash_with_indifferent_access.rb → utilities/hash_with_indifferent_access.rb} +80 -85
  31. data/lib/fleck/utilities/host_rating.rb +104 -0
  32. data/lib/fleck/version.rb +6 -3
  33. data/lib/fleck.rb +81 -72
  34. metadata +35 -24
  35. data/lib/fleck/consumer/request.rb +0 -52
  36. data/lib/fleck/consumer/response.rb +0 -80
  37. data/lib/fleck/host_rating.rb +0 -74
data/examples/example.rb CHANGED
@@ -1,74 +1,76 @@
1
- #!/usr/bin/env ruby
2
- # encoding: utf-8
3
-
4
- require 'fleck'
5
-
6
- user = ENV['USER'] || 'guest'
7
- pass = ENV['PASS'] || 'guest'
8
-
9
- CONCURRENCY = (ENV['CONCURRENCY'] || 10).to_i
10
- SAMPLES = (ENV['SAMPLES'] || 10_000).to_i
11
-
12
- Fleck.configure do |config|
13
- config.default_user = user
14
- config.default_pass = pass
15
- config.loglevel = Logger::DEBUG
16
- end
17
-
18
- client = Fleck::Client.new(Fleck.connection, "example.queue", concurrency: CONCURRENCY.to_i)
19
-
20
- count = 0
21
- success = 0
22
- failure = 0
23
-
24
- mutex = Mutex.new
25
- lock = Mutex.new
26
- condition = ConditionVariable.new
27
-
28
- class First < Fleck::Consumer
29
- configure queue: "example.queue", concurrency: CONCURRENCY.to_i
30
-
31
- def on_message(request, response)
32
- if rand > 0.1
33
- if request.action == "incr"
34
- response.body = "#{request.params[:num].to_i + 1}. Hello, World!"
35
- else
36
- response.not_found
37
- end
38
- else
39
- logger.warn "REJECTING REQUEST {headers: #{request.headers}, params: #{request.params}"
40
- response.reject!(requeue: true)
41
- end
42
- end
43
- end
44
-
45
- Thread.new do
46
- SAMPLES.times do |i|
47
- client.request(action: 'incr', params: {num: i, secret: 'supersecret'}, async: true, timeout: 1, rmq_options: { priority: (rand * 9).round(0), mandatory: false}) do |request, response|
48
- if response.status == 200
49
- request.logger.debug response.body
50
- else
51
- request.logger.error "#{response.status} #{response.errors.join(", ")}"
52
- end
53
- mutex.synchronize do
54
- count += 1
55
- if response.status == 200
56
- success += 1
57
- else
58
- failure += 1
59
- end
60
-
61
- lock.synchronize { condition.signal } if count >= SAMPLES
62
- end
63
- end
64
- end
65
- end
66
-
67
- at_exit do
68
- puts "Total: #{count}, Success: #{success}, Failure: #{failure}"
69
- end
70
-
71
- lock.synchronize { condition.wait(lock) }
72
- exit
73
-
74
- #First.consumers.map(&:terminate)
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require 'fleck'
5
+
6
+ user = ENV['USER'] || 'guest'
7
+ pass = ENV['PASS'] || 'guest'
8
+
9
+ CONCURRENCY = (ENV['CONCURRENCY'] || 10).to_i
10
+ SAMPLES = (ENV['SAMPLES'] || 10_000).to_i
11
+ QUEUE = 'example.queue'
12
+
13
+ Fleck.configure do |config|
14
+ config.default_user = user
15
+ config.default_pass = pass
16
+ config.loglevel = Logger::DEBUG
17
+ end
18
+
19
+ client = Fleck::Client.new(Fleck.connection, QUEUE, concurrency: CONCURRENCY.to_i)
20
+
21
+ count = 0
22
+ success = 0
23
+ failure = 0
24
+
25
+ mutex = Mutex.new
26
+ lock = Mutex.new
27
+ condition = ConditionVariable.new
28
+
29
+ class First < Fleck::Consumer
30
+ configure queue: QUEUE, concurrency: CONCURRENCY.to_i
31
+
32
+ action :incr, 'Returns a message with incremented number'
33
+ param :num, type: 'number', required: true
34
+ def incr
35
+ if rand > 0.1
36
+ not_found! if request.action != 'incr'
37
+
38
+ ok! "#{params[:num].to_i + 1}. Hello, World!"
39
+ else
40
+ logger.warn "REJECTING REQUEST {headers: #{headers}, params: #{params}"
41
+ request.reject!(requeue: true)
42
+ end
43
+ end
44
+ end
45
+
46
+ Thread.new do
47
+ SAMPLES.times do |i|
48
+ client.request(
49
+ action: 'incr',
50
+ params: { num: i, secret: 'supersecret' },
51
+ async: true,
52
+ timeout: 1,
53
+ rmq_options: { priority: (rand * 9).round(0), mandatory: false }
54
+ ) do |request, response|
55
+ if response.status == 200
56
+ request.logger.debug response.body
57
+ else
58
+ request.logger.error "#{response.status} #{response.errors.join(', ')}"
59
+ end
60
+ mutex.synchronize do
61
+ count += 1
62
+ if response.status == 200
63
+ success += 1
64
+ else
65
+ failure += 1
66
+ end
67
+
68
+ lock.synchronize { condition.signal } if count >= SAMPLES
69
+ end
70
+ end
71
+ end
72
+ end
73
+
74
+ lock.synchronize { condition.wait(lock) }
75
+
76
+ puts "Total: #{count}, Success: #{success}, Failure: #{failure}"
data/examples/expired.rb CHANGED
@@ -1,76 +1,72 @@
1
- #!/usr/bin/env ruby
2
- # encoding: utf-8
3
-
4
- require 'fleck'
5
-
6
- user = ENV['USER'] || 'guest'
7
- pass = ENV['PASS'] || 'guest'
8
-
9
- CONCURRENCY = (ENV['CONCURRENCY'] || 2).to_i
10
- SAMPLES = (ENV['SAMPLES'] || 10).to_i
11
-
12
- Fleck.configure do |config|
13
- config.default_user = user
14
- config.default_pass = pass
15
- config.loglevel = Logger::DEBUG
16
- end
17
-
18
- connection = Fleck.connection(host: "127.0.0.1", port: 5672, user: user, pass: pass, vhost: "/")
19
- client = Fleck::Client.new(connection, "expiration.example.queue", concurrency: CONCURRENCY.to_i)
20
- success_probability = 0.8
21
-
22
- count = 0
23
- success = 0
24
- failure = 0
25
-
26
- mutex = Mutex.new
27
- lock = Mutex.new
28
- condition = ConditionVariable.new
29
-
30
- class MyConsumer < Fleck::Consumer
31
- configure queue: 'expiration.example.queue', concurrency: CONCURRENCY.to_i
32
-
33
- def on_message(request, response)
34
- case request.action
35
- when 'hello' then hello
36
- else
37
- response.not_found!
38
- end
39
- end
40
-
41
- def hello
42
- sleep rand
43
- response.body = "#{request.params[:num] + 1}. Hello!"
44
- end
45
- end
46
-
47
- SAMPLES.to_i.times do |num|
48
- client.request(action: 'hello', params: {num: num}, async: true, timeout: (success_probability * SAMPLES.to_f)/CONCURRENCY.to_f) do |request, response|
49
- if request.expired?
50
- puts "EXPIRED: #{response.inspect}"
51
- elsif response.status == 200
52
- puts "SUCCESS: #{response.body}"
53
- else
54
- puts "ERROR: #{response.inspect}"
55
- end
56
-
57
- mutex.synchronize do
58
- count += 1
59
- if response.status == 200
60
- success += 1
61
- else
62
- failure += 1
63
- end
64
-
65
- lock.synchronize { condition.signal } if count >= SAMPLES
66
- end
67
- end
68
- end
69
-
70
- at_exit do
71
- puts "Ztimer: (count: #{Ztimer.count}, jobs: #{Ztimer.jobs_count})"
72
- puts "Total: #{count}, Success: #{success}, Failure: #{failure}"
73
- end
74
-
75
- lock.synchronize { condition.wait(lock) }
76
- exit
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require 'fleck'
5
+
6
+ user = ENV['USER'] || 'guest'
7
+ pass = ENV['PASS'] || 'guest'
8
+
9
+ CONCURRENCY = (ENV['CONCURRENCY'] || 2).to_i
10
+ SAMPLES = (ENV['SAMPLES'] || 10).to_i
11
+ QUEUE = 'expiration.example.queue'
12
+
13
+ Fleck.configure do |config|
14
+ config.default_user = user
15
+ config.default_pass = pass
16
+ config.loglevel = Logger::DEBUG
17
+ end
18
+
19
+ connection = Fleck.connection(host: '127.0.0.1', port: 5672, user: user, pass: pass, vhost: '/')
20
+ client = Fleck::Client.new(connection, QUEUE, concurrency: CONCURRENCY.to_i)
21
+ success_probability = 0.8
22
+
23
+ count = 0
24
+ success = 0
25
+ failure = 0
26
+
27
+ mutex = Mutex.new
28
+ lock = Mutex.new
29
+ condition = ConditionVariable.new
30
+
31
+ class MyConsumer < Fleck::Consumer
32
+ configure queue: QUEUE, concurrency: CONCURRENCY.to_i
33
+
34
+ action :hello
35
+ def hello
36
+ sleep rand
37
+ ok! "#{params[:num] + 1}. Hello!"
38
+ end
39
+ end
40
+
41
+ SAMPLES.to_i.times do |num|
42
+ client.request(
43
+ action: 'hello',
44
+ params: { num: num },
45
+ async: true,
46
+ timeout: (success_probability * SAMPLES.to_f) / CONCURRENCY
47
+ ) do |request, response|
48
+ if request.expired?
49
+ puts "EXPIRED: #{response.inspect}"
50
+ elsif response.status == 200
51
+ puts "SUCCESS: #{response.body}"
52
+ else
53
+ puts "ERROR: #{response.inspect}"
54
+ end
55
+
56
+ mutex.synchronize do
57
+ count += 1
58
+ if response.status == 200
59
+ success += 1
60
+ else
61
+ failure += 1
62
+ end
63
+
64
+ lock.synchronize { condition.signal } if count >= SAMPLES
65
+ end
66
+ end
67
+ end
68
+
69
+ lock.synchronize { condition.wait(lock) }
70
+
71
+ puts "Ztimer: (count: #{Ztimer.count}, jobs: #{Ztimer.jobs_count})"
72
+ puts "Total: #{count}, Success: #{success}, Failure: #{failure}"
data/examples/fanout.rb CHANGED
@@ -1,64 +1,62 @@
1
- #!/usr/bin/env ruby
2
- # encoding: utf-8
3
-
4
- require 'fleck'
5
-
6
- user = ENV['USER'] || 'guest'
7
- pass = ENV['PASS'] || 'guest'
8
-
9
- CONCURRENCY = (ENV['CONCURRENCY'] || 10).to_i
10
- SAMPLES = (ENV['SAMPLES'] || 1_000).to_i
11
-
12
- Fleck.configure do |config|
13
- config.default_user = user
14
- config.default_pass = pass
15
- config.loglevel = Logger::DEBUG
16
- end
17
-
18
- connection = Fleck.connection(host: "127.0.0.1", port: 5672, user: user, pass: pass, vhost: "/")
19
- client = Fleck::Client.new(connection, "example.queue", concurrency: CONCURRENCY.to_i, exchange_type: :fanout, exchange_name: 'fanout.example.queue', multiple_responses: true)
20
-
21
- count = 0
22
- success = 0
23
- failure = 0
24
-
25
- mutex = Mutex.new
26
- lock = Mutex.new
27
- condition = ConditionVariable.new
28
-
29
- class First < Fleck::Consumer
30
- configure queue: "example.queue", concurrency: CONCURRENCY.to_i, exchange_type: :fanout, exchange_name: 'fanout.example.queue'
31
-
32
- def on_message(request, response)
33
- if request.action == "incr"
34
- response.body = "#{request.params[:num].to_i + 1}. Hello, World!"
35
- else
36
- response.not_found
37
- end
38
- end
39
- end
40
-
41
- Thread.new do
42
- SAMPLES.times do |i|
43
- client.request(action: 'incr', params: {num: i}, timeout: 60) do |request, response|
44
- request.logger.debug response.body
45
- mutex.synchronize do
46
- count += 1
47
- if response.status == 200
48
- success += 1
49
- else
50
- failure += 1
51
- end
52
-
53
- lock.synchronize { condition.signal } if count >= SAMPLES
54
- end
55
- end
56
- end
57
- end
58
-
59
- at_exit do
60
- puts "Total: #{count}, Success: #{success}, Failure: #{failure}"
61
- end
62
-
63
- lock.synchronize { condition.wait(lock) }
64
- exit
1
+ #!/usr/bin/env ruby
2
+ # encoding: utf-8
3
+
4
+ require 'fleck'
5
+
6
+ user = ENV['USER'] || 'guest'
7
+ pass = ENV['PASS'] || 'guest'
8
+
9
+ CONCURRENCY = (ENV['CONCURRENCY'] || 10).to_i
10
+ SAMPLES = (ENV['SAMPLES'] || 1_000).to_i
11
+
12
+ Fleck.configure do |config|
13
+ config.default_user = user
14
+ config.default_pass = pass
15
+ config.loglevel = Logger::DEBUG
16
+ end
17
+
18
+ connection = Fleck.connection(host: "127.0.0.1", port: 5672, user: user, pass: pass, vhost: "/")
19
+ client = Fleck::Client.new(connection, "example.queue", concurrency: CONCURRENCY.to_i, exchange_type: :fanout, exchange_name: 'fanout.example.queue', multiple_responses: true)
20
+
21
+ count = 0
22
+ success = 0
23
+ failure = 0
24
+
25
+ mutex = Mutex.new
26
+ lock = Mutex.new
27
+ condition = ConditionVariable.new
28
+
29
+ class First < Fleck::Consumer
30
+ configure queue: "example.queue", concurrency: CONCURRENCY.to_i, exchange_type: :fanout, exchange_name: 'fanout.example.queue'
31
+
32
+ action :incr
33
+ def incr
34
+ if request.action == 'incr'
35
+ ok! "#{request.params[:num].to_i + 1}. Hello, World!"
36
+ else
37
+ not_found!
38
+ end
39
+ end
40
+ end
41
+
42
+ Thread.new do
43
+ SAMPLES.times do |i|
44
+ client.request(action: 'incr', params: { num: i }, timeout: 60) do |request, response|
45
+ request.logger.debug response.body
46
+ mutex.synchronize do
47
+ count += 1
48
+ if response.status == 200
49
+ success += 1
50
+ else
51
+ failure += 1
52
+ end
53
+
54
+ lock.synchronize { condition.signal } if count >= SAMPLES
55
+ end
56
+ end
57
+ end
58
+ end
59
+
60
+ lock.synchronize { condition.wait(lock) }
61
+
62
+ puts "Total: #{count}, Success: #{success}, Failure: #{failure}"
data/fleck.gemspec CHANGED
@@ -1,36 +1,37 @@
1
- # coding: utf-8
2
- lib = File.expand_path('../lib', __FILE__)
3
- $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
- require 'fleck/version'
5
-
6
- Gem::Specification.new do |spec|
7
- spec.name = "fleck"
8
- spec.platform = "ruby"
9
- spec.version = Fleck::VERSION
10
- spec.authors = ["Groza Sergiu"]
11
- spec.email = ["serioja90@gmail.com"]
12
-
13
- spec.summary = %q{A Ruby gem for syncronous and asyncronous communication via Message Queue services.}
14
- spec.description = %q{
15
- Fleck is a library for syncronous and asyncronous communication over Message Queues services. Unlike a common
16
- HTTP communication, Fleck requests and responses are pure JSON messages.
17
- }
18
- spec.homepage = "https://github.com/serioja90/fleck"
19
- spec.license = "MIT"
20
-
21
- spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
22
- spec.bindir = "exe"
23
- spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
24
- spec.require_paths = ["lib"]
25
-
26
- spec.required_ruby_version = ">= 2.3"
27
-
28
- spec.add_development_dependency "bundler", "~> 1.17"
29
- spec.add_development_dependency "rake", "~> 13.0"
30
- spec.add_development_dependency "rspec", "~> 3.9"
31
- spec.add_dependency "rainbow", "~> 2.2"
32
- spec.add_dependency "bunny", "~> 2.14"
33
- spec.add_dependency "thread_safe", "~> 0.3"
34
- spec.add_dependency "oj", "~> 3.10"
35
- spec.add_dependency "ztimer", "~> 0.6"
36
- end
1
+ # frozen_string_literal: true
2
+
3
+ lib = File.expand_path(__dir__)
4
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
+ require 'lib/fleck/version'
6
+
7
+ Gem::Specification.new do |spec|
8
+ spec.name = 'fleck'
9
+ spec.platform = 'ruby'
10
+ spec.version = Fleck::VERSION
11
+ spec.authors = ['Groza Sergiu']
12
+ spec.email = ['serioja90@gmail.com']
13
+
14
+ spec.summary = %(A Ruby gem for syncronous and asyncronous communication via Message Queue services.)
15
+ spec.description = %(
16
+ Fleck is a library for syncronous and asyncronous communication over Message Queues services. Unlike a common
17
+ HTTP communication, Fleck requests and responses are pure JSON messages.
18
+ )
19
+ spec.homepage = 'https://github.com/serioja90/fleck'
20
+ spec.license = 'MIT'
21
+
22
+ spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
23
+ spec.bindir = 'exe'
24
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
25
+ spec.require_paths = ['lib']
26
+
27
+ spec.required_ruby_version = '>= 2.5'
28
+
29
+ spec.add_development_dependency 'bundler', '>= 2.2.33'
30
+ spec.add_development_dependency 'rake', '~> 13.0'
31
+ spec.add_development_dependency 'rspec', '~> 3.9'
32
+ spec.add_dependency 'bunny', '~> 2.14'
33
+ spec.add_dependency 'oj', '~> 3.10'
34
+ spec.add_dependency 'rainbow', '~> 2.2'
35
+ spec.add_dependency 'thread_safe', '~> 0.3'
36
+ spec.add_dependency 'ztimer', '~> 0.6'
37
+ end