fleck 2.2.1 → 2.2.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +11 -11
- data/Gemfile +6 -6
- data/examples/actions.rb +60 -60
- data/examples/blocking_consumer.rb +42 -42
- data/examples/consumer_initialization.rb +44 -44
- data/examples/deprecation.rb +50 -50
- data/examples/example.rb +76 -76
- data/examples/expired.rb +72 -72
- data/examples/fanout.rb +62 -62
- data/lib/fleck/client.rb +147 -124
- data/lib/fleck/configuration.rb +147 -147
- data/lib/fleck/core/consumer/configuration.rb +69 -69
- data/lib/fleck/core/consumer/helpers_definers.rb +56 -56
- data/lib/fleck/core/consumer/logger.rb +88 -88
- data/lib/fleck/core/consumer/request.rb +100 -100
- data/lib/fleck/core/consumer/response.rb +77 -77
- data/lib/fleck/core/consumer/response_helpers.rb +81 -81
- data/lib/fleck/core/consumer.rb +1 -1
- data/lib/fleck/loggable.rb +15 -15
- data/lib/fleck/utilities/host_rating.rb +102 -102
- data/lib/fleck/version.rb +1 -1
- data/lib/fleck.rb +82 -82
- metadata +2 -2
@@ -1,81 +1,81 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Fleck
|
4
|
-
module Core
|
5
|
-
# Open `Consumer` class in order to define consumer helpers
|
6
|
-
class Consumer
|
7
|
-
# Define methods for 1xx codes
|
8
|
-
information_method :continue!, 100
|
9
|
-
information_method :switching_protocols!, 101
|
10
|
-
information_method :processing!, 102
|
11
|
-
information_method :early_hints!, 103
|
12
|
-
|
13
|
-
# Define methods for 2xx codes
|
14
|
-
success_method :ok!, 200
|
15
|
-
success_method :created!, 201
|
16
|
-
success_method :accepted!, 202
|
17
|
-
success_method :non_authoritative_information!, 203
|
18
|
-
success_method :no_content!, 204
|
19
|
-
success_method :reset_content!, 205
|
20
|
-
success_method :partial_content!, 206
|
21
|
-
success_method :multi_status!, 207
|
22
|
-
success_method :already_reported!, 208
|
23
|
-
success_method :im_used!, 226
|
24
|
-
|
25
|
-
# Define methods for 3xx codes
|
26
|
-
redirect_method :multiple_choice!, 300
|
27
|
-
redirect_method :moved_permanently!, 301
|
28
|
-
redirect_method :found!, 302
|
29
|
-
redirect_method :see_other!, 303
|
30
|
-
redirect_method :not_modified!, 304
|
31
|
-
redirect_method :use_proxy!, 305
|
32
|
-
redirect_method :unused!, 306
|
33
|
-
redirect_method :temporary_redirect!, 307
|
34
|
-
redirect_method :permanent_redirect!, 308
|
35
|
-
|
36
|
-
# Define methods for 4xx errors
|
37
|
-
error_method :bad_request!, 400, 'Bad Request'
|
38
|
-
error_method :unauthorized!, 401, 'Unauthorized'
|
39
|
-
error_method :payment_required!, 402, 'Payment Required'
|
40
|
-
error_method :forbidden!, 403, 'Forbidden'
|
41
|
-
error_method :not_found!, 404, 'Not Found'
|
42
|
-
error_method :method_not_allowed!, 405, 'Method Not Allowed'
|
43
|
-
error_method :not_acceptable!, 406, 'Not Acceptable'
|
44
|
-
error_method :proxy_authentication_required!, 407, 'Proxy Authentication Required'
|
45
|
-
error_method :request_timeout!, 408, 'Request Timeout'
|
46
|
-
error_method :conflict!, 409, 'Conflict'
|
47
|
-
error_method :gone!, 410, 'Gone'
|
48
|
-
error_method :length_required!, 411, 'Length Required'
|
49
|
-
error_method :precondition_failed!, 412, 'Precondition Failed'
|
50
|
-
error_method :payload_too_large!, 413, 'Payload Too Large'
|
51
|
-
error_method :uri_too_long!, 414, 'URI Too Long'
|
52
|
-
error_method :unsupported_media_type!, 415, 'Unsupported Media Type'
|
53
|
-
error_method :range_not_satisfiable!, 416, 'Range Not Satisfiable'
|
54
|
-
error_method :expectation_failed!, 417, 'Expectation Failed'
|
55
|
-
error_method :im_a_teapot!, 418, "I'm a teapot"
|
56
|
-
error_method :misdirected_request!, 421, 'Misdirected Request'
|
57
|
-
error_method :unprocessable_entity!, 422, 'Unprocessable Entity'
|
58
|
-
error_method :locked!, 423, 'Locked'
|
59
|
-
error_method :failed_dependency!, 424, 'Failed Dependency'
|
60
|
-
error_method :too_early!, 425, 'Too Early'
|
61
|
-
error_method :upgrade_required!, 426, 'Upgrade Required'
|
62
|
-
error_method :precondition_required!, 428, 'Precondition Required'
|
63
|
-
error_method :too_many_requests!, 429, 'Too Many Requests'
|
64
|
-
error_method :request_header_fields_too_large!, 431, 'Request Header Fields Too Large'
|
65
|
-
error_method :unavailable_for_legal_reasons!, 451, 'Unavailable For Legal Reasons'
|
66
|
-
|
67
|
-
# Define methods for 5xx errors
|
68
|
-
error_method :internal_server_error!, 500, 'Internal Server Error'
|
69
|
-
error_method :not_implemented!, 501, 'Not Implemented'
|
70
|
-
error_method :bad_gateway!, 502, 'Bad Gateway'
|
71
|
-
error_method :service_unavailable!, 503, 'Service Unavailable'
|
72
|
-
error_method :gateway_timeout!, 504, 'Gateway Timeout'
|
73
|
-
error_method :http_version_not_supported!, 505, 'HTTP Version Not Supported'
|
74
|
-
error_method :variant_also_negotiates!, 506, 'Variant Also Negotiates'
|
75
|
-
error_method :insufficient_storage!, 507, 'Insufficient Storage'
|
76
|
-
error_method :loop_detected!, 508, 'Loop Detected'
|
77
|
-
error_method :not_extended!, 510, 'Not Extended'
|
78
|
-
error_method :network_authentication_required!, 511, 'Network Authentication Required'
|
79
|
-
end
|
80
|
-
end
|
81
|
-
end
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Fleck
|
4
|
+
module Core
|
5
|
+
# Open `Consumer` class in order to define consumer helpers
|
6
|
+
class Consumer
|
7
|
+
# Define methods for 1xx codes
|
8
|
+
information_method :continue!, 100
|
9
|
+
information_method :switching_protocols!, 101
|
10
|
+
information_method :processing!, 102
|
11
|
+
information_method :early_hints!, 103
|
12
|
+
|
13
|
+
# Define methods for 2xx codes
|
14
|
+
success_method :ok!, 200
|
15
|
+
success_method :created!, 201
|
16
|
+
success_method :accepted!, 202
|
17
|
+
success_method :non_authoritative_information!, 203
|
18
|
+
success_method :no_content!, 204
|
19
|
+
success_method :reset_content!, 205
|
20
|
+
success_method :partial_content!, 206
|
21
|
+
success_method :multi_status!, 207
|
22
|
+
success_method :already_reported!, 208
|
23
|
+
success_method :im_used!, 226
|
24
|
+
|
25
|
+
# Define methods for 3xx codes
|
26
|
+
redirect_method :multiple_choice!, 300
|
27
|
+
redirect_method :moved_permanently!, 301
|
28
|
+
redirect_method :found!, 302
|
29
|
+
redirect_method :see_other!, 303
|
30
|
+
redirect_method :not_modified!, 304
|
31
|
+
redirect_method :use_proxy!, 305
|
32
|
+
redirect_method :unused!, 306
|
33
|
+
redirect_method :temporary_redirect!, 307
|
34
|
+
redirect_method :permanent_redirect!, 308
|
35
|
+
|
36
|
+
# Define methods for 4xx errors
|
37
|
+
error_method :bad_request!, 400, 'Bad Request'
|
38
|
+
error_method :unauthorized!, 401, 'Unauthorized'
|
39
|
+
error_method :payment_required!, 402, 'Payment Required'
|
40
|
+
error_method :forbidden!, 403, 'Forbidden'
|
41
|
+
error_method :not_found!, 404, 'Not Found'
|
42
|
+
error_method :method_not_allowed!, 405, 'Method Not Allowed'
|
43
|
+
error_method :not_acceptable!, 406, 'Not Acceptable'
|
44
|
+
error_method :proxy_authentication_required!, 407, 'Proxy Authentication Required'
|
45
|
+
error_method :request_timeout!, 408, 'Request Timeout'
|
46
|
+
error_method :conflict!, 409, 'Conflict'
|
47
|
+
error_method :gone!, 410, 'Gone'
|
48
|
+
error_method :length_required!, 411, 'Length Required'
|
49
|
+
error_method :precondition_failed!, 412, 'Precondition Failed'
|
50
|
+
error_method :payload_too_large!, 413, 'Payload Too Large'
|
51
|
+
error_method :uri_too_long!, 414, 'URI Too Long'
|
52
|
+
error_method :unsupported_media_type!, 415, 'Unsupported Media Type'
|
53
|
+
error_method :range_not_satisfiable!, 416, 'Range Not Satisfiable'
|
54
|
+
error_method :expectation_failed!, 417, 'Expectation Failed'
|
55
|
+
error_method :im_a_teapot!, 418, "I'm a teapot"
|
56
|
+
error_method :misdirected_request!, 421, 'Misdirected Request'
|
57
|
+
error_method :unprocessable_entity!, 422, 'Unprocessable Entity'
|
58
|
+
error_method :locked!, 423, 'Locked'
|
59
|
+
error_method :failed_dependency!, 424, 'Failed Dependency'
|
60
|
+
error_method :too_early!, 425, 'Too Early'
|
61
|
+
error_method :upgrade_required!, 426, 'Upgrade Required'
|
62
|
+
error_method :precondition_required!, 428, 'Precondition Required'
|
63
|
+
error_method :too_many_requests!, 429, 'Too Many Requests'
|
64
|
+
error_method :request_header_fields_too_large!, 431, 'Request Header Fields Too Large'
|
65
|
+
error_method :unavailable_for_legal_reasons!, 451, 'Unavailable For Legal Reasons'
|
66
|
+
|
67
|
+
# Define methods for 5xx errors
|
68
|
+
error_method :internal_server_error!, 500, 'Internal Server Error'
|
69
|
+
error_method :not_implemented!, 501, 'Not Implemented'
|
70
|
+
error_method :bad_gateway!, 502, 'Bad Gateway'
|
71
|
+
error_method :service_unavailable!, 503, 'Service Unavailable'
|
72
|
+
error_method :gateway_timeout!, 504, 'Gateway Timeout'
|
73
|
+
error_method :http_version_not_supported!, 505, 'HTTP Version Not Supported'
|
74
|
+
error_method :variant_also_negotiates!, 506, 'Variant Also Negotiates'
|
75
|
+
error_method :insufficient_storage!, 507, 'Insufficient Storage'
|
76
|
+
error_method :loop_detected!, 508, 'Loop Detected'
|
77
|
+
error_method :not_extended!, 510, 'Not Extended'
|
78
|
+
error_method :network_authentication_required!, 511, 'Network Authentication Required'
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
data/lib/fleck/core/consumer.rb
CHANGED
data/lib/fleck/loggable.rb
CHANGED
@@ -1,15 +1,15 @@
|
|
1
|
-
|
2
|
-
module Fleck::Loggable
|
3
|
-
def logger
|
4
|
-
return @logger if @logger
|
5
|
-
|
6
|
-
@logger = Fleck.logger.clone
|
7
|
-
@logger.progname = self.class.name
|
8
|
-
|
9
|
-
@logger
|
10
|
-
end
|
11
|
-
|
12
|
-
def log_error(error)
|
13
|
-
logger.error "#{error.inspect}\n#{error.backtrace.join("\n")}"
|
14
|
-
end
|
15
|
-
end
|
1
|
+
|
2
|
+
module Fleck::Loggable
|
3
|
+
def logger
|
4
|
+
return @logger if @logger
|
5
|
+
|
6
|
+
@logger = Fleck.logger.clone
|
7
|
+
@logger.progname = self.class.name
|
8
|
+
|
9
|
+
@logger
|
10
|
+
end
|
11
|
+
|
12
|
+
def log_error(error)
|
13
|
+
logger.error "#{error.inspect}\n#{error.backtrace.join("\n")}"
|
14
|
+
end
|
15
|
+
end
|
@@ -1,102 +1,102 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require 'socket'
|
4
|
-
|
5
|
-
# Open `Fleck` module to add `HostRating` class.
|
6
|
-
module Fleck
|
7
|
-
# `HostRating` class allows to test host latency on a regular basis and to compare the latency
|
8
|
-
# with other hosts.
|
9
|
-
class HostRating
|
10
|
-
include Fleck::Loggable
|
11
|
-
|
12
|
-
CONN_TIMEOUT = 5
|
13
|
-
|
14
|
-
attr_reader :host, :port, :avg, :history
|
15
|
-
|
16
|
-
def initialize(host: 'localhost', port: 5672, refresh_rate: 30_000, period: 300_000)
|
17
|
-
@host = host
|
18
|
-
@port = port
|
19
|
-
@refresh_rate = refresh_rate
|
20
|
-
@period = period
|
21
|
-
|
22
|
-
# metrics
|
23
|
-
@reachable = false
|
24
|
-
@avg = 0
|
25
|
-
@updated_at = nil
|
26
|
-
@history = []
|
27
|
-
|
28
|
-
refresh!
|
29
|
-
@timer = Ztimer.every(@refresh_rate) { refresh! }
|
30
|
-
end
|
31
|
-
|
32
|
-
def reachable?
|
33
|
-
@reachable
|
34
|
-
end
|
35
|
-
|
36
|
-
def close
|
37
|
-
@timer.cancel!
|
38
|
-
end
|
39
|
-
|
40
|
-
def <=>(other)
|
41
|
-
# the other host is reachable, so it comes first
|
42
|
-
return 1 if !reachable? && other.reachable?
|
43
|
-
|
44
|
-
# both host are unreachable, so they have the same priority
|
45
|
-
return 0 unless reachable? || other.reachable?
|
46
|
-
|
47
|
-
# the current host comes first, because it's reachable, while the other host is unreachable
|
48
|
-
return -1 if reachable? && !other.reachable?
|
49
|
-
|
50
|
-
# when both hosts are reachable, use avg latency to order them
|
51
|
-
avg <=> other.avg
|
52
|
-
end
|
53
|
-
|
54
|
-
private
|
55
|
-
|
56
|
-
def refresh!
|
57
|
-
@history << measure_latency
|
58
|
-
@history.shift if @history.size > @period / @refresh_rate
|
59
|
-
@avg = @history.inject(:+).to_f / @history.size
|
60
|
-
@reachable = true
|
61
|
-
rescue SocketError, Timeout::Error => e
|
62
|
-
@reachable = false
|
63
|
-
logger.error "Connection error: #{@host}:#{@port} (#{e.inspect})"
|
64
|
-
ensure
|
65
|
-
@updated_at = Time.now
|
66
|
-
end
|
67
|
-
|
68
|
-
# Use a socket to test connection latency.
|
69
|
-
def measure_latency
|
70
|
-
socket = create_socket
|
71
|
-
|
72
|
-
started_at = Time.now.to_f
|
73
|
-
begin
|
74
|
-
socket.connect_nonblock(sock_addr)
|
75
|
-
rescue IO::WaitWritable
|
76
|
-
IO.select(nil, [socket], nil, CONN_TIMEOUT) or raise Timeout::Error
|
77
|
-
end
|
78
|
-
|
79
|
-
(Time.now.to_f - started_at) * 1000 # ms
|
80
|
-
ensure
|
81
|
-
socket&.close
|
82
|
-
end
|
83
|
-
|
84
|
-
# Create a new socket for connection test.
|
85
|
-
def create_socket
|
86
|
-
socket = Socket.new(:AF_INET, :SOCK_STREAM, 0)
|
87
|
-
socket.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
88
|
-
|
89
|
-
socket
|
90
|
-
end
|
91
|
-
|
92
|
-
# Resolve domain name in order to obtain IP address to test.
|
93
|
-
def sock_addr
|
94
|
-
return @sock_addr if @sock_addr
|
95
|
-
|
96
|
-
addr = Socket.getaddrinfo(@host, nil)
|
97
|
-
@sock_addr = Socket.pack_sockaddr_in(@port, addr[0][3])
|
98
|
-
|
99
|
-
@sock_addr
|
100
|
-
end
|
101
|
-
end
|
102
|
-
end
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'socket'
|
4
|
+
|
5
|
+
# Open `Fleck` module to add `HostRating` class.
|
6
|
+
module Fleck
|
7
|
+
# `HostRating` class allows to test host latency on a regular basis and to compare the latency
|
8
|
+
# with other hosts.
|
9
|
+
class HostRating
|
10
|
+
include Fleck::Loggable
|
11
|
+
|
12
|
+
CONN_TIMEOUT = 5
|
13
|
+
|
14
|
+
attr_reader :host, :port, :avg, :history
|
15
|
+
|
16
|
+
def initialize(host: 'localhost', port: 5672, refresh_rate: 30_000, period: 300_000)
|
17
|
+
@host = host
|
18
|
+
@port = port
|
19
|
+
@refresh_rate = refresh_rate
|
20
|
+
@period = period
|
21
|
+
|
22
|
+
# metrics
|
23
|
+
@reachable = false
|
24
|
+
@avg = 0
|
25
|
+
@updated_at = nil
|
26
|
+
@history = []
|
27
|
+
|
28
|
+
refresh!
|
29
|
+
@timer = Ztimer.every(@refresh_rate) { refresh! }
|
30
|
+
end
|
31
|
+
|
32
|
+
def reachable?
|
33
|
+
@reachable
|
34
|
+
end
|
35
|
+
|
36
|
+
def close
|
37
|
+
@timer.cancel!
|
38
|
+
end
|
39
|
+
|
40
|
+
def <=>(other)
|
41
|
+
# the other host is reachable, so it comes first
|
42
|
+
return 1 if !reachable? && other.reachable?
|
43
|
+
|
44
|
+
# both host are unreachable, so they have the same priority
|
45
|
+
return 0 unless reachable? || other.reachable?
|
46
|
+
|
47
|
+
# the current host comes first, because it's reachable, while the other host is unreachable
|
48
|
+
return -1 if reachable? && !other.reachable?
|
49
|
+
|
50
|
+
# when both hosts are reachable, use avg latency to order them
|
51
|
+
avg <=> other.avg
|
52
|
+
end
|
53
|
+
|
54
|
+
private
|
55
|
+
|
56
|
+
def refresh!
|
57
|
+
@history << measure_latency
|
58
|
+
@history.shift if @history.size > @period / @refresh_rate
|
59
|
+
@avg = @history.inject(:+).to_f / @history.size
|
60
|
+
@reachable = true
|
61
|
+
rescue SocketError, Timeout::Error => e
|
62
|
+
@reachable = false
|
63
|
+
logger.error "Connection error: #{@host}:#{@port} (#{e.inspect})"
|
64
|
+
ensure
|
65
|
+
@updated_at = Time.now
|
66
|
+
end
|
67
|
+
|
68
|
+
# Use a socket to test connection latency.
|
69
|
+
def measure_latency
|
70
|
+
socket = create_socket
|
71
|
+
|
72
|
+
started_at = Time.now.to_f
|
73
|
+
begin
|
74
|
+
socket.connect_nonblock(sock_addr)
|
75
|
+
rescue IO::WaitWritable
|
76
|
+
IO.select(nil, [socket], nil, CONN_TIMEOUT) or raise Timeout::Error
|
77
|
+
end
|
78
|
+
|
79
|
+
(Time.now.to_f - started_at) * 1000 # ms
|
80
|
+
ensure
|
81
|
+
socket&.close
|
82
|
+
end
|
83
|
+
|
84
|
+
# Create a new socket for connection test.
|
85
|
+
def create_socket
|
86
|
+
socket = Socket.new(:AF_INET, :SOCK_STREAM, 0)
|
87
|
+
socket.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
88
|
+
|
89
|
+
socket
|
90
|
+
end
|
91
|
+
|
92
|
+
# Resolve domain name in order to obtain IP address to test.
|
93
|
+
def sock_addr
|
94
|
+
return @sock_addr if @sock_addr
|
95
|
+
|
96
|
+
addr = Socket.getaddrinfo(@host, nil)
|
97
|
+
@sock_addr = Socket.pack_sockaddr_in(@port, addr[0][3])
|
98
|
+
|
99
|
+
@sock_addr
|
100
|
+
end
|
101
|
+
end
|
102
|
+
end
|
data/lib/fleck/version.rb
CHANGED
data/lib/fleck.rb
CHANGED
@@ -1,82 +1,82 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
$LOAD_PATH << File.expand_path(__dir__)
|
4
|
-
|
5
|
-
require 'English'
|
6
|
-
require 'logger'
|
7
|
-
require 'rainbow'
|
8
|
-
require 'rainbow/ext/string'
|
9
|
-
require 'bunny'
|
10
|
-
require 'thread_safe'
|
11
|
-
require 'securerandom'
|
12
|
-
require 'oj'
|
13
|
-
require 'ztimer'
|
14
|
-
# require 'fleck/version'
|
15
|
-
require 'fleck/utilities/hash_with_indifferent_access'
|
16
|
-
# require 'fleck/loggable'
|
17
|
-
# require 'fleck/host_rating'
|
18
|
-
# require 'fleck/configuration'
|
19
|
-
# require 'fleck/consumer'
|
20
|
-
# require 'fleck/client'
|
21
|
-
|
22
|
-
# `Fleck` module implements the features for `Fleck` configuration and messages production/consumption.
|
23
|
-
module Fleck
|
24
|
-
autoload :VERSION, 'fleck/version.rb'
|
25
|
-
autoload :Loggable, 'fleck/loggable.rb'
|
26
|
-
autoload :HostRating, 'fleck/utilities/host_rating.rb'
|
27
|
-
autoload :Configuration, 'fleck/configuration.rb'
|
28
|
-
autoload :Core, 'fleck/core.rb'
|
29
|
-
autoload :Consumer, 'fleck/consumer.rb'
|
30
|
-
autoload :Client, 'fleck/client.rb'
|
31
|
-
|
32
|
-
@config = Configuration.new
|
33
|
-
@consumers = ThreadSafe::Array.new
|
34
|
-
@connections = ThreadSafe::Hash.new
|
35
|
-
|
36
|
-
class << self
|
37
|
-
attr_reader :config, :consumers
|
38
|
-
|
39
|
-
def configure
|
40
|
-
yield @config if block_given?
|
41
|
-
@config
|
42
|
-
end
|
43
|
-
|
44
|
-
def logger
|
45
|
-
@config.logger
|
46
|
-
end
|
47
|
-
|
48
|
-
def register_consumer(consumer_class)
|
49
|
-
return if @consumers.include?(consumer_class)
|
50
|
-
|
51
|
-
@consumers << consumer_class
|
52
|
-
end
|
53
|
-
|
54
|
-
def connection(options = {})
|
55
|
-
opts = Fleck.config.default_options.merge(options)
|
56
|
-
key = "ampq://#{opts[:user]}@#{opts[:host]}:#{opts[:port]}#{opts[:vhost]}"
|
57
|
-
conn = @connections[key]
|
58
|
-
if !conn || conn.closed?
|
59
|
-
opts[:logger] = Fleck.logger.clone
|
60
|
-
opts[:logger].progname += '::Bunny'
|
61
|
-
logger.info "New connection #{key}"
|
62
|
-
conn = Bunny.new(opts)
|
63
|
-
conn.start
|
64
|
-
@connections[key] = conn
|
65
|
-
end
|
66
|
-
|
67
|
-
conn
|
68
|
-
end
|
69
|
-
|
70
|
-
def terminate
|
71
|
-
@connections.each do |key, connection|
|
72
|
-
Fleck.logger.info "Closing connection #{key}"
|
73
|
-
connection.close
|
74
|
-
rescue StandardError => e
|
75
|
-
Fleck.logger.error e.inspect
|
76
|
-
end
|
77
|
-
@connections.clear
|
78
|
-
|
79
|
-
true
|
80
|
-
end
|
81
|
-
end
|
82
|
-
end
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
$LOAD_PATH << File.expand_path(__dir__)
|
4
|
+
|
5
|
+
require 'English'
|
6
|
+
require 'logger'
|
7
|
+
require 'rainbow'
|
8
|
+
require 'rainbow/ext/string'
|
9
|
+
require 'bunny'
|
10
|
+
require 'thread_safe'
|
11
|
+
require 'securerandom'
|
12
|
+
require 'oj'
|
13
|
+
require 'ztimer'
|
14
|
+
# require 'fleck/version'
|
15
|
+
require 'fleck/utilities/hash_with_indifferent_access'
|
16
|
+
# require 'fleck/loggable'
|
17
|
+
# require 'fleck/host_rating'
|
18
|
+
# require 'fleck/configuration'
|
19
|
+
# require 'fleck/consumer'
|
20
|
+
# require 'fleck/client'
|
21
|
+
|
22
|
+
# `Fleck` module implements the features for `Fleck` configuration and messages production/consumption.
|
23
|
+
module Fleck
|
24
|
+
autoload :VERSION, 'fleck/version.rb'
|
25
|
+
autoload :Loggable, 'fleck/loggable.rb'
|
26
|
+
autoload :HostRating, 'fleck/utilities/host_rating.rb'
|
27
|
+
autoload :Configuration, 'fleck/configuration.rb'
|
28
|
+
autoload :Core, 'fleck/core.rb'
|
29
|
+
autoload :Consumer, 'fleck/consumer.rb'
|
30
|
+
autoload :Client, 'fleck/client.rb'
|
31
|
+
|
32
|
+
@config = Configuration.new
|
33
|
+
@consumers = ThreadSafe::Array.new
|
34
|
+
@connections = ThreadSafe::Hash.new
|
35
|
+
|
36
|
+
class << self
|
37
|
+
attr_reader :config, :consumers
|
38
|
+
|
39
|
+
def configure
|
40
|
+
yield @config if block_given?
|
41
|
+
@config
|
42
|
+
end
|
43
|
+
|
44
|
+
def logger
|
45
|
+
@config.logger
|
46
|
+
end
|
47
|
+
|
48
|
+
def register_consumer(consumer_class)
|
49
|
+
return if @consumers.include?(consumer_class)
|
50
|
+
|
51
|
+
@consumers << consumer_class
|
52
|
+
end
|
53
|
+
|
54
|
+
def connection(options = {})
|
55
|
+
opts = Fleck.config.default_options.merge(options)
|
56
|
+
key = "ampq://#{opts[:user]}@#{opts[:host]}:#{opts[:port]}#{opts[:vhost]}"
|
57
|
+
conn = @connections[key]
|
58
|
+
if !conn || conn.closed?
|
59
|
+
opts[:logger] = Fleck.logger.clone
|
60
|
+
opts[:logger].progname += '::Bunny'
|
61
|
+
logger.info "New connection #{key}"
|
62
|
+
conn = Bunny.new(opts)
|
63
|
+
conn.start
|
64
|
+
@connections[key] = conn
|
65
|
+
end
|
66
|
+
|
67
|
+
conn
|
68
|
+
end
|
69
|
+
|
70
|
+
def terminate
|
71
|
+
@connections.each do |key, connection|
|
72
|
+
Fleck.logger.info "Closing connection #{key}"
|
73
|
+
connection.close
|
74
|
+
rescue StandardError => e
|
75
|
+
Fleck.logger.error e.inspect
|
76
|
+
end
|
77
|
+
@connections.clear
|
78
|
+
|
79
|
+
true
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: fleck
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.2.
|
4
|
+
version: 2.2.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Groza Sergiu
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-
|
11
|
+
date: 2023-11-17 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|