deimos-ruby 1.16.3 → 1.16.5

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 (84) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ci.yml +3 -3
  3. data/.gitignore +1 -0
  4. data/.rubocop.yml +20 -14
  5. data/.rubocop_todo.yml +364 -0
  6. data/.ruby-version +2 -1
  7. data/CHANGELOG.md +9 -0
  8. data/Gemfile +6 -0
  9. data/README.md +7 -1
  10. data/Steepfile +6 -0
  11. data/deimos-ruby.gemspec +3 -2
  12. data/lib/deimos/active_record_consume/batch_consumption.rb +7 -2
  13. data/lib/deimos/active_record_consume/batch_slicer.rb +2 -0
  14. data/lib/deimos/active_record_consume/message_consumption.rb +8 -4
  15. data/lib/deimos/active_record_consumer.rb +7 -4
  16. data/lib/deimos/active_record_producer.rb +3 -0
  17. data/lib/deimos/backends/base.rb +4 -2
  18. data/lib/deimos/backends/kafka.rb +1 -0
  19. data/lib/deimos/backends/kafka_async.rb +1 -0
  20. data/lib/deimos/config/configuration.rb +4 -0
  21. data/lib/deimos/config/phobos_config.rb +2 -1
  22. data/lib/deimos/consume/batch_consumption.rb +8 -1
  23. data/lib/deimos/consume/message_consumption.rb +4 -1
  24. data/lib/deimos/instrumentation.rb +11 -4
  25. data/lib/deimos/kafka_message.rb +1 -0
  26. data/lib/deimos/kafka_source.rb +5 -0
  27. data/lib/deimos/kafka_topic_info.rb +4 -0
  28. data/lib/deimos/message.rb +19 -2
  29. data/lib/deimos/metrics/datadog.rb +2 -1
  30. data/lib/deimos/metrics/mock.rb +2 -2
  31. data/lib/deimos/metrics/provider.rb +6 -0
  32. data/lib/deimos/monkey_patches/phobos_cli.rb +1 -1
  33. data/lib/deimos/monkey_patches/phobos_producer.rb +1 -0
  34. data/lib/deimos/producer.rb +12 -6
  35. data/lib/deimos/schema_backends/base.rb +31 -17
  36. data/lib/deimos/schema_backends/mock.rb +2 -2
  37. data/lib/deimos/schema_class/base.rb +9 -5
  38. data/lib/deimos/schema_class/enum.rb +4 -2
  39. data/lib/deimos/schema_class/record.rb +5 -5
  40. data/lib/deimos/shared_config.rb +6 -2
  41. data/lib/deimos/test_helpers.rb +21 -4
  42. data/lib/deimos/tracing/datadog.rb +1 -1
  43. data/lib/deimos/tracing/mock.rb +4 -3
  44. data/lib/deimos/tracing/provider.rb +5 -0
  45. data/lib/deimos/utils/db_poller.rb +9 -1
  46. data/lib/deimos/utils/db_producer.rb +14 -2
  47. data/lib/deimos/utils/deadlock_retry.rb +3 -0
  48. data/lib/deimos/utils/inline_consumer.rb +14 -6
  49. data/lib/deimos/utils/lag_reporter.rb +11 -0
  50. data/lib/deimos/utils/schema_controller_mixin.rb +8 -0
  51. data/lib/deimos/version.rb +1 -1
  52. data/lib/deimos.rb +3 -2
  53. data/lib/generators/deimos/active_record_generator.rb +1 -1
  54. data/lib/generators/deimos/db_backend_generator.rb +1 -0
  55. data/lib/generators/deimos/db_poller_generator.rb +1 -0
  56. data/lib/generators/deimos/schema_class/templates/schema_record.rb.tt +1 -1
  57. data/lib/generators/deimos/schema_class_generator.rb +13 -4
  58. data/rbs_collection.lock.yaml +176 -0
  59. data/rbs_collection.yaml +15 -0
  60. data/sig/avro.rbs +14 -0
  61. data/sig/defs.rbs +1867 -0
  62. data/sig/fig_tree.rbs +2 -0
  63. data/spec/consumer_spec.rb +14 -14
  64. data/spec/generators/schema_class/my_schema_spec.rb +3 -3
  65. data/spec/generators/schema_class/my_schema_with_complex_types_spec.rb +1 -1
  66. data/spec/producer_spec.rb +1 -1
  67. data/spec/schemas/my_namespace/my_schema_with_complex_type.rb +3 -3
  68. data/spec/snapshots/consumers-no-nest.snap +1 -1
  69. data/spec/snapshots/consumers.snap +1 -1
  70. data/spec/snapshots/consumers_and_producers-no-nest.snap +3 -3
  71. data/spec/snapshots/consumers_and_producers.snap +3 -3
  72. data/spec/snapshots/consumers_circular-no-nest.snap +1 -1
  73. data/spec/snapshots/consumers_circular.snap +1 -1
  74. data/spec/snapshots/consumers_complex_types-no-nest.snap +1 -1
  75. data/spec/snapshots/consumers_complex_types.snap +1 -1
  76. data/spec/snapshots/consumers_nested-no-nest.snap +1 -1
  77. data/spec/snapshots/consumers_nested.snap +1 -1
  78. data/spec/snapshots/namespace_folders.snap +3 -3
  79. data/spec/snapshots/producers_with_key-no-nest.snap +1 -1
  80. data/spec/snapshots/producers_with_key.snap +1 -1
  81. metadata +39 -21
  82. data/.gemfiles/avro_turf-0.gemfile +0 -3
  83. data/.gemfiles/avro_turf-1.gemfile +0 -3
  84. data/.ruby-gemset +0 -1
