karafka 1.1.0 → 1.3.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -5
- checksums.yaml.gz.sig +2 -0
- data.tar.gz.sig +0 -0
- data/.coditsu/ci.yml +3 -0
- data/.console_irbrc +1 -3
- data/.github/FUNDING.yml +3 -0
- data/.github/ISSUE_TEMPLATE/bug_report.md +50 -0
- data/.github/ISSUE_TEMPLATE/feature_request.md +20 -0
- data/.gitignore +1 -0
- data/.ruby-version +1 -1
- data/.travis.yml +35 -16
- data/CHANGELOG.md +151 -2
- data/CONTRIBUTING.md +6 -7
- data/Gemfile +3 -3
- data/Gemfile.lock +96 -70
- data/README.md +29 -23
- data/bin/karafka +1 -1
- data/certs/mensfeld.pem +25 -0
- data/config/errors.yml +38 -5
- data/karafka.gemspec +19 -10
- data/lib/karafka.rb +15 -12
- data/lib/karafka/app.rb +19 -18
- data/lib/karafka/attributes_map.rb +15 -14
- data/lib/karafka/backends/inline.rb +1 -2
- data/lib/karafka/base_consumer.rb +57 -0
- data/lib/karafka/base_responder.rb +72 -31
- data/lib/karafka/cli.rb +1 -1
- data/lib/karafka/cli/console.rb +11 -9
- data/lib/karafka/cli/flow.rb +0 -1
- data/lib/karafka/cli/info.rb +3 -1
- data/lib/karafka/cli/install.rb +29 -8
- data/lib/karafka/cli/server.rb +11 -7
- data/lib/karafka/code_reloader.rb +67 -0
- data/lib/karafka/connection/{config_adapter.rb → api_adapter.rb} +67 -24
- data/lib/karafka/connection/batch_delegator.rb +51 -0
- data/lib/karafka/connection/builder.rb +16 -0
- data/lib/karafka/connection/client.rb +117 -0
- data/lib/karafka/connection/listener.rb +37 -17
- data/lib/karafka/connection/message_delegator.rb +36 -0
- data/lib/karafka/consumers/callbacks.rb +71 -0
- data/lib/karafka/consumers/includer.rb +63 -0
- data/lib/karafka/consumers/metadata.rb +10 -0
- data/lib/karafka/consumers/responders.rb +24 -0
- data/lib/karafka/{controllers → consumers}/single_params.rb +3 -3
- data/lib/karafka/contracts.rb +10 -0
- data/lib/karafka/contracts/config.rb +21 -0
- data/lib/karafka/contracts/consumer_group.rb +206 -0
- data/lib/karafka/contracts/consumer_group_topic.rb +19 -0
- data/lib/karafka/contracts/responder_usage.rb +54 -0
- data/lib/karafka/contracts/server_cli_options.rb +29 -0
- data/lib/karafka/errors.rb +23 -15
- data/lib/karafka/fetcher.rb +6 -12
- data/lib/karafka/helpers/class_matcher.rb +19 -9
- data/lib/karafka/helpers/config_retriever.rb +3 -3
- data/lib/karafka/helpers/inflector.rb +26 -0
- data/lib/karafka/helpers/multi_delegator.rb +0 -1
- data/lib/karafka/instrumentation/logger.rb +57 -0
- data/lib/karafka/instrumentation/monitor.rb +70 -0
- data/lib/karafka/instrumentation/proctitle_listener.rb +36 -0
- data/lib/karafka/instrumentation/stdout_listener.rb +138 -0
- data/lib/karafka/params/builders/metadata.rb +33 -0
- data/lib/karafka/params/builders/params.rb +36 -0
- data/lib/karafka/params/builders/params_batch.rb +25 -0
- data/lib/karafka/params/metadata.rb +35 -0
- data/lib/karafka/params/params.rb +35 -95
- data/lib/karafka/params/params_batch.rb +38 -18
- data/lib/karafka/patches/ruby_kafka.rb +25 -12
- data/lib/karafka/persistence/client.rb +29 -0
- data/lib/karafka/persistence/consumers.rb +45 -0
- data/lib/karafka/persistence/topics.rb +48 -0
- data/lib/karafka/process.rb +5 -8
- data/lib/karafka/responders/builder.rb +15 -14
- data/lib/karafka/responders/topic.rb +6 -8
- data/lib/karafka/routing/builder.rb +37 -9
- data/lib/karafka/routing/consumer_group.rb +1 -1
- data/lib/karafka/routing/consumer_mapper.rb +10 -9
- data/lib/karafka/routing/proxy.rb +10 -1
- data/lib/karafka/routing/router.rb +1 -1
- data/lib/karafka/routing/topic.rb +8 -12
- data/lib/karafka/routing/topic_mapper.rb +16 -18
- data/lib/karafka/serialization/json/deserializer.rb +27 -0
- data/lib/karafka/serialization/json/serializer.rb +31 -0
- data/lib/karafka/server.rb +45 -24
- data/lib/karafka/setup/config.rb +95 -37
- data/lib/karafka/setup/configurators/water_drop.rb +12 -5
- data/lib/karafka/setup/dsl.rb +21 -0
- data/lib/karafka/status.rb +7 -3
- data/lib/karafka/templates/{application_controller.rb.example → application_consumer.rb.erb} +2 -2
- data/lib/karafka/templates/{application_responder.rb.example → application_responder.rb.erb} +0 -0
- data/lib/karafka/templates/karafka.rb.erb +92 -0
- data/lib/karafka/version.rb +1 -1
- metadata +126 -57
- metadata.gz.sig +0 -0
- data/.github/ISSUE_TEMPLATE.md +0 -2
- data/lib/karafka/base_controller.rb +0 -60
- data/lib/karafka/connection/consumer.rb +0 -121
- data/lib/karafka/connection/processor.rb +0 -61
- data/lib/karafka/controllers/callbacks.rb +0 -54
- data/lib/karafka/controllers/includer.rb +0 -51
- data/lib/karafka/controllers/responders.rb +0 -19
- data/lib/karafka/loader.rb +0 -29
- data/lib/karafka/logger.rb +0 -53
- data/lib/karafka/monitor.rb +0 -98
- data/lib/karafka/parsers/json.rb +0 -38
- data/lib/karafka/patches/dry_configurable.rb +0 -31
- data/lib/karafka/persistence/consumer.rb +0 -25
- data/lib/karafka/persistence/controller.rb +0 -38
- data/lib/karafka/schemas/config.rb +0 -21
- data/lib/karafka/schemas/consumer_group.rb +0 -65
- data/lib/karafka/schemas/consumer_group_topic.rb +0 -18
- data/lib/karafka/schemas/responder_usage.rb +0 -39
- data/lib/karafka/schemas/server_cli_options.rb +0 -43
- data/lib/karafka/setup/configurators/base.rb +0 -35
- data/lib/karafka/templates/karafka.rb.example +0 -41
metadata.gz.sig
ADDED
Binary file
|
data/.github/ISSUE_TEMPLATE.md
DELETED
@@ -1,60 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Karafka module namespace
|
4
|
-
module Karafka
|
5
|
-
# Base controller from which all Karafka controllers should inherit
|
6
|
-
class BaseController
|
7
|
-
extend ActiveSupport::DescendantsTracker
|
8
|
-
|
9
|
-
class << self
|
10
|
-
attr_reader :topic
|
11
|
-
|
12
|
-
# Assigns a topic to a controller and build up proper controller functionalities, so it can
|
13
|
-
# cooperate with the topic settings
|
14
|
-
# @param topic [Karafka::Routing::Topic]
|
15
|
-
# @return [Karafka::Routing::Topic] assigned topic
|
16
|
-
def topic=(topic)
|
17
|
-
@topic = topic
|
18
|
-
Controllers::Includer.call(self)
|
19
|
-
end
|
20
|
-
end
|
21
|
-
|
22
|
-
# @return [Karafka::Routing::Topic] topic to which a given controller is subscribed
|
23
|
-
def topic
|
24
|
-
self.class.topic
|
25
|
-
end
|
26
|
-
|
27
|
-
# Creates lazy loaded params batch object
|
28
|
-
# @note Until first params usage, it won't parse data at all
|
29
|
-
# @param messages [Array<Kafka::FetchedMessage>, Array<Hash>] messages with raw
|
30
|
-
# content (from Kafka) or messages inside a hash (from backend, etc)
|
31
|
-
# @return [Karafka::Params::ParamsBatch] lazy loaded params batch
|
32
|
-
def params_batch=(messages)
|
33
|
-
@params_batch = Karafka::Params::ParamsBatch.new(messages, topic.parser)
|
34
|
-
end
|
35
|
-
|
36
|
-
# Executes the default controller flow.
|
37
|
-
def call
|
38
|
-
process
|
39
|
-
end
|
40
|
-
|
41
|
-
private
|
42
|
-
|
43
|
-
# We make it private as it should be accesible only from the inside of a controller
|
44
|
-
attr_reader :params_batch
|
45
|
-
|
46
|
-
# @return [Karafka::Connection::Consumer] messages consumer that can be used to
|
47
|
-
# commit manually offset or pause / stop consumer based on the business logic
|
48
|
-
def consumer
|
49
|
-
Persistence::Consumer.read
|
50
|
-
end
|
51
|
-
|
52
|
-
# Method that will perform business logic and on data received from Kafka (it will consume
|
53
|
-
# the data)
|
54
|
-
# @note This method needs bo be implemented in a subclass. We stub it here as a failover if
|
55
|
-
# someone forgets about it or makes on with typo
|
56
|
-
def consume
|
57
|
-
raise NotImplementedError, 'Implement this in a subclass'
|
58
|
-
end
|
59
|
-
end
|
60
|
-
end
|
@@ -1,121 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
module Connection
|
5
|
-
# Class used as a wrapper around Ruby-Kafka to simplify additional
|
6
|
-
# features that we provide/might provide in future and to hide the internal implementation
|
7
|
-
class Consumer
|
8
|
-
# Creates a queue consumer that will pull the data from Kafka
|
9
|
-
# @param consumer_group [Karafka::Routing::ConsumerGroup] consumer group for which
|
10
|
-
# we create a client
|
11
|
-
# @return [Karafka::Connection::Consumer] group consumer that can subscribe to
|
12
|
-
# multiple topics
|
13
|
-
def initialize(consumer_group)
|
14
|
-
@consumer_group = consumer_group
|
15
|
-
Persistence::Consumer.write(self)
|
16
|
-
end
|
17
|
-
|
18
|
-
# Opens connection, gets messages and calls a block for each of the incoming messages
|
19
|
-
# @yieldparam [Array<Kafka::FetchedMessage>] kafka fetched messages
|
20
|
-
# @note This will yield with raw messages - no preprocessing or reformatting.
|
21
|
-
def fetch_loop
|
22
|
-
send(
|
23
|
-
consumer_group.batch_fetching ? :consume_each_batch : :consume_each_message
|
24
|
-
) { |messages| yield(messages) }
|
25
|
-
rescue Kafka::ProcessingError => e
|
26
|
-
# If there was an error during consumption, we have to log it, pause current partition
|
27
|
-
# and process other things
|
28
|
-
Karafka.monitor.notice_error(self.class, e.cause)
|
29
|
-
pause(e.topic, e.partition)
|
30
|
-
retry
|
31
|
-
# This is on purpose - see the notes for this method
|
32
|
-
# rubocop:disable RescueException
|
33
|
-
rescue Exception => e
|
34
|
-
# rubocop:enable RescueException
|
35
|
-
Karafka.monitor.notice_error(self.class, e)
|
36
|
-
retry
|
37
|
-
end
|
38
|
-
|
39
|
-
# Gracefuly stops topic consumption
|
40
|
-
# @note Stopping running consumers without a really important reason is not recommended
|
41
|
-
# as until all the consumers are stopped, the server will keep running serving only
|
42
|
-
# part of the messages
|
43
|
-
def stop
|
44
|
-
@kafka_consumer&.stop
|
45
|
-
@kafka_consumer = nil
|
46
|
-
end
|
47
|
-
|
48
|
-
# Pauses fetching and consumption of a given topic partition
|
49
|
-
# @param topic [String] topic that we want to pause
|
50
|
-
# @param partition [Integer] number partition that we want to pause
|
51
|
-
def pause(topic, partition)
|
52
|
-
settings = ConfigAdapter.pausing(consumer_group)
|
53
|
-
timeout = settings[:timeout]
|
54
|
-
raise(Errors::InvalidPauseTimeout, timeout) unless timeout.positive?
|
55
|
-
kafka_consumer.pause(topic, partition, settings)
|
56
|
-
end
|
57
|
-
|
58
|
-
# Marks a given message as consumed and commit the offsets
|
59
|
-
# @note In opposite to ruby-kafka, we commit the offset for each manual marking to be sure
|
60
|
-
# that offset commit happen asap in case of a crash
|
61
|
-
# @param [Karafka::Params::Params] params message that we want to mark as processed
|
62
|
-
def mark_as_consumed(params)
|
63
|
-
kafka_consumer.mark_message_as_processed(params)
|
64
|
-
# Trigger an immediate, blocking offset commit in order to minimize the risk of crashing
|
65
|
-
# before the automatic triggers have kicked in.
|
66
|
-
kafka_consumer.commit_offsets
|
67
|
-
end
|
68
|
-
|
69
|
-
private
|
70
|
-
|
71
|
-
attr_reader :consumer_group
|
72
|
-
|
73
|
-
# Consumes messages from Kafka in batches
|
74
|
-
# @yieldparam [Array<Kafka::FetchedMessage>] kafka fetched messages
|
75
|
-
def consume_each_batch
|
76
|
-
kafka_consumer.each_batch(
|
77
|
-
ConfigAdapter.consuming(consumer_group)
|
78
|
-
) do |batch|
|
79
|
-
yield(batch.messages)
|
80
|
-
end
|
81
|
-
end
|
82
|
-
|
83
|
-
# Consumes messages from Kafka one by one
|
84
|
-
# @yieldparam [Array<Kafka::FetchedMessage>] kafka fetched messages
|
85
|
-
def consume_each_message
|
86
|
-
kafka_consumer.each_message(
|
87
|
-
ConfigAdapter.consuming(consumer_group)
|
88
|
-
) do |message|
|
89
|
-
# always yield an array of messages, so we have consistent API (always a batch)
|
90
|
-
yield([message])
|
91
|
-
end
|
92
|
-
end
|
93
|
-
|
94
|
-
# @return [Kafka::Consumer] returns a ready to consume Kafka consumer
|
95
|
-
# that is set up to consume from topics of a given consumer group
|
96
|
-
def kafka_consumer
|
97
|
-
@kafka_consumer ||= kafka.consumer(
|
98
|
-
ConfigAdapter.consumer(consumer_group)
|
99
|
-
).tap do |consumer|
|
100
|
-
consumer_group.topics.each do |topic|
|
101
|
-
consumer.subscribe(*ConfigAdapter.subscription(topic))
|
102
|
-
end
|
103
|
-
end
|
104
|
-
rescue Kafka::ConnectionError
|
105
|
-
# If we would not wait it would totally spam log file with failed
|
106
|
-
# attempts if Kafka is down
|
107
|
-
sleep(consumer_group.reconnect_timeout)
|
108
|
-
# We don't log and just reraise - this will be logged
|
109
|
-
# down the road
|
110
|
-
raise
|
111
|
-
end
|
112
|
-
|
113
|
-
# @return [Kafka] returns a Kafka
|
114
|
-
# @note We don't cache it internally because we cache kafka_consumer that uses kafka
|
115
|
-
# object instance
|
116
|
-
def kafka
|
117
|
-
Kafka.new(ConfigAdapter.client(consumer_group))
|
118
|
-
end
|
119
|
-
end
|
120
|
-
end
|
121
|
-
end
|
@@ -1,61 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
module Connection
|
5
|
-
# Class that consumes messages for which we listen
|
6
|
-
module Processor
|
7
|
-
class << self
|
8
|
-
# Processes messages (does something with them)
|
9
|
-
# It will either schedule or run a proper controller action for messages
|
10
|
-
# @note This should be looped to obtain a constant listening
|
11
|
-
# @note We catch all the errors here, to make sure that none failures
|
12
|
-
# for a given consumption will affect other consumed messages
|
13
|
-
# If we wouldn't catch it, it would propagate up until killing the thread
|
14
|
-
# @param group_id [String] group_id of a group from which a given message came
|
15
|
-
# @param kafka_messages [Array<Kafka::FetchedMessage>] raw messages fetched from kafka
|
16
|
-
def process(group_id, kafka_messages)
|
17
|
-
# @note We always get messages by topic and partition so we can take topic from the
|
18
|
-
# first one and it will be valid for all the messages
|
19
|
-
# We map from incoming topic name, as it might be namespaced, etc.
|
20
|
-
# @see topic_mapper internal docs
|
21
|
-
mapped_topic_name = Karafka::App.config.topic_mapper.incoming(kafka_messages[0].topic)
|
22
|
-
topic = Routing::Router.find("#{group_id}_#{mapped_topic_name}")
|
23
|
-
controller = Persistence::Controller.fetch(topic, kafka_messages[0].partition) do
|
24
|
-
topic.controller.new
|
25
|
-
end
|
26
|
-
|
27
|
-
# Depending on a case (persisted or not) we might use new controller instance per each
|
28
|
-
# batch, or use the same instance for all of them (for implementing buffering, etc)
|
29
|
-
send(
|
30
|
-
topic.batch_consuming ? :process_batch : :process_each,
|
31
|
-
controller,
|
32
|
-
kafka_messages
|
33
|
-
)
|
34
|
-
end
|
35
|
-
|
36
|
-
private
|
37
|
-
|
38
|
-
# Processes whole batch in one request (all at once)
|
39
|
-
# @param controller [Karafka::BaseController] base controller descendant
|
40
|
-
# @param kafka_messages [Array<Kafka::FetchedMessage>] raw messages from kafka
|
41
|
-
def process_batch(controller, kafka_messages)
|
42
|
-
controller.params_batch = kafka_messages
|
43
|
-
Karafka.monitor.notice(self, kafka_messages)
|
44
|
-
controller.call
|
45
|
-
end
|
46
|
-
|
47
|
-
# Processes messages one by one (like with std http requests)
|
48
|
-
# @param controller [Karafka::BaseController] base controller descendant
|
49
|
-
# @param kafka_messages [Array<Kafka::FetchedMessage>] raw messages from kafka
|
50
|
-
def process_each(controller, kafka_messages)
|
51
|
-
kafka_messages.each do |kafka_message|
|
52
|
-
# @note This is a simple trick - we just process one after another, but in order
|
53
|
-
# not to handle everywhere both cases (single vs batch), we just "fake" batching with
|
54
|
-
# a single message for each
|
55
|
-
process_batch(controller, [kafka_message])
|
56
|
-
end
|
57
|
-
end
|
58
|
-
end
|
59
|
-
end
|
60
|
-
end
|
61
|
-
end
|
@@ -1,54 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
module Controllers
|
5
|
-
# Additional callbacks that can be used to trigger some actions on certain moments like
|
6
|
-
# manual offset management, committing or anything else outside of a standard messages flow
|
7
|
-
# They are not included by default, as we don't want to provide functionalities that are
|
8
|
-
# not required by users by default
|
9
|
-
# Please refer to the wiki callbacks page for more details on how to use them
|
10
|
-
module Callbacks
|
11
|
-
# Types of events on which we run callbacks
|
12
|
-
TYPES = %i[
|
13
|
-
after_fetched
|
14
|
-
after_poll
|
15
|
-
before_poll
|
16
|
-
before_stop
|
17
|
-
].freeze
|
18
|
-
|
19
|
-
# Class methods needed to make callbacks run
|
20
|
-
module ClassMethods
|
21
|
-
TYPES.each do |type|
|
22
|
-
# A Creates a callback wrapper
|
23
|
-
# @param method_name [Symbol, String] method name or nil if we plan to provide a block
|
24
|
-
# @yield A block with a code that should be executed before scheduling
|
25
|
-
define_method type do |method_name = nil, &block|
|
26
|
-
set_callback type, :before, method_name ? method_name : block
|
27
|
-
end
|
28
|
-
end
|
29
|
-
end
|
30
|
-
|
31
|
-
# @param controller_class [Class] controller class that we extend with callbacks
|
32
|
-
def self.included(controller_class)
|
33
|
-
controller_class.class_eval do
|
34
|
-
extend ClassMethods
|
35
|
-
include ActiveSupport::Callbacks
|
36
|
-
|
37
|
-
# The call method is wrapped with a set of callbacks
|
38
|
-
# We won't run process if any of the callbacks throw abort
|
39
|
-
# @see http://api.rubyonrails.org/classes/ActiveSupport/Callbacks/ClassMethods.html#method-i-get_callbacks
|
40
|
-
TYPES.each { |type| define_callbacks type }
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
# Executes the default controller flow, runs callbacks and if not halted will call process
|
45
|
-
# method of a proper backend. This is here because it interacts with the default Karafka
|
46
|
-
# call flow and needs to be overwritten in order to support callbacks
|
47
|
-
def call
|
48
|
-
run_callbacks :after_fetched do
|
49
|
-
process
|
50
|
-
end
|
51
|
-
end
|
52
|
-
end
|
53
|
-
end
|
54
|
-
end
|
@@ -1,51 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
# Additional functionalities for controllers
|
5
|
-
module Controllers
|
6
|
-
# Module used to inject functionalities into a given controller class, based on the controller
|
7
|
-
# topic and its settings
|
8
|
-
# We don't need all the behaviors in all the cases, so it is totally not worth having
|
9
|
-
# everything in all the cases all the time
|
10
|
-
module Includer
|
11
|
-
class << self
|
12
|
-
# @param controller_class [Class] controller class, that will get some functionalities
|
13
|
-
# based on the topic under which it operates
|
14
|
-
def call(controller_class)
|
15
|
-
topic = controller_class.topic
|
16
|
-
|
17
|
-
bind_backend(controller_class, topic)
|
18
|
-
bind_params(controller_class, topic)
|
19
|
-
bind_responders(controller_class, topic)
|
20
|
-
end
|
21
|
-
|
22
|
-
private
|
23
|
-
|
24
|
-
# Figures out backend for a given controller class, based on the topic backend and
|
25
|
-
# includes it into the controller class
|
26
|
-
# @param controller_class [Class] controller class
|
27
|
-
# @param topic [Karafka::Routing::Topic] topic of a controller class
|
28
|
-
def bind_backend(controller_class, topic)
|
29
|
-
backend = Kernel.const_get("::Karafka::Backends::#{topic.backend.to_s.capitalize}")
|
30
|
-
controller_class.include backend
|
31
|
-
end
|
32
|
-
|
33
|
-
# Adds a single #params support for non batch processed topics
|
34
|
-
# @param controller_class [Class] controller class
|
35
|
-
# @param topic [Karafka::Routing::Topic] topic of a controller class
|
36
|
-
def bind_params(controller_class, topic)
|
37
|
-
return if topic.batch_consuming
|
38
|
-
controller_class.include SingleParams
|
39
|
-
end
|
40
|
-
|
41
|
-
# Adds responders support for topics and controllers with responders defined for them
|
42
|
-
# @param controller_class [Class] controller class
|
43
|
-
# @param topic [Karafka::Routing::Topic] topic of a controller class
|
44
|
-
def bind_responders(controller_class, topic)
|
45
|
-
return unless topic.responder
|
46
|
-
controller_class.include Responders
|
47
|
-
end
|
48
|
-
end
|
49
|
-
end
|
50
|
-
end
|
51
|
-
end
|
@@ -1,19 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
module Controllers
|
5
|
-
# Feature that allows us to use responders flow in controller
|
6
|
-
module Responders
|
7
|
-
# Responds with given data using given responder. This allows us to have a similar way of
|
8
|
-
# defining flows like synchronous protocols
|
9
|
-
# @param data Anything we want to pass to responder based on which we want to trigger further
|
10
|
-
# Kafka responding
|
11
|
-
def respond_with(*data)
|
12
|
-
Karafka.monitor.notice(self.class, data: data)
|
13
|
-
# @note we build a new instance of responder each time, as a long running (persisted)
|
14
|
-
# controllers can respond multiple times during the lifecycle
|
15
|
-
topic.responder.new(topic.parser).call(*data)
|
16
|
-
end
|
17
|
-
end
|
18
|
-
end
|
19
|
-
end
|
data/lib/karafka/loader.rb
DELETED
@@ -1,29 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
# Loader for requiring all the files in a proper order
|
5
|
-
module Loader
|
6
|
-
# Order in which we want to load app files
|
7
|
-
DIRS = %w[
|
8
|
-
config/initializers
|
9
|
-
lib
|
10
|
-
app
|
11
|
-
].freeze
|
12
|
-
|
13
|
-
# Will load files in a proper order (based on DIRS)
|
14
|
-
# @param [String] root path from which we want to start
|
15
|
-
def self.load(root)
|
16
|
-
DIRS.each do |dir|
|
17
|
-
path = File.join(root, dir)
|
18
|
-
next unless File.exist?(path)
|
19
|
-
load!(path)
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
|
-
# Requires all the ruby files from one path in a proper order
|
24
|
-
# @param path [String] path (dir) from which we want to load ruby files in a proper order
|
25
|
-
def self.load!(path)
|
26
|
-
require_all(path)
|
27
|
-
end
|
28
|
-
end
|
29
|
-
end
|
data/lib/karafka/logger.rb
DELETED
@@ -1,53 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Karafka
|
4
|
-
# Default logger for Event Delegator
|
5
|
-
# @note It uses ::Logger features - providing basic logging
|
6
|
-
class Logger < ::Logger
|
7
|
-
include Singleton
|
8
|
-
|
9
|
-
# Map containing informations about log level for given environment
|
10
|
-
ENV_MAP = {
|
11
|
-
'production' => ::Logger::ERROR,
|
12
|
-
'test' => ::Logger::ERROR,
|
13
|
-
'development' => ::Logger::INFO,
|
14
|
-
'debug' => ::Logger::DEBUG,
|
15
|
-
default: ::Logger::INFO
|
16
|
-
}.freeze
|
17
|
-
|
18
|
-
# Creates a new instance of logger ensuring that it has a place to write to
|
19
|
-
def initialize(*_args)
|
20
|
-
ensure_dir_exists
|
21
|
-
super(target)
|
22
|
-
self.level = ENV_MAP[Karafka.env] || ENV_MAP[:default]
|
23
|
-
end
|
24
|
-
|
25
|
-
private
|
26
|
-
|
27
|
-
# @return [Karafka::Helpers::MultiDelegator] multi delegator instance
|
28
|
-
# to which we will be writtng logs
|
29
|
-
# We use this approach to log stuff to file and to the STDOUT at the same time
|
30
|
-
def target
|
31
|
-
Karafka::Helpers::MultiDelegator
|
32
|
-
.delegate(:write, :close)
|
33
|
-
.to(STDOUT, file)
|
34
|
-
end
|
35
|
-
|
36
|
-
# Makes sure the log directory exists
|
37
|
-
def ensure_dir_exists
|
38
|
-
dir = File.dirname(log_path)
|
39
|
-
FileUtils.mkdir_p(dir) unless Dir.exist?(dir)
|
40
|
-
end
|
41
|
-
|
42
|
-
# @return [Pathname] Path to a file to which we should log
|
43
|
-
def log_path
|
44
|
-
@log_path ||= Karafka::App.root.join("log/#{Karafka.env}.log")
|
45
|
-
end
|
46
|
-
|
47
|
-
# @return [File] file to which we want to write our logs
|
48
|
-
# @note File is being opened in append mode ('a')
|
49
|
-
def file
|
50
|
-
@file ||= File.open(log_path, 'a')
|
51
|
-
end
|
52
|
-
end
|
53
|
-
end
|