@@ -7,23 +7,26 @@ module Deimos
7
7
  # Base Class for Schema Classes generated from Avro.
8
8
  class Base
9
9
 
10
- # :nodoc:
10
+ # @param _args [Array<Object>]
11
11
  def initialize(*_args)
12
12
  end
13
13
 
14
14
  # Converts the object to a hash which can be used for debugging or comparing objects.
15
+ # @param _opts [Hash]
15
16
  # @return [Hash] a hash representation of the payload
16
17
  def as_json(_opts={})
17
18
  raise NotImplementedError
18
19
  end
19
20
 
20
- # @param key [String|Symbol]
21
+ # @param key [String,Symbol]
21
22
  # @param val [Object]
23
+ # @return [void]
22
24
  def []=(key, val)
23
25
  self.send("#{key}=", val)
24
26
  end
25
27
 
26
- # :nodoc:
28
+ # @param other [SchemaClass::Base]
29
+ # @return [Boolean]
27
30
  def ==(other)
28
31
  comparison = other
29
32
  if other.class == self.class
@@ -33,7 +36,7 @@ module Deimos
33
36
  comparison == self.as_json
34
37
  end
35
38
 
36
- # :nodoc:
39
+ # @return [String]
37
40
  def inspect
38
41
  klass = self.class
39
42
  "#{klass}(#{self.as_json})"
@@ -41,13 +44,14 @@ module Deimos
41
44
 
42
45
  # Initializes this class from a given value
43
46
  # @param value [Object]
47
+ # @return [SchemaClass::Base]
44
48
  def self.initialize_from_value(value)
45
49
  raise NotImplementedError
46
50
  end
47
51
 
48
52
  protected
49
53
 
50
- # :nodoc:
54
+ # @return [Integer]
51
55
  def hash
52
56
  as_json.hash
53
57
  end
@@ -8,9 +8,11 @@ module Deimos
8
8
  # Base Class for Enum Classes generated from Avro.
9
9
  class Enum < Base
10
10
 
11
+ # @return [String]
11
12
  attr_accessor :value
12
13
 
13
14
  # @param other [Deimos::SchemaClass::Enum]
15
+ # @return [Boolean]
14
16
  def ==(other)
15
17
  other.is_a?(self.class) ? other.value == @value : other == @value
16
18
  end
@@ -31,12 +33,12 @@ module Deimos
31
33
  raise NotImplementedError
32
34
  end
33
35
 
34
- # :nodoc:
36
+ # @return [String]
35
37
  def as_json(_opts={})
36
38
  @value
37
39
  end
38
40
 
39
- # :nodoc:
41
+ # @return [SchemaClass::Enum]
40
42
  def self.initialize_from_value(value)
41
43
  return nil if value.nil?
42
44
 
@@ -21,8 +21,8 @@ module Deimos
21
21
  end
22
22
 
23
23
  # Merge a hash or an identical schema object with this one and return a new object.
24
- # @param other_hash [Hash|SchemaClasses::Base]
25
- # @return [SchemaClasses::Base]
24
+ # @param other_hash [Hash,SchemaClass::Base]
25
+ # @return [SchemaClass::Base]
26
26
  def merge(other_hash)
27
27
  obj = self.class.new(**self.to_h.symbolize_keys)
28
28
  other_hash.to_h.each do |k, v|
@@ -32,13 +32,13 @@ module Deimos
32
32
  end
33
33
 
34
34
  # Element access method as if this Object were a hash
35
- # @param key[String||Symbol]
35
+ # @param key[String,Symbol]
36
36
  # @return [Object] The value of the attribute if exists, nil otherwise
37
37
  def [](key)
38
38
  self.try(key.to_sym)
39
39
  end
40
40
 
41
- # :nodoc
41
+ # @return [SchemaClass::Record]
42
42
  def with_indifferent_access
43
43
  self
44
44
  end
@@ -72,7 +72,7 @@ module Deimos
72
72
  validator.schema_fields.map(&:name)
73
73
  end
74
74
 
75
- # :nodoc:
75
+ # @return [SchemaClass::Record]
76
76
  def self.initialize_from_value(value)
77
77
  return nil if value.nil?
78
78
 
@@ -35,12 +35,14 @@ module Deimos
35
35
 
36
36
  # Set the schema.
37
37
  # @param schema [String]
38
+ # @return [void]
38
39
  def schema(schema)
39
40
  config[:schema] = schema
40
41
  end
41
42
 
42
43
  # Set the namespace.
43
44
  # @param namespace [String]
45
+ # @return [void]
44
46
  def namespace(namespace)
45
47
  config[:namespace] = namespace
46
48
  end
@@ -48,9 +50,10 @@ module Deimos
48
50
  # Set key configuration.
49
51
  # @param field [Symbol] the name of a field to use in the value schema as
50
52
  # a generated key schema
51
- # @param schema [String|Symbol] the name of a schema to use for the key
53
+ # @param schema [String, Symbol] the name of a schema to use for the key
52
54
  # @param plain [Boolean] if true, do not encode keys at all
53
55
  # @param none [Boolean] if true, do not use keys at all
56
+ # @return [void]
54
57
  def key_config(plain: nil, field: nil, schema: nil, none: nil)
55
58
  config[:key_configured] = true
56
59
  config[:no_keys] = none
@@ -59,7 +62,8 @@ module Deimos
59
62
  config[:key_schema] = schema
60
63
  end
61
64
 
62
- # @param enabled [Boolean]
65
+ # @param use_schema_classes [Boolean]
66
+ # @return [void]
63
67
  def schema_class_config(use_schema_classes)
64
68
  config[:use_schema_classes] = use_schema_classes
65
69
  end
@@ -20,6 +20,7 @@ module Deimos
20
20
  end
21
21
 
22
22
  # Set the config to the right settings for a unit test
23
+ # @return [void]
23
24
  def unit_test!
24
25
  Deimos.configure do |deimos_config|
25
26
  deimos_config.logger = Logger.new(STDOUT)
@@ -31,6 +32,7 @@ module Deimos
31
32
  end
32
33
 
33
34
  # Kafka test config with avro schema registry
35
+ # @return [void]
34
36
  def full_integration_test!
35
37
  Deimos.configure do |deimos_config|
36
38
  deimos_config.producers.backend = :kafka
@@ -39,6 +41,7 @@ module Deimos
39
41
  end
40
42
 
41
43
  # Set the config to the right settings for a kafka test
44
+ # @return [void]
42
45
  def kafka_test!
43
46
  Deimos.configure do |deimos_config|
44
47
  deimos_config.producers.backend = :kafka
@@ -62,21 +65,25 @@ module Deimos
62
65
  end
63
66
 
64
67
  # @deprecated
68
+ # @!visibility private
65
69
  def stub_producers_and_consumers!
66
70
  warn('stub_producers_and_consumers! is no longer necessary and this method will be removed in 3.0')
67
71
  end
68
72
 
69
73
  # @deprecated
74
+ # @!visibility private
70
75
  def stub_producer(_klass)
71
76
  warn('Stubbing producers is no longer necessary and this method will be removed in 3.0')
72
77
  end
73
78
 
74
79
  # @deprecated
80
+ # @!visibility private
75
81
  def stub_consumer(_klass)
76
82
  warn('Stubbing consumers is no longer necessary and this method will be removed in 3.0')
77
83
  end
78
84
 
79
85
  # @deprecated
86
+ # @!visibility private
80
87
  def stub_batch_consumer(_klass)
81
88
  warn('Stubbing batch consumers is no longer necessary and this method will be removed in 3.0')
82
89
  end
@@ -84,6 +91,7 @@ module Deimos
84
91
  # get the difference of 2 hashes.
85
92
  # @param hash1 [Hash]
86
93
  # @param hash2 [Hash]
94
+ # @!visibility private
87
95
  def _hash_diff(hash1, hash2)
88
96
  if hash1.nil? || !hash1.is_a?(Hash)
89
97
  hash2
@@ -96,7 +104,7 @@ module Deimos
96
104
  end
97
105
  end
98
106
 
99
- # :nodoc:
107
+ # @!visibility private
100
108
  def _frk_failure_message(topic, message, key=nil, partition_key=nil, was_negated=false)
101
109
  messages = Deimos::Backends::Test.sent_messages.
102
110
  select { |m| m[:topic] == topic }.
@@ -162,6 +170,7 @@ module Deimos
162
170
 
163
171
  # Clear all sent messages - e.g. if we want to check that
164
172
  # particular messages were sent or not sent after a point in time.
173
+ # @return [void]
165
174
  def clear_kafka_messages!
166
175
  Deimos::Backends::Test.sent_messages.clear
167
176
  end
@@ -170,15 +179,16 @@ module Deimos
170
179
  # that the schema is correct. If
171
180
  # a block is given, that block will be executed when `consume` is called.
172
181
  # Otherwise it will just confirm that `consume` is called at all.
173
- # @param handler_class_or_topic [Class|String] Class which inherits from
182
+ # @param handler_class_or_topic [Class, String] Class which inherits from
174
183
  # Deimos::Consumer or the topic as a string
175
184
  # @param payload [Hash] the payload to consume
176
185
  # @param call_original [Boolean] if true, allow the consume handler
177
186
  # to continue as normal. Not compatible with a block.
178
- # @param ignore_expectation [Boolean] Set to true to not place any
187
+ # @param skip_expectation [Boolean] Set to true to not place any
179
188
  # expectations on the consumer. Primarily used internally to Deimos.
180
189
  # @param key [Object] the key to use.
181
190
  # @param partition_key [Object] the partition key to use.
191
+ # @return [void]
182
192
  def test_consume_message(handler_class_or_topic,
183
193
  payload,
184
194
  call_original: false,
@@ -225,6 +235,7 @@ module Deimos
225
235
  # Check to see that a given message will fail due to validation errors.
226
236
  # @param handler_class [Class]
227
237
  # @param payload [Hash]
238
+ # @return [void]
228
239
  def test_consume_invalid_message(handler_class, payload)
229
240
  expect {
230
241
  handler_class.decoder.validate(payload,
@@ -236,9 +247,14 @@ module Deimos
236
247
  # i.e. that the schema is correct. If
237
248
  # a block is given, that block will be executed when `consume` is called.
238
249
  # Otherwise it will just confirm that `consume` is called at all.
239
- # @param handler_class_or_topic [Class|String] Class which inherits from
250
+ # @param handler_class_or_topic [Class, String] Class which inherits from
240
251
  # Deimos::Consumer or the topic as a string
241
252
  # @param payloads [Array<Hash>] the payload to consume
253
+ # @param keys [Array<Hash,String>]
254
+ # @param partition_keys [Array<Integer>]
255
+ # @param call_original [Boolean]
256
+ # @param skip_expectation [Boolean]
257
+ # @return [void]
242
258
  def test_consume_batch(handler_class_or_topic,
243
259
  payloads,
244
260
  keys: [],
@@ -297,6 +313,7 @@ module Deimos
297
313
  # Check to see that a given message will fail due to validation errors.
298
314
  # @param handler_class [Class]
299
315
  # @param payloads [Array<Hash>]
316
+ # @return [void]
300
317
  def test_consume_batch_invalid_message(handler_class, payloads)
301
318
  topic_name = 'my-topic'
302
319
  handler = handler_class.new
@@ -6,7 +6,7 @@ module Deimos
6
6
  module Tracing
7
7
  # Tracing wrapper class for Datadog.
8
8
  class Datadog < Tracing::Provider
9
- # :nodoc:
9
+ # @param config [Hash]
10
10
  def initialize(config)
11
11
  raise 'Tracing config must specify service_name' if config[:service_name].nil?
12
12
 
@@ -6,13 +6,14 @@ module Deimos
6
6
  module Tracing
7
7
  # Class that mocks out tracing functionality
8
8
  class Mock < Tracing::Provider
9
- # :nodoc:
9
+ # @param logger [Logger]
10
10
  def initialize(logger=nil)
11
11
  @logger = logger || Logger.new(STDOUT)
12
12
  @logger.info('MockTracingProvider initialized')
13
13
  end
14
14
 
15
- # :nodoc:
15
+ # @param span_name [String]
16
+ # @param _options [Hash]
16
17
  def start(span_name, _options={})
17
18
  @logger.info("Mock span '#{span_name}' started")
18
19
  {
@@ -35,7 +36,7 @@ module Deimos
35
36
  end
36
37
 
37
38
  # :nodoc:
38
- def set_tag(name, value)
39
+ def set_tag(tag, value, span=nil)
39
40
  nil
40
41
  end
41
42
 
@@ -14,6 +14,7 @@ module Deimos
14
14
 
15
15
  # Finishes the trace on the span object.
16
16
  # @param span [Object] The span to finish trace on
17
+ # @return [void]
17
18
  def finish(span)
18
19
  raise NotImplementedError
19
20
  end
@@ -21,11 +22,13 @@ module Deimos
21
22
  # Set an error on the span.
22
23
  # @param span [Object] The span to set error on
23
24
  # @param exception [Exception] The exception that occurred
25
+ # @return [void]
24
26
  def set_error(span, exception)
25
27
  raise NotImplementedError
26
28
  end
27
29
 
28
30
  # Get the currently activated span.
31
+ # @return [Object]
29
32
  def active_span
30
33
  raise NotImplementedError
31
34
  end
@@ -33,6 +36,8 @@ module Deimos
33
36
  # Set a tag to a span. Use the currently active span if not given.
34
37
  # @param tag [String]
35
38
  # @param value [String]
39
+ # @param span [Object]
40
+ # @return [void]
36
41
  def set_tag(tag, value, span=nil)
37
42
  raise NotImplementedError
38
43
  end
@@ -7,12 +7,15 @@ module Deimos
7
7
  module Utils
8
8
  # Class which continually polls the database and sends Kafka messages.
9
9
  class DbPoller
10
+ # @return [Integer]
10
11
  BATCH_SIZE = 1000
11
12
 
12
13
  # Needed for Executor so it can identify the worker
14
+ # @return [Integer]
13
15
  attr_reader :id
14
16
 
15
17
  # Begin the DB Poller process.
18
+ # @return [void]
16
19
  def self.start!
17
20
  if Deimos.config.db_poller_objects.empty?
18
21
  raise('No pollers configured!')
@@ -28,7 +31,7 @@ module Deimos
28
31
  signal_handler.run!
29
32
  end
30
33
 
31
- # @param config [Deimos::Configuration::ConfigStruct]
34
+ # @param config [FigTree::ConfigStruct]
32
35
  def initialize(config)
33
36
  @config = config
34
37
  @id = SecureRandom.hex
@@ -47,6 +50,7 @@ module Deimos
47
50
  # time we ran
48
51
  # 2) On a loop, process all the recent updates between the last time
49
52
  # we ran and now.
53
+ # @return [void]
50
54
  def start
51
55
  # Don't send asynchronously
52
56
  if Deimos.config.producers.backend == :kafka_async
@@ -66,6 +70,7 @@ module Deimos
66
70
  end
67
71
 
68
72
  # Grab the PollInfo or create if it doesn't exist.
73
+ # @return [void]
69
74
  def retrieve_poll_info
70
75
  ActiveRecord::Base.connection.reconnect! unless ActiveRecord::Base.connection.open_transactions.positive?
71
76
  new_time = @config.start_from_beginning ? Time.new(0) : Time.zone.now
@@ -76,6 +81,7 @@ module Deimos
76
81
  end
77
82
 
78
83
  # Stop the poll.
84
+ # @return [void]
79
85
  def stop
80
86
  Deimos.config.logger.info('Received signal to stop')
81
87
  @signal_to_stop = true
@@ -95,6 +101,7 @@ module Deimos
95
101
  end
96
102
 
97
103
  # Send messages for updated data.
104
+ # @return [void]
98
105
  def process_updates
99
106
  return unless should_run?
100
107
 
@@ -135,6 +142,7 @@ module Deimos
135
142
  end
136
143
 
137
144
  # @param batch [Array<ActiveRecord::Base>]
145
+ # @return [void]
138
146
  def process_batch(batch)
139
147
  record = batch.last
140
148
  id_method = record.class.primary_key
@@ -8,8 +8,11 @@ module Deimos
8
8
  include Phobos::Producer
9
9
  attr_accessor :id, :current_topic
10
10
 
11
+ # @return [Integer]
11
12
  BATCH_SIZE = 1000
13
+ # @return [Integer]
12
14
  DELETE_BATCH_SIZE = 10
15
+ # @return [Integer]
13
16
  MAX_DELETE_ATTEMPTS = 3
14
17
 
15
18
  # @param logger [Logger]
@@ -19,12 +22,13 @@ module Deimos
19
22
  @logger.push_tags("DbProducer #{@id}") if @logger.respond_to?(:push_tags)
20
23
  end
21
24
 
22
- # @return [Deimos::DbProducerConfig]
25
+ # @return [FigTree]
23
26
  def config
24
27
  Deimos.config.db_producer
25
28
  end
26
29
 
27
30
  # Start the poll.
31
+ # @return [void]
28
32
  def start
29
33
  @logger.info('Starting...')
30
34
  @signal_to_stop = false
@@ -40,12 +44,14 @@ module Deimos
40
44
  end
41
45
 
42
46
  # Stop the poll.
47
+ # @return [void]
43
48
  def stop
44
49
  @logger.info('Received signal to stop')
45
50
  @signal_to_stop = true
46
51
  end
47
52
 
48
53
  # Complete one loop of processing all messages in the DB.
54
+ # @return [void]
49
55
  def process_next_messages
50
56
  topics = retrieve_topics
51
57
  @logger.info("Found topics: #{topics}")
@@ -80,6 +86,7 @@ module Deimos
80
86
  end
81
87
 
82
88
  # Process a single batch in a topic.
89
+ # @return [void]
83
90
  def process_topic_batch
84
91
  messages = retrieve_messages
85
92
  return false if messages.empty?
@@ -111,6 +118,7 @@ module Deimos
111
118
  end
112
119
 
113
120
  # @param messages [Array<Deimos::KafkaMessage>]
121
+ # @return [void]
114
122
  def delete_messages(messages)
115
123
  attempts = 1
116
124
  begin
@@ -137,6 +145,7 @@ module Deimos
137
145
  end
138
146
 
139
147
  # @param messages [Array<Deimos::KafkaMessage>]
148
+ # @return [void]
140
149
  def log_messages(messages)
141
150
  return if config.log_topics != :all && !config.log_topics.include?(@current_topic)
142
151
 
@@ -146,7 +155,8 @@ module Deimos
146
155
  end
147
156
  end
148
157
 
149
- # Send metrics to Datadog.
158
+ # Send metrics related to pending messages.
159
+ # @return [void]
150
160
  def send_pending_metrics
151
161
  metrics = Deimos.config.metrics
152
162
  return unless metrics
@@ -185,6 +195,7 @@ module Deimos
185
195
  # Shut down the sync producer if we have to. Phobos will automatically
186
196
  # create a new one. We should call this if the producer can be in a bad
187
197
  # state and e.g. we need to clear the buffer.
198
+ # @return [void]
188
199
  def shutdown_producer
189
200
  if self.class.producer.respond_to?(:sync_producer_shutdown) # Phobos 1.8.3
190
201
  self.class.producer.sync_producer_shutdown
@@ -194,6 +205,7 @@ module Deimos
194
205
  # Produce messages in batches, reducing the size 1/10 if the batch is too
195
206
  # large. Does not retry batches of messages that have already been sent.
196
207
  # @param batch [Array<Hash>]
208
+ # @return [void]
197
209
  def produce_messages(batch)
198
210
  batch_size = batch.size
199
211
  current_index = 0
@@ -7,9 +7,11 @@ module Deimos
7
7
  class DeadlockRetry
8
8
  class << self
9
9
  # Maximum number of times to retry the block after encountering a deadlock
10
+ # @return [Integer]
10
11
  RETRY_COUNT = 2
11
12
 
12
13
  # Need to match on error messages to support older Rails versions
14
+ # @return [Array<String>]
13
15
  DEADLOCK_MESSAGES = [
14
16
  # MySQL
15
17
  'Deadlock found when trying to get lock',
@@ -28,6 +30,7 @@ module Deimos
28
30
  # from retrying at the same time.
29
31
  # @param tags [Array] Tags to attach when logging and reporting metrics.
30
32
  # @yield Yields to the block that may deadlock.
33
+ # @return [void]
31
34
  def wrap(tags=[])
32
35
  count = RETRY_COUNT
33
36
 
@@ -6,10 +6,12 @@ module Deimos
6
6
  module Utils
7
7
  # Listener that can seek to get the last X messages in a topic.
8
8
  class SeekListener < Phobos::Listener
9
+ # @return [Integer]
9
10
  MAX_SEEK_RETRIES = 3
11
+ # @return [Integer]
10
12
  attr_accessor :num_messages
11
13
 
12
- # :nodoc:
14
+ # @return [void]
13
15
  def start_listener
14
16
  @num_messages ||= 10
15
17
  @consumer = create_kafka_consumer
@@ -45,17 +47,20 @@ module Deimos
45
47
 
46
48
  cattr_accessor :total_messages
47
49
 
48
- # @param klass [Class < Deimos::Consumer]
50
+ # @param klass [Class<Deimos::Consumer>]
51
+ # @return [void]
49
52
  def self.config_class=(klass)
50
53
  self.config.merge!(klass.config)
51
54
  end
52
55
 
53
- # :nodoc:
56
+ # @param _kafka_client [Kafka::Client]
57
+ # @return [void]
54
58
  def self.start(_kafka_client)
55
59
  self.total_messages = []
56
60
  end
57
61
 
58
- # :nodoc:
62
+ # @param payload [Hash]
63
+ # @param metadata [Hash]
59
64
  def consume(payload, metadata)
60
65
  self.class.total_messages << {
61
66
  key: metadata[:key],
@@ -66,18 +71,20 @@ module Deimos
66
71
 
67
72
  # Class which can process/consume messages inline.
68
73
  class InlineConsumer
74
+ # @return [Integer]
69
75
  MAX_MESSAGE_WAIT_TIME = 1.second
76
+ # @return [Integer]
70
77
  MAX_TOPIC_WAIT_TIME = 10.seconds
71
78
 
72
79
  # Get the last X messages from a topic. You can specify a subclass of
73
80
  # Deimos::Consumer or Deimos::Producer, or provide the
74
81
  # schema, namespace and key_config directly.
75
82
  # @param topic [String]
76
- # @param config_class [Class < Deimos::Consumer|Deimos::Producer>]
83
+ # @param config_class [Class<Deimos::Consumer>,Class<Deimos::Producer>]
77
84
  # @param schema [String]
78
85
  # @param namespace [String]
79
86
  # @param key_config [Hash]
80
- # @param num_messages [Number]
87
+ # @param num_messages [Integer]
81
88
  # @return [Array<Hash>]
82
89
  def self.get_messages_for(topic:, schema: nil, namespace: nil, key_config: nil,
83
90
  config_class: nil, num_messages: 10)
@@ -106,6 +113,7 @@ module Deimos
106
113
  # @param frk_consumer [Class]
107
114
  # @param num_messages [Integer] If this number is >= the number
108
115
  # of messages in the topic, all messages will be consumed.
116
+ # @return [void]
109
117
  def self.consume(topic:, frk_consumer:, num_messages: 10)
110
118
  listener = SeekListener.new(
111
119
  handler: frk_consumer,
@@ -24,6 +24,7 @@ module Deimos
24
24
 
25
25
  # @param topic [String]
26
26
  # @param partition [Integer]
27
+ # @return [void]
27
28
  def report_lag(topic, partition)
28
29
  self.topics[topic.to_s] ||= Topic.new(topic, self)
29
30
  self.topics[topic.to_s].report_lag(partition)
@@ -32,6 +33,7 @@ module Deimos
32
33
  # @param topic [String]
33
34
  # @param partition [Integer]
34
35
  # @param offset [Integer]
36
+ # @return [void]
35
37
  def assign_current_offset(topic, partition, offset)
36
38
  self.topics[topic.to_s] ||= Topic.new(topic, self)
37
39
  self.topics[topic.to_s].assign_current_offset(partition, offset)
@@ -56,11 +58,15 @@ module Deimos
56
58
  end
57
59
 
58
60
  # @param partition [Integer]
61
+ # @param offset [Integer]
62
+ # @return [void]
59
63
  def assign_current_offset(partition, offset)
60
64
  self.partition_current_offsets[partition.to_i] = offset
61
65
  end
62
66
 
63
67
  # @param partition [Integer]
68
+ # @param offset [Integer]
69
+ # @return [Integer]
64
70
  def compute_lag(partition, offset)
65
71
  begin
66
72
  client = Phobos.create_kafka_client
@@ -74,6 +80,7 @@ module Deimos
74
80
  end
75
81
 
76
82
  # @param partition [Integer]
83
+ # @return [void]
77
84
  def report_lag(partition)
78
85
  current_offset = self.partition_current_offsets[partition.to_i]
79
86
  return unless current_offset
@@ -94,6 +101,7 @@ module Deimos
94
101
 
95
102
  class << self
96
103
  # Reset all group information.
104
+ # @return [void]
97
105
  def reset
98
106
  @groups = {}
99
107
  end
@@ -103,6 +111,7 @@ module Deimos
103
111
  # topic = event.payload.fetch(:topic)
104
112
  # partition = event.payload.fetch(:partition)
105
113
  # @param payload [Hash]
114
+ # @return [void]
106
115
  def message_processed(payload)
107
116
  offset = payload[:offset] || payload[:last_offset]
108
117
  topic = payload[:topic]
@@ -116,6 +125,7 @@ module Deimos
116
125
  end
117
126
 
118
127
  # @param payload [Hash]
128
+ # @return [void]
119
129
  def offset_seek(payload)
120
130
  offset = payload[:offset]
121
131
  topic = payload[:topic]
@@ -129,6 +139,7 @@ module Deimos
129
139
  end
130
140
 
131
141
  # @param payload [Hash]
142
+ # @return [void]
132
143
  def heartbeat(payload)
133
144
  group = payload[:group_id]
134
145
  synchronize do