karafka 2.5.9 → 2.6.0.beta1

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 (471) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +34 -0
  3. data/certs/expired.txt +83 -0
  4. data/config/locales/errors.yml +17 -7
  5. data/karafka.gemspec +3 -3
  6. data/lib/active_job/queue_adapters/karafka_adapter.rb +1 -2
  7. data/lib/karafka/active_job/job_extensions.rb +1 -2
  8. data/lib/karafka/admin/configs/resource.rb +1 -2
  9. data/lib/karafka/admin/consumer_groups.rb +109 -98
  10. data/lib/karafka/admin/isolation_levels.rb +22 -0
  11. data/lib/karafka/admin/topics.rb +103 -8
  12. data/lib/karafka/admin.rb +59 -31
  13. data/lib/karafka/app.rb +16 -5
  14. data/lib/karafka/base_consumer.rb +2 -2
  15. data/lib/karafka/cli/contracts/server.rb +4 -4
  16. data/lib/karafka/cli/info.rb +1 -1
  17. data/lib/karafka/cli/topics/base.rb +10 -18
  18. data/lib/karafka/cli/topics/repartition.rb +1 -1
  19. data/lib/karafka/connection/client.rb +40 -9
  20. data/lib/karafka/connection/consumer_groups/rebalance_manager.rb +120 -0
  21. data/lib/karafka/connection/listener.rb +8 -7
  22. data/lib/karafka/connection/listeners_batch.rb +1 -1
  23. data/lib/karafka/connection/mode.rb +1 -2
  24. data/lib/karafka/connection/raw_messages_buffer.rb +0 -5
  25. data/lib/karafka/declaratives/builder.rb +65 -0
  26. data/lib/karafka/declaratives/contracts/topic.rb +28 -0
  27. data/lib/karafka/declaratives/repository.rb +52 -0
  28. data/lib/karafka/declaratives/topic.rb +100 -0
  29. data/lib/karafka/declaratives.rb +9 -0
  30. data/lib/karafka/helpers/interval_runner.rb +2 -2
  31. data/lib/karafka/instrumentation/assignments_tracker.rb +65 -2
  32. data/lib/karafka/instrumentation/callbacks/consumer_groups/error.rb +56 -0
  33. data/lib/karafka/instrumentation/callbacks/consumer_groups/rebalance.rb +93 -0
  34. data/lib/karafka/instrumentation/callbacks/consumer_groups/statistics.rb +59 -0
  35. data/lib/karafka/instrumentation/logger_listener.rb +27 -9
  36. data/lib/karafka/instrumentation/notifications.rb +2 -0
  37. data/lib/karafka/instrumentation/vendors/appsignal/metrics_listener.rb +14 -17
  38. data/lib/karafka/instrumentation/vendors/datadog/metrics_listener.rb +8 -9
  39. data/lib/karafka/instrumentation/vendors/kubernetes/base_listener.rb +7 -3
  40. data/lib/karafka/instrumentation/vendors/kubernetes/liveness_listener.rb +13 -10
  41. data/lib/karafka/licenser.rb +16 -3
  42. data/lib/karafka/pro/active_job/consumer.rb +1 -2
  43. data/lib/karafka/pro/active_job/dispatcher.rb +1 -2
  44. data/lib/karafka/pro/admin/recovery.rb +19 -19
  45. data/lib/karafka/pro/base_consumer.rb +3 -3
  46. data/lib/karafka/pro/cli/contracts/server.rb +5 -5
  47. data/lib/karafka/pro/cli/parallel_segments/base.rb +7 -7
  48. data/lib/karafka/pro/cli/parallel_segments/collapse.rb +4 -4
  49. data/lib/karafka/pro/cli/parallel_segments/distribute.rb +6 -6
  50. data/lib/karafka/pro/iterator/tpl_builder.rb +38 -18
  51. data/lib/karafka/pro/loader.rb +15 -12
  52. data/lib/karafka/pro/processing/consumer_groups/adaptive_iterator/consumer.rb +84 -0
  53. data/lib/karafka/pro/processing/consumer_groups/adaptive_iterator/tracker.rb +97 -0
  54. data/lib/karafka/pro/processing/consumer_groups/collapser.rb +84 -0
  55. data/lib/karafka/pro/processing/consumer_groups/coordinator.rb +202 -0
  56. data/lib/karafka/pro/processing/consumer_groups/coordinators/errors_tracker.rb +124 -0
  57. data/lib/karafka/pro/processing/consumer_groups/coordinators/filters_applier.rb +157 -0
  58. data/lib/karafka/pro/processing/consumer_groups/coordinators/virtual_offset_manager.rb +212 -0
  59. data/lib/karafka/pro/processing/{filters/expirer.rb → consumer_groups/executor.rb} +17 -31
  60. data/lib/karafka/pro/processing/{jobs/periodic.rb → consumer_groups/expansions_selector.rb} +18 -21
  61. data/lib/karafka/pro/processing/consumer_groups/filters/base.rb +103 -0
  62. data/lib/karafka/pro/processing/consumer_groups/filters/delayer.rb +92 -0
  63. data/lib/karafka/pro/processing/consumer_groups/filters/expirer.rb +78 -0
  64. data/lib/karafka/pro/processing/consumer_groups/filters/inline_insights_delayer.rb +99 -0
  65. data/lib/karafka/pro/processing/consumer_groups/filters/throttler.rb +106 -0
  66. data/lib/karafka/pro/processing/consumer_groups/filters/virtual_limiter.rb +79 -0
  67. data/lib/karafka/pro/processing/{jobs → consumer_groups/jobs}/consume_non_blocking.rb +21 -17
  68. data/lib/karafka/pro/processing/{virtual_partitions/distributors/consistent.rb → consumer_groups/jobs/eofed_non_blocking.rb} +16 -14
  69. data/lib/karafka/pro/processing/consumer_groups/jobs/periodic.rb +64 -0
  70. data/lib/karafka/pro/processing/{jobs → consumer_groups/jobs}/periodic_non_blocking.rb +16 -11
  71. data/lib/karafka/pro/processing/{jobs → consumer_groups/jobs}/revoked_non_blocking.rb +19 -15
  72. data/lib/karafka/pro/processing/consumer_groups/jobs_builder.rb +95 -0
  73. data/lib/karafka/pro/processing/consumer_groups/offset_metadata/consumer.rb +66 -0
  74. data/lib/karafka/pro/processing/consumer_groups/offset_metadata/fetcher.rb +154 -0
  75. data/lib/karafka/pro/processing/consumer_groups/offset_metadata/listener.rb +68 -0
  76. data/lib/karafka/pro/processing/consumer_groups/parallel_segments/filters/base.rb +102 -0
  77. data/lib/karafka/pro/processing/consumer_groups/parallel_segments/filters/default.rb +115 -0
  78. data/lib/karafka/pro/processing/consumer_groups/parallel_segments/filters/mom.rb +96 -0
  79. data/lib/karafka/pro/processing/consumer_groups/partitioner.rb +98 -0
  80. data/lib/karafka/pro/processing/consumer_groups/periodic_job/consumer.rb +90 -0
  81. data/lib/karafka/pro/processing/consumer_groups/piping/consumer.rb +154 -0
  82. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_ftr_lrj_mom.rb +93 -0
  83. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_ftr_lrj_mom_vp.rb +99 -0
  84. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_ftr_mom.rb +92 -0
  85. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_ftr_mom_vp.rb +90 -0
  86. data/lib/karafka/pro/processing/{strategies/aj/dlq_ftr_lrj_mom.rb → consumer_groups/strategies/aj/dlq_lrj_mom.rb} +37 -39
  87. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_lrj_mom_vp.rb +90 -0
  88. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_mom.rb +84 -0
  89. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/dlq_mom_vp.rb +89 -0
  90. data/lib/karafka/pro/processing/{strategies → consumer_groups/strategies}/aj/ftr_lrj_mom.rb +20 -15
  91. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/ftr_lrj_mom_vp.rb +91 -0
  92. data/lib/karafka/pro/processing/{strategies → consumer_groups/strategies}/aj/ftr_mom.rb +20 -15
  93. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/ftr_mom_vp.rb +80 -0
  94. data/lib/karafka/pro/processing/{strategies/mom/default.rb → consumer_groups/strategies/aj/lrj_mom.rb} +18 -22
  95. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/lrj_mom_vp.rb +106 -0
  96. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/mom.rb +58 -0
  97. data/lib/karafka/pro/processing/consumer_groups/strategies/aj/mom_vp.rb +74 -0
  98. data/lib/karafka/pro/processing/{strategies/lrj/vp.rb → consumer_groups/strategies/base.rb} +9 -14
  99. data/lib/karafka/pro/processing/consumer_groups/strategies/default.rb +421 -0
  100. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/default.rb +285 -0
  101. data/lib/karafka/pro/processing/{strategies/dlq/lrj.rb → consumer_groups/strategies/dlq/ftr.rb} +30 -29
  102. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/ftr_lrj.rb +95 -0
  103. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/ftr_lrj_mom.rb +97 -0
  104. data/lib/karafka/pro/processing/{executor.rb → consumer_groups/strategies/dlq/ftr_lrj_mom_vp.rb} +26 -15
  105. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/ftr_lrj_vp.rb +63 -0
  106. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/ftr_mom.rb +97 -0
  107. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/ftr_mom_vp.rb +63 -0
  108. data/lib/karafka/pro/{routing/features/patterns/patterns.rb → processing/consumer_groups/strategies/dlq/ftr_vp.rb} +22 -12
  109. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/lrj.rb +83 -0
  110. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/lrj_mom.rb +100 -0
  111. data/lib/karafka/pro/processing/{strategies → consumer_groups/strategies}/dlq/lrj_mom_vp.rb +18 -13
  112. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/lrj_vp.rb +61 -0
  113. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/mom.rb +96 -0
  114. data/lib/karafka/pro/processing/{strategies/lrj → consumer_groups/strategies/dlq}/mom_vp.rb +19 -15
  115. data/lib/karafka/pro/processing/consumer_groups/strategies/dlq/vp.rb +62 -0
  116. data/lib/karafka/pro/processing/consumer_groups/strategies/ftr/default.rb +146 -0
  117. data/lib/karafka/pro/processing/{strategies/mom/ftr.rb → consumer_groups/strategies/ftr/vp.rb} +20 -28
  118. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/default.rb +119 -0
  119. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/ftr.rb +94 -0
  120. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/ftr_mom.rb +92 -0
  121. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/ftr_mom_vp.rb +62 -0
  122. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/ftr_vp.rb +61 -0
  123. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/mom.rb +101 -0
  124. data/lib/karafka/pro/processing/consumer_groups/strategies/lrj/mom_vp.rb +60 -0
  125. data/lib/karafka/pro/processing/{strategies/mom → consumer_groups/strategies/lrj}/vp.rb +18 -12
  126. data/lib/karafka/pro/processing/{strategies/aj/mom_vp.rb → consumer_groups/strategies/mom/default.rb} +22 -23
  127. data/lib/karafka/pro/processing/{strategies/aj/ftr_mom_vp.rb → consumer_groups/strategies/mom/ftr.rb} +28 -28
  128. data/lib/karafka/pro/processing/{virtual_partitions/distributors/base.rb → consumer_groups/strategies/mom/ftr_vp.rb} +19 -14
  129. data/lib/karafka/pro/processing/{strategies/aj/mom.rb → consumer_groups/strategies/mom/vp.rb} +16 -12
  130. data/lib/karafka/pro/processing/consumer_groups/strategies/vp/default.rb +197 -0
  131. data/lib/karafka/pro/processing/consumer_groups/strategy_selector.rb +106 -0
  132. data/lib/karafka/pro/processing/consumer_groups/subscription_groups_coordinator.rb +73 -0
  133. data/lib/karafka/pro/processing/consumer_groups/virtual_partitions/distributors/balanced.rb +82 -0
  134. data/lib/karafka/pro/processing/consumer_groups/virtual_partitions/distributors/base.rb +59 -0
  135. data/lib/karafka/pro/processing/{strategies/dlq/ftr.rb → consumer_groups/virtual_partitions/distributors/consistent.rb} +18 -33
  136. data/lib/karafka/pro/processing/filters/base.rb +3 -61
  137. data/lib/karafka/pro/processing/partitioner.rb +2 -57
  138. data/lib/karafka/pro/processing/schedulers/base.rb +10 -6
  139. data/lib/karafka/pro/processing/schedulers/default.rb +6 -5
  140. data/lib/karafka/pro/recurring_tasks/executor.rb +1 -2
  141. data/lib/karafka/pro/routing/features/{active_job → consumer_groups/active_job}/builder.rb +20 -18
  142. data/lib/karafka/pro/routing/features/{inline_insights/config.rb → consumer_groups/active_job.rb} +5 -9
  143. data/lib/karafka/pro/routing/features/consumer_groups/adaptive_iterator/config.rb +53 -0
  144. data/lib/karafka/pro/routing/features/consumer_groups/adaptive_iterator/contracts/topic.rb +91 -0
  145. data/lib/karafka/pro/routing/features/consumer_groups/adaptive_iterator/topic.rb +90 -0
  146. data/lib/karafka/pro/routing/features/consumer_groups/adaptive_iterator.rb +50 -0
  147. data/lib/karafka/pro/routing/features/{patterns/contracts/consumer_group.rb → consumer_groups/dead_letter_queue/contracts/topic.rb} +25 -30
  148. data/lib/karafka/pro/routing/features/consumer_groups/dead_letter_queue/topic.rb +70 -0
  149. data/lib/karafka/pro/routing/features/consumer_groups/dead_letter_queue.rb +46 -0
  150. data/lib/karafka/pro/routing/features/{direct_assignments → consumer_groups/delaying}/config.rb +6 -4
  151. data/lib/karafka/pro/routing/features/{patterns/contracts/pattern.rb → consumer_groups/delaying/contracts/topic.rb} +13 -16
  152. data/lib/karafka/pro/routing/features/consumer_groups/delaying/topic.rb +85 -0
  153. data/lib/karafka/pro/routing/features/{adaptive_iterator/config.rb → consumer_groups/delaying.rb} +8 -11
  154. data/lib/karafka/pro/routing/features/consumer_groups/direct_assignments/config.rb +46 -0
  155. data/lib/karafka/pro/routing/features/consumer_groups/direct_assignments/contracts/consumer_group.rb +68 -0
  156. data/lib/karafka/pro/routing/features/consumer_groups/direct_assignments/contracts/topic.rb +125 -0
  157. data/lib/karafka/pro/routing/features/consumer_groups/direct_assignments/subscription_group.rb +97 -0
  158. data/lib/karafka/pro/routing/features/consumer_groups/direct_assignments/topic.rb +97 -0
  159. data/lib/karafka/pro/routing/features/consumer_groups/direct_assignments.rb +44 -0
  160. data/lib/karafka/pro/routing/features/consumer_groups/inline_insights/config.rb +51 -0
  161. data/lib/karafka/pro/routing/features/consumer_groups/inline_insights/contracts/topic.rb +58 -0
  162. data/lib/karafka/pro/routing/features/consumer_groups/inline_insights/topic.rb +80 -0
  163. data/lib/karafka/pro/routing/features/consumer_groups/inline_insights.rb +45 -0
  164. data/lib/karafka/pro/routing/features/consumer_groups/long_running_job/config.rb +47 -0
  165. data/lib/karafka/pro/routing/features/{multiplexing/patches/contracts/consumer_group.rb → consumer_groups/long_running_job/contracts/topic.rb} +13 -15
  166. data/lib/karafka/pro/routing/features/consumer_groups/long_running_job/topic.rb +72 -0
  167. data/lib/karafka/pro/routing/features/{long_running_job.rb → consumer_groups/long_running_job.rb} +6 -4
  168. data/lib/karafka/pro/routing/features/consumer_groups/multiplexing/config.rb +58 -0
  169. data/lib/karafka/pro/routing/features/consumer_groups/multiplexing/contracts/routing.rb +83 -0
  170. data/lib/karafka/pro/routing/features/consumer_groups/multiplexing/contracts/topic.rb +148 -0
  171. data/lib/karafka/pro/routing/features/{delaying/contracts/topic.rb → consumer_groups/multiplexing/patches/contracts/consumer_group.rb} +19 -14
  172. data/lib/karafka/pro/routing/features/{multiplexing/subscription_group.rb → consumer_groups/multiplexing/proxy.rb} +17 -23
  173. data/lib/karafka/pro/routing/features/consumer_groups/multiplexing/subscription_group.rb +68 -0
  174. data/lib/karafka/pro/routing/features/{multiplexing → consumer_groups/multiplexing}/subscription_groups_builder.rb +16 -14
  175. data/lib/karafka/pro/routing/features/consumer_groups/multiplexing.rb +85 -0
  176. data/lib/karafka/pro/routing/features/consumer_groups/non_blocking_job/topic.rb +51 -0
  177. data/lib/karafka/pro/routing/features/{non_blocking_job.rb → consumer_groups/non_blocking_job.rb} +15 -13
  178. data/lib/karafka/pro/routing/features/consumer_groups/offset_metadata/config.rb +52 -0
  179. data/lib/karafka/pro/routing/features/consumer_groups/offset_metadata/contracts/topic.rb +59 -0
  180. data/lib/karafka/pro/routing/features/consumer_groups/offset_metadata/topic.rb +93 -0
  181. data/lib/karafka/pro/routing/features/{offset_metadata.rb → consumer_groups/offset_metadata.rb} +16 -14
  182. data/lib/karafka/pro/routing/features/consumer_groups/parallel_segments/builder.rb +74 -0
  183. data/lib/karafka/pro/routing/features/{multiplexing → consumer_groups/parallel_segments}/config.rb +13 -15
  184. data/lib/karafka/pro/routing/features/consumer_groups/parallel_segments/consumer_group.rb +110 -0
  185. data/lib/karafka/pro/routing/features/consumer_groups/parallel_segments/contracts/consumer_group.rb +74 -0
  186. data/lib/karafka/pro/routing/features/{parallel_segments → consumer_groups/parallel_segments}/topic.rb +24 -22
  187. data/lib/karafka/pro/routing/features/consumer_groups/parallel_segments.rb +51 -0
  188. data/lib/karafka/pro/routing/features/{patterns → consumer_groups/patterns}/builder.rb +15 -13
  189. data/lib/karafka/pro/routing/features/{offset_metadata/contracts/topic.rb → consumer_groups/patterns/config.rb} +28 -13
  190. data/lib/karafka/pro/routing/features/consumer_groups/patterns/consumer_group.rb +91 -0
  191. data/lib/karafka/pro/routing/features/consumer_groups/patterns/contracts/consumer_group.rb +83 -0
  192. data/lib/karafka/pro/routing/features/{parallel_segments.rb → consumer_groups/patterns/contracts/pattern.rb} +24 -10
  193. data/lib/karafka/pro/routing/features/consumer_groups/patterns/contracts/topic.rb +58 -0
  194. data/lib/karafka/pro/routing/features/consumer_groups/patterns/detector.rb +98 -0
  195. data/lib/karafka/pro/routing/features/consumer_groups/patterns/pattern.rb +114 -0
  196. data/lib/karafka/pro/routing/features/{recurring_tasks/contracts/topic.rb → consumer_groups/patterns/patterns.rb} +12 -13
  197. data/lib/karafka/pro/routing/features/consumer_groups/patterns/topic.rb +78 -0
  198. data/lib/karafka/pro/routing/features/consumer_groups/patterns/topics.rb +72 -0
  199. data/lib/karafka/pro/routing/features/consumer_groups/patterns.rb +52 -0
  200. data/lib/karafka/pro/routing/features/consumer_groups/periodic_job/config.rb +56 -0
  201. data/lib/karafka/pro/routing/features/{direct_assignments/contracts/consumer_group.rb → consumer_groups/periodic_job/contracts/topic.rb} +17 -22
  202. data/lib/karafka/pro/routing/features/consumer_groups/periodic_job/topic.rb +122 -0
  203. data/lib/karafka/pro/routing/features/consumer_groups/periodic_job.rb +46 -0
  204. data/lib/karafka/pro/routing/features/consumer_groups/recurring_tasks/builder.rb +150 -0
  205. data/lib/karafka/pro/routing/features/{swarm → consumer_groups/recurring_tasks}/config.rb +7 -8
  206. data/lib/karafka/pro/routing/features/{inline_insights → consumer_groups/recurring_tasks}/contracts/topic.rb +14 -13
  207. data/lib/karafka/pro/routing/features/{scheduled_messages → consumer_groups/recurring_tasks}/proxy.rb +6 -4
  208. data/lib/karafka/pro/routing/features/consumer_groups/recurring_tasks/topic.rb +72 -0
  209. data/lib/karafka/pro/routing/features/consumer_groups/recurring_tasks.rb +44 -0
  210. data/lib/karafka/pro/routing/features/consumer_groups/scheduled_messages/builder.rb +154 -0
  211. data/lib/karafka/pro/routing/features/consumer_groups/scheduled_messages/config.rb +47 -0
  212. data/lib/karafka/pro/routing/features/{long_running_job → consumer_groups/scheduled_messages}/contracts/topic.rb +14 -12
  213. data/lib/karafka/pro/routing/features/{delaying/config.rb → consumer_groups/scheduled_messages/proxy.rb} +6 -4
  214. data/lib/karafka/pro/routing/features/consumer_groups/scheduled_messages/topic.rb +72 -0
  215. data/lib/karafka/pro/routing/features/{recurring_tasks/proxy.rb → consumer_groups/scheduled_messages.rb} +3 -4
  216. data/lib/karafka/pro/routing/features/{non_blocking_job/topic.rb → consumer_groups/swarm/config.rb} +9 -8
  217. data/lib/karafka/pro/routing/features/consumer_groups/swarm/contracts/routing.rb +94 -0
  218. data/lib/karafka/pro/routing/features/consumer_groups/swarm/contracts/topic.rb +95 -0
  219. data/lib/karafka/pro/routing/features/consumer_groups/swarm/topic.rb +105 -0
  220. data/lib/karafka/pro/routing/features/consumer_groups/swarm.rb +58 -0
  221. data/lib/karafka/pro/routing/features/consumer_groups/virtual_partitions/config.rb +69 -0
  222. data/lib/karafka/pro/routing/features/{parallel_segments/contracts/consumer_group.rb → consumer_groups/virtual_partitions/contracts/topic.rb} +21 -18
  223. data/lib/karafka/pro/routing/features/consumer_groups/virtual_partitions/topic.rb +101 -0
  224. data/lib/karafka/pro/routing/features/consumer_groups/virtual_partitions.rb +46 -0
  225. data/lib/karafka/pro/routing/features/{scheduled_messages.rb → consumer_groups.rb} +3 -2
  226. data/lib/karafka/pro/routing/features/expiring/topic.rb +4 -4
  227. data/lib/karafka/pro/routing/features/filtering/topic.rb +3 -3
  228. data/lib/karafka/pro/routing/features/pausing/topic.rb +3 -3
  229. data/lib/karafka/pro/routing/features/throttling/topic.rb +4 -4
  230. data/lib/karafka/pro/setup/defaults_injector.rb +70 -0
  231. data/lib/karafka/pro/swarm/liveness_listener.rb +22 -10
  232. data/lib/karafka/processing/consumer_groups/coordinator.rb +221 -0
  233. data/lib/karafka/processing/consumer_groups/coordinators_buffer.rb +69 -0
  234. data/lib/karafka/processing/consumer_groups/executor.rb +220 -0
  235. data/lib/karafka/processing/consumer_groups/executors_buffer.rb +94 -0
  236. data/lib/karafka/processing/consumer_groups/expansions_selector.rb +26 -0
  237. data/lib/karafka/processing/consumer_groups/inline_insights/consumer.rb +47 -0
  238. data/lib/karafka/processing/consumer_groups/inline_insights/listener.rb +23 -0
  239. data/lib/karafka/processing/consumer_groups/inline_insights/tracker.rb +132 -0
  240. data/lib/karafka/processing/consumer_groups/jobs/consume.rb +52 -0
  241. data/lib/karafka/processing/consumer_groups/jobs/eofed.rb +34 -0
  242. data/lib/karafka/processing/consumer_groups/jobs/idle.rb +33 -0
  243. data/lib/karafka/processing/consumer_groups/jobs/revoked.rb +34 -0
  244. data/lib/karafka/processing/consumer_groups/jobs/shutdown.rb +32 -0
  245. data/lib/karafka/processing/consumer_groups/jobs_builder.rb +36 -0
  246. data/lib/karafka/processing/consumer_groups/partitioner.rb +28 -0
  247. data/lib/karafka/processing/consumer_groups/strategies/aj_dlq_mom.rb +48 -0
  248. data/lib/karafka/processing/consumer_groups/strategies/aj_mom.rb +25 -0
  249. data/lib/karafka/processing/consumer_groups/strategies/base.rb +65 -0
  250. data/lib/karafka/processing/consumer_groups/strategies/default.rb +218 -0
  251. data/lib/karafka/processing/consumer_groups/strategies/dlq.rb +157 -0
  252. data/lib/karafka/processing/consumer_groups/strategies/dlq_mom.rb +72 -0
  253. data/lib/karafka/processing/consumer_groups/strategies/mom.rb +33 -0
  254. data/lib/karafka/processing/consumer_groups/strategy_selector.rb +53 -0
  255. data/lib/karafka/processing/coordinator.rb +4 -211
  256. data/lib/karafka/processing/coordinators_buffer.rb +4 -59
  257. data/lib/karafka/processing/jobs_queue.rb +12 -4
  258. data/lib/karafka/processing/partitioner.rb +4 -18
  259. data/lib/karafka/processing/schedulers/default.rb +2 -1
  260. data/lib/karafka/processing/strategy_selector.rb +4 -42
  261. data/lib/karafka/processing/worker.rb +8 -4
  262. data/lib/karafka/processing/workers_pool.rb +158 -0
  263. data/lib/karafka/routing/builder.rb +12 -12
  264. data/lib/karafka/routing/contracts/routing.rb +3 -4
  265. data/lib/karafka/routing/features/base/expander.rb +5 -5
  266. data/lib/karafka/routing/features/consumer_groups/active_job/builder.rb +35 -0
  267. data/lib/karafka/routing/features/consumer_groups/active_job/config.rb +17 -0
  268. data/lib/karafka/routing/features/consumer_groups/active_job/contracts/topic.rb +44 -0
  269. data/lib/karafka/routing/features/consumer_groups/active_job/proxy.rb +16 -0
  270. data/lib/karafka/routing/features/consumer_groups/active_job/topic.rb +50 -0
  271. data/lib/karafka/routing/features/consumer_groups/active_job.rb +15 -0
  272. data/lib/karafka/routing/features/consumer_groups/dead_letter_queue/config.rb +39 -0
  273. data/lib/karafka/routing/features/consumer_groups/dead_letter_queue/contracts/topic.rb +58 -0
  274. data/lib/karafka/routing/features/consumer_groups/dead_letter_queue/topic.rb +76 -0
  275. data/lib/karafka/routing/features/consumer_groups/dead_letter_queue.rb +18 -0
  276. data/lib/karafka/routing/features/consumer_groups/eofed/config.rb +17 -0
  277. data/lib/karafka/routing/features/consumer_groups/eofed/contracts/topic.rb +39 -0
  278. data/lib/karafka/routing/features/consumer_groups/eofed/topic.rb +42 -0
  279. data/lib/karafka/routing/features/consumer_groups/eofed.rb +16 -0
  280. data/lib/karafka/routing/features/consumer_groups/inline_insights/config.rb +17 -0
  281. data/lib/karafka/routing/features/consumer_groups/inline_insights/contracts/topic.rb +27 -0
  282. data/lib/karafka/routing/features/consumer_groups/inline_insights/topic.rb +42 -0
  283. data/lib/karafka/routing/features/consumer_groups/inline_insights.rb +42 -0
  284. data/lib/karafka/routing/features/consumer_groups/manual_offset_management/config.rb +17 -0
  285. data/lib/karafka/routing/features/consumer_groups/manual_offset_management/contracts/topic.rb +27 -0
  286. data/lib/karafka/routing/features/consumer_groups/manual_offset_management/topic.rb +46 -0
  287. data/lib/karafka/routing/features/consumer_groups/manual_offset_management.rb +20 -0
  288. data/lib/karafka/routing/features/consumer_groups.rb +12 -0
  289. data/lib/karafka/routing/features/declaratives/contracts/topic.rb +4 -19
  290. data/lib/karafka/routing/features/declaratives/topic.rb +30 -14
  291. data/lib/karafka/routing/features/deserializers/topic.rb +3 -3
  292. data/lib/karafka/routing/router.rb +2 -2
  293. data/lib/karafka/routing/subscription_group.rb +18 -9
  294. data/lib/karafka/routing/topic.rb +25 -11
  295. data/lib/karafka/runner.rb +17 -17
  296. data/lib/karafka/server.rb +28 -6
  297. data/lib/karafka/setup/attributes_map.rb +2 -0
  298. data/lib/karafka/setup/config.rb +64 -15
  299. data/lib/karafka/setup/config_proxy.rb +1 -2
  300. data/lib/karafka/setup/contracts/config.rb +28 -8
  301. data/lib/karafka/setup/defaults_injector.rb +10 -0
  302. data/lib/karafka/status.rb +1 -2
  303. data/lib/karafka/swarm/liveness_listener.rb +7 -0
  304. data/lib/karafka/swarm/manager.rb +7 -7
  305. data/lib/karafka/swarm/node.rb +8 -0
  306. data/lib/karafka/swarm/supervisor.rb +9 -1
  307. data/lib/karafka/templates/karafka.rb.erb +11 -5
  308. data/lib/karafka/version.rb +1 -1
  309. metadata +237 -224
  310. data/lib/karafka/connection/rebalance_manager.rb +0 -116
  311. data/lib/karafka/instrumentation/callbacks/error.rb +0 -52
  312. data/lib/karafka/instrumentation/callbacks/rebalance.rb +0 -84
  313. data/lib/karafka/instrumentation/callbacks/statistics.rb +0 -55
  314. data/lib/karafka/pro/processing/adaptive_iterator/consumer.rb +0 -79
  315. data/lib/karafka/pro/processing/adaptive_iterator/tracker.rb +0 -92
  316. data/lib/karafka/pro/processing/collapser.rb +0 -79
  317. data/lib/karafka/pro/processing/coordinator.rb +0 -197
  318. data/lib/karafka/pro/processing/coordinators/errors_tracker.rb +0 -119
  319. data/lib/karafka/pro/processing/coordinators/filters_applier.rb +0 -152
  320. data/lib/karafka/pro/processing/coordinators/virtual_offset_manager.rb +0 -207
  321. data/lib/karafka/pro/processing/expansions_selector.rb +0 -52
  322. data/lib/karafka/pro/processing/filters/delayer.rb +0 -87
  323. data/lib/karafka/pro/processing/filters/inline_insights_delayer.rb +0 -95
  324. data/lib/karafka/pro/processing/filters/throttler.rb +0 -101
  325. data/lib/karafka/pro/processing/filters/virtual_limiter.rb +0 -74
  326. data/lib/karafka/pro/processing/jobs/eofed_non_blocking.rb +0 -51
  327. data/lib/karafka/pro/processing/jobs_builder.rb +0 -90
  328. data/lib/karafka/pro/processing/offset_metadata/consumer.rb +0 -61
  329. data/lib/karafka/pro/processing/offset_metadata/fetcher.rb +0 -149
  330. data/lib/karafka/pro/processing/offset_metadata/listener.rb +0 -63
  331. data/lib/karafka/pro/processing/parallel_segments/filters/base.rb +0 -98
  332. data/lib/karafka/pro/processing/parallel_segments/filters/default.rb +0 -110
  333. data/lib/karafka/pro/processing/parallel_segments/filters/mom.rb +0 -91
  334. data/lib/karafka/pro/processing/periodic_job/consumer.rb +0 -85
  335. data/lib/karafka/pro/processing/piping/consumer.rb +0 -149
  336. data/lib/karafka/pro/processing/strategies/aj/dlq_ftr_lrj_mom_vp.rb +0 -94
  337. data/lib/karafka/pro/processing/strategies/aj/dlq_ftr_mom.rb +0 -87
  338. data/lib/karafka/pro/processing/strategies/aj/dlq_ftr_mom_vp.rb +0 -85
  339. data/lib/karafka/pro/processing/strategies/aj/dlq_lrj_mom.rb +0 -81
  340. data/lib/karafka/pro/processing/strategies/aj/dlq_lrj_mom_vp.rb +0 -85
  341. data/lib/karafka/pro/processing/strategies/aj/dlq_mom.rb +0 -79
  342. data/lib/karafka/pro/processing/strategies/aj/dlq_mom_vp.rb +0 -84
  343. data/lib/karafka/pro/processing/strategies/aj/ftr_lrj_mom_vp.rb +0 -86
  344. data/lib/karafka/pro/processing/strategies/aj/lrj_mom.rb +0 -54
  345. data/lib/karafka/pro/processing/strategies/aj/lrj_mom_vp.rb +0 -101
  346. data/lib/karafka/pro/processing/strategies/base.rb +0 -43
  347. data/lib/karafka/pro/processing/strategies/default.rb +0 -416
  348. data/lib/karafka/pro/processing/strategies/dlq/default.rb +0 -280
  349. data/lib/karafka/pro/processing/strategies/dlq/ftr_lrj.rb +0 -90
  350. data/lib/karafka/pro/processing/strategies/dlq/ftr_lrj_mom.rb +0 -92
  351. data/lib/karafka/pro/processing/strategies/dlq/ftr_lrj_mom_vp.rb +0 -60
  352. data/lib/karafka/pro/processing/strategies/dlq/ftr_lrj_vp.rb +0 -58
  353. data/lib/karafka/pro/processing/strategies/dlq/ftr_mom.rb +0 -92
  354. data/lib/karafka/pro/processing/strategies/dlq/ftr_mom_vp.rb +0 -58
  355. data/lib/karafka/pro/processing/strategies/dlq/ftr_vp.rb +0 -57
  356. data/lib/karafka/pro/processing/strategies/dlq/lrj_mom.rb +0 -95
  357. data/lib/karafka/pro/processing/strategies/dlq/lrj_vp.rb +0 -56
  358. data/lib/karafka/pro/processing/strategies/dlq/mom.rb +0 -91
  359. data/lib/karafka/pro/processing/strategies/dlq/mom_vp.rb +0 -54
  360. data/lib/karafka/pro/processing/strategies/dlq/vp.rb +0 -57
  361. data/lib/karafka/pro/processing/strategies/ftr/default.rb +0 -141
  362. data/lib/karafka/pro/processing/strategies/ftr/vp.rb +0 -57
  363. data/lib/karafka/pro/processing/strategies/lrj/default.rb +0 -114
  364. data/lib/karafka/pro/processing/strategies/lrj/ftr.rb +0 -89
  365. data/lib/karafka/pro/processing/strategies/lrj/ftr_mom.rb +0 -87
  366. data/lib/karafka/pro/processing/strategies/lrj/ftr_mom_vp.rb +0 -57
  367. data/lib/karafka/pro/processing/strategies/lrj/ftr_vp.rb +0 -56
  368. data/lib/karafka/pro/processing/strategies/lrj/mom.rb +0 -96
  369. data/lib/karafka/pro/processing/strategies/mom/ftr_vp.rb +0 -54
  370. data/lib/karafka/pro/processing/strategies/vp/default.rb +0 -192
  371. data/lib/karafka/pro/processing/strategies.rb +0 -39
  372. data/lib/karafka/pro/processing/strategy_selector.rb +0 -102
  373. data/lib/karafka/pro/processing/subscription_groups_coordinator.rb +0 -68
  374. data/lib/karafka/pro/processing/virtual_partitions/distributors/balanced.rb +0 -77
  375. data/lib/karafka/pro/routing/features/active_job.rb +0 -43
  376. data/lib/karafka/pro/routing/features/adaptive_iterator/contracts/topic.rb +0 -89
  377. data/lib/karafka/pro/routing/features/adaptive_iterator/topic.rb +0 -88
  378. data/lib/karafka/pro/routing/features/adaptive_iterator.rb +0 -48
  379. data/lib/karafka/pro/routing/features/dead_letter_queue/contracts/topic.rb +0 -74
  380. data/lib/karafka/pro/routing/features/dead_letter_queue/topic.rb +0 -68
  381. data/lib/karafka/pro/routing/features/dead_letter_queue.rb +0 -44
  382. data/lib/karafka/pro/routing/features/delaying/topic.rb +0 -83
  383. data/lib/karafka/pro/routing/features/delaying.rb +0 -46
  384. data/lib/karafka/pro/routing/features/direct_assignments/contracts/topic.rb +0 -123
  385. data/lib/karafka/pro/routing/features/direct_assignments/subscription_group.rb +0 -95
  386. data/lib/karafka/pro/routing/features/direct_assignments/topic.rb +0 -95
  387. data/lib/karafka/pro/routing/features/direct_assignments.rb +0 -42
  388. data/lib/karafka/pro/routing/features/inline_insights/topic.rb +0 -78
  389. data/lib/karafka/pro/routing/features/inline_insights.rb +0 -43
  390. data/lib/karafka/pro/routing/features/long_running_job/config.rb +0 -45
  391. data/lib/karafka/pro/routing/features/long_running_job/topic.rb +0 -70
  392. data/lib/karafka/pro/routing/features/multiplexing/contracts/routing.rb +0 -81
  393. data/lib/karafka/pro/routing/features/multiplexing/contracts/topic.rb +0 -146
  394. data/lib/karafka/pro/routing/features/multiplexing/proxy.rb +0 -58
  395. data/lib/karafka/pro/routing/features/multiplexing.rb +0 -83
  396. data/lib/karafka/pro/routing/features/offset_metadata/config.rb +0 -50
  397. data/lib/karafka/pro/routing/features/offset_metadata/topic.rb +0 -91
  398. data/lib/karafka/pro/routing/features/parallel_segments/builder.rb +0 -72
  399. data/lib/karafka/pro/routing/features/parallel_segments/config.rb +0 -52
  400. data/lib/karafka/pro/routing/features/parallel_segments/consumer_group.rb +0 -108
  401. data/lib/karafka/pro/routing/features/patterns/config.rb +0 -71
  402. data/lib/karafka/pro/routing/features/patterns/consumer_group.rb +0 -89
  403. data/lib/karafka/pro/routing/features/patterns/contracts/topic.rb +0 -56
  404. data/lib/karafka/pro/routing/features/patterns/detector.rb +0 -96
  405. data/lib/karafka/pro/routing/features/patterns/pattern.rb +0 -112
  406. data/lib/karafka/pro/routing/features/patterns/topic.rb +0 -76
  407. data/lib/karafka/pro/routing/features/patterns/topics.rb +0 -70
  408. data/lib/karafka/pro/routing/features/patterns.rb +0 -50
  409. data/lib/karafka/pro/routing/features/periodic_job/config.rb +0 -54
  410. data/lib/karafka/pro/routing/features/periodic_job/contracts/topic.rb +0 -59
  411. data/lib/karafka/pro/routing/features/periodic_job/topic.rb +0 -120
  412. data/lib/karafka/pro/routing/features/periodic_job.rb +0 -44
  413. data/lib/karafka/pro/routing/features/recurring_tasks/builder.rb +0 -148
  414. data/lib/karafka/pro/routing/features/recurring_tasks/config.rb +0 -45
  415. data/lib/karafka/pro/routing/features/recurring_tasks/topic.rb +0 -70
  416. data/lib/karafka/pro/routing/features/recurring_tasks.rb +0 -42
  417. data/lib/karafka/pro/routing/features/scheduled_messages/builder.rb +0 -152
  418. data/lib/karafka/pro/routing/features/scheduled_messages/config.rb +0 -45
  419. data/lib/karafka/pro/routing/features/scheduled_messages/contracts/topic.rb +0 -55
  420. data/lib/karafka/pro/routing/features/scheduled_messages/topic.rb +0 -70
  421. data/lib/karafka/pro/routing/features/swarm/contracts/routing.rb +0 -92
  422. data/lib/karafka/pro/routing/features/swarm/contracts/topic.rb +0 -93
  423. data/lib/karafka/pro/routing/features/swarm/topic.rb +0 -103
  424. data/lib/karafka/pro/routing/features/swarm.rb +0 -56
  425. data/lib/karafka/pro/routing/features/virtual_partitions/config.rb +0 -67
  426. data/lib/karafka/pro/routing/features/virtual_partitions/contracts/topic.rb +0 -73
  427. data/lib/karafka/pro/routing/features/virtual_partitions/topic.rb +0 -99
  428. data/lib/karafka/pro/routing/features/virtual_partitions.rb +0 -44
  429. data/lib/karafka/processing/executor.rb +0 -216
  430. data/lib/karafka/processing/executors_buffer.rb +0 -90
  431. data/lib/karafka/processing/expansions_selector.rb +0 -22
  432. data/lib/karafka/processing/inline_insights/consumer.rb +0 -43
  433. data/lib/karafka/processing/inline_insights/listener.rb +0 -19
  434. data/lib/karafka/processing/inline_insights/tracker.rb +0 -129
  435. data/lib/karafka/processing/jobs/consume.rb +0 -47
  436. data/lib/karafka/processing/jobs/eofed.rb +0 -29
  437. data/lib/karafka/processing/jobs/idle.rb +0 -31
  438. data/lib/karafka/processing/jobs/revoked.rb +0 -29
  439. data/lib/karafka/processing/jobs/shutdown.rb +0 -30
  440. data/lib/karafka/processing/jobs_builder.rb +0 -34
  441. data/lib/karafka/processing/strategies/aj_dlq_mom.rb +0 -44
  442. data/lib/karafka/processing/strategies/aj_mom.rb +0 -21
  443. data/lib/karafka/processing/strategies/base.rb +0 -61
  444. data/lib/karafka/processing/strategies/default.rb +0 -214
  445. data/lib/karafka/processing/strategies/dlq.rb +0 -153
  446. data/lib/karafka/processing/strategies/dlq_mom.rb +0 -68
  447. data/lib/karafka/processing/strategies/mom.rb +0 -29
  448. data/lib/karafka/processing/workers_batch.rb +0 -29
  449. data/lib/karafka/routing/features/active_job/builder.rb +0 -33
  450. data/lib/karafka/routing/features/active_job/config.rb +0 -15
  451. data/lib/karafka/routing/features/active_job/contracts/topic.rb +0 -42
  452. data/lib/karafka/routing/features/active_job/proxy.rb +0 -14
  453. data/lib/karafka/routing/features/active_job/topic.rb +0 -48
  454. data/lib/karafka/routing/features/active_job.rb +0 -13
  455. data/lib/karafka/routing/features/dead_letter_queue/config.rb +0 -37
  456. data/lib/karafka/routing/features/dead_letter_queue/contracts/topic.rb +0 -56
  457. data/lib/karafka/routing/features/dead_letter_queue/topic.rb +0 -74
  458. data/lib/karafka/routing/features/dead_letter_queue.rb +0 -16
  459. data/lib/karafka/routing/features/declaratives/config.rb +0 -18
  460. data/lib/karafka/routing/features/eofed/config.rb +0 -15
  461. data/lib/karafka/routing/features/eofed/contracts/topic.rb +0 -37
  462. data/lib/karafka/routing/features/eofed/topic.rb +0 -40
  463. data/lib/karafka/routing/features/eofed.rb +0 -14
  464. data/lib/karafka/routing/features/inline_insights/config.rb +0 -15
  465. data/lib/karafka/routing/features/inline_insights/contracts/topic.rb +0 -25
  466. data/lib/karafka/routing/features/inline_insights/topic.rb +0 -40
  467. data/lib/karafka/routing/features/inline_insights.rb +0 -40
  468. data/lib/karafka/routing/features/manual_offset_management/config.rb +0 -15
  469. data/lib/karafka/routing/features/manual_offset_management/contracts/topic.rb +0 -25
  470. data/lib/karafka/routing/features/manual_offset_management/topic.rb +0 -44
  471. data/lib/karafka/routing/features/manual_offset_management.rb +0 -18
@@ -1,99 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- # Karafka Pro - Source Available Commercial Software
4
- # Copyright (c) 2017-present Maciej Mensfeld. All rights reserved.
5
- #
6
- # This software is NOT open source. It is source-available commercial software
7
- # requiring a paid license for use. It is NOT covered by LGPL.
8
- #
9
- # The author retains all right, title, and interest in this software,
10
- # including all copyrights, patents, and other intellectual property rights.
11
- # No patent rights are granted under this license.
12
- #
13
- # PROHIBITED:
14
- # - Use without a valid commercial license
15
- # - Redistribution, modification, or derivative works without authorization
16
- # - Reverse engineering, decompilation, or disassembly of this software
17
- # - Use as training data for AI/ML models or inclusion in datasets
18
- # - Scraping, crawling, or automated collection for any purpose
19
- #
20
- # PERMITTED:
21
- # - Reading, referencing, and linking for personal or commercial use
22
- # - Runtime retrieval by AI assistants, coding agents, and RAG systems
23
- # for the purpose of providing contextual help to Karafka users
24
- #
25
- # Receipt, viewing, or possession of this software does not convey or
26
- # imply any license or right beyond those expressly stated above.
27
- #
28
- # License: https://karafka.io/docs/Pro-License-Comm/
29
- # Contact: contact@karafka.io
30
-
31
- module Karafka
32
- module Pro
33
- module Routing
34
- module Features
35
- class VirtualPartitions < Base
36
- # Topic extensions to be able to manage virtual partitions feature
37
- module Topic
38
- # This method calls the parent class initializer and then sets up the
39
- # extra instance variable to nil. The explicit initialization
40
- # to nil is included as an optimization for Ruby's object shapes system,
41
- # which improves memory layout and access performance.
42
- def initialize(...)
43
- super
44
- @virtual_partitions = nil
45
- end
46
-
47
- # @param max_partitions [Integer] max number of virtual partitions that can come out of
48
- # the single distribution flow. When set to more than the Karafka threading, will
49
- # create more work than workers. When less, can ensure we have spare resources to
50
- # process other things in parallel.
51
- # @param partitioner [nil, #call] nil or callable partitioner
52
- # @param offset_metadata_strategy [Symbol] how we should match the metadata for the
53
- # offset. `:exact` will match the offset matching metadata and `:current` will select
54
- # the most recently reported metadata
55
- # @param reducer [nil, #call] reducer for VPs key. It allows for using a custom
56
- # reducer to achieve enhanced parallelization when the default reducer is not enough.
57
- # @param distribution [Symbol] the strategy to use for virtual partitioning. Can be
58
- # either `:consistent` or `:balanced`. The `:balanced` strategy ensures balanced
59
- # distribution of work across available workers while maintaining message order
60
- # within groups.
61
- # @return [VirtualPartitions] method that allows to set the virtual partitions details
62
- # during the routing configuration and then allows to retrieve it
63
- def virtual_partitions(
64
- max_partitions: Karafka::App.config.concurrency,
65
- partitioner: nil,
66
- offset_metadata_strategy: :current,
67
- reducer: nil,
68
- distribution: :consistent
69
- )
70
- @virtual_partitions ||= Config.new(
71
- active: !partitioner.nil?,
72
- max_partitions: max_partitions,
73
- partitioner: partitioner,
74
- offset_metadata_strategy: offset_metadata_strategy,
75
- # If no reducer provided, we use this one. It just runs a modulo on the sum of
76
- # a stringified version, providing fairly good distribution.
77
- reducer: reducer || ->(virtual_key) { virtual_key.to_s.sum % max_partitions },
78
- distribution: distribution
79
- )
80
- end
81
-
82
- # @return [Boolean] are virtual partitions enabled for given topic
83
- def virtual_partitions?
84
- virtual_partitions.active?
85
- end
86
-
87
- # @return [Hash] topic with all its native configuration options plus manual offset
88
- # management namespace settings
89
- def to_h
90
- super.merge(
91
- virtual_partitions: virtual_partitions.to_h
92
- ).freeze
93
- end
94
- end
95
- end
96
- end
97
- end
98
- end
99
- end
@@ -1,44 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- # Karafka Pro - Source Available Commercial Software
4
- # Copyright (c) 2017-present Maciej Mensfeld. All rights reserved.
5
- #
6
- # This software is NOT open source. It is source-available commercial software
7
- # requiring a paid license for use. It is NOT covered by LGPL.
8
- #
9
- # The author retains all right, title, and interest in this software,
10
- # including all copyrights, patents, and other intellectual property rights.
11
- # No patent rights are granted under this license.
12
- #
13
- # PROHIBITED:
14
- # - Use without a valid commercial license
15
- # - Redistribution, modification, or derivative works without authorization
16
- # - Reverse engineering, decompilation, or disassembly of this software
17
- # - Use as training data for AI/ML models or inclusion in datasets
18
- # - Scraping, crawling, or automated collection for any purpose
19
- #
20
- # PERMITTED:
21
- # - Reading, referencing, and linking for personal or commercial use
22
- # - Runtime retrieval by AI assistants, coding agents, and RAG systems
23
- # for the purpose of providing contextual help to Karafka users
24
- #
25
- # Receipt, viewing, or possession of this software does not convey or
26
- # imply any license or right beyond those expressly stated above.
27
- #
28
- # License: https://karafka.io/docs/Pro-License-Comm/
29
- # Contact: contact@karafka.io
30
-
31
- module Karafka
32
- module Pro
33
- module Routing
34
- module Features
35
- # Virtual Partitions feature config and DSL namespace.
36
- #
37
- # Virtual Partitions allow you to parallelize the processing of data from a single
38
- # partition. This can drastically increase throughput when IO operations are involved.
39
- class VirtualPartitions < Base
40
- end
41
- end
42
- end
43
- end
44
- end
@@ -1,216 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Karafka
4
- # Namespace that encapsulates all the logic related to processing data.
5
- module Processing
6
- # Executors:
7
- # - run consumers code (for `#call`) or run given preparation / teardown operations when needed
8
- # from separate threads.
9
- # - they re-create consumer instances in case of partitions that were revoked and assigned
10
- # back.
11
- #
12
- # @note Executors are not removed after partition is revoked. They are not that big and will
13
- # be re-used in case of a re-claim
14
- #
15
- # @note Since given consumer can run various operations, executor manages that and its
16
- # lifecycle. There are following types of operations with appropriate before/after, etc:
17
- #
18
- # - consume - primary operation related to running user consumption code
19
- # - idle - cleanup job that runs on idle runs where no messages would be passed to the end
20
- # user. This is used for complex flows with filters, etc
21
- # - revoked - runs after the partition was revoked
22
- # - shutdown - runs when process is going to shutdown
23
- class Executor
24
- extend Forwardable
25
- include Helpers::ConfigImporter.new(
26
- strategy_selector: %i[internal processing strategy_selector],
27
- expansions_selector: %i[internal processing expansions_selector]
28
- )
29
-
30
- def_delegators :@coordinator, :topic, :partition
31
-
32
- # @return [String] unique id that we use to ensure, that we use for state tracking
33
- attr_reader :id
34
-
35
- # @return [String] subscription group id to which a given executor belongs
36
- attr_reader :group_id
37
-
38
- # @return [Karafka::Messages::Messages] messages batch
39
- attr_reader :messages
40
-
41
- # @return [Karafka::Processing::Coordinator] coordinator for this executor
42
- attr_reader :coordinator
43
-
44
- # @param group_id [String] id of the subscription group to which the executor belongs
45
- # @param client [Karafka::Connection::Client] kafka client
46
- # @param coordinator [Karafka::Processing::Coordinator]
47
- def initialize(group_id, client, coordinator)
48
- @id = SecureRandom.hex(6)
49
- @group_id = group_id
50
- @client = client
51
- @coordinator = coordinator
52
- end
53
-
54
- # Allows us to prepare the consumer in the listener thread prior to the job being send to
55
- # be scheduled. It also allows to run some code that is time sensitive and cannot wait in the
56
- # queue as it could cause starvation.
57
- #
58
- # @param messages [Array<Karafka::Messages::Message>]
59
- def before_schedule_consume(messages)
60
- # Recreate consumer with each batch if persistence is not enabled
61
- # We reload the consumers with each batch instead of relying on some external signals
62
- # when needed for consistency. That way devs may have it on or off and not in this
63
- # middle state, where re-creation of a consumer instance would occur only sometimes
64
- @consumer = nil unless topic.consumer_persistence
65
-
66
- # First we build messages batch...
67
- consumer.messages = Messages::Builders::Messages.call(
68
- messages,
69
- topic,
70
- partition,
71
- # the moment we've received the batch or actually the moment we've enqueued it,
72
- # but good enough
73
- Time.now
74
- )
75
-
76
- consumer.on_before_schedule_consume
77
- end
78
-
79
- # Runs setup and warm-up code in the worker prior to running the consumption
80
- def before_consume
81
- consumer.on_before_consume
82
- end
83
-
84
- # Runs the wrap/around execution context appropriate for a given action
85
- # @param action [Symbol] action execution wrapped with our block
86
- def wrap(action, &)
87
- consumer.on_wrap(action, &)
88
- end
89
-
90
- # Runs consumer data processing against given batch and handles failures and errors.
91
- def consume
92
- # We run the consumer client logic...
93
- consumer.on_consume
94
- end
95
-
96
- # Runs consumer after consumption code
97
- def after_consume
98
- consumer.on_after_consume
99
- end
100
-
101
- # Runs the code needed before idle work is scheduled
102
- def before_schedule_idle
103
- consumer.on_before_schedule_idle
104
- end
105
-
106
- # Runs consumer idle operations
107
- # This may include house-keeping or other state management changes that can occur but that
108
- # not mean there are any new messages available for the end user to process
109
- def idle
110
- consumer.on_idle
111
- end
112
-
113
- # Runs the code needed before eofed work is scheduled
114
- def before_schedule_eofed
115
- consumer.on_before_schedule_eofed
116
- end
117
-
118
- # Runs consumed eofed operation.
119
- # This may run even when there were no messages received prior. This will however not
120
- # run when eof is received together with messages as in such case `#consume` will run
121
- def eofed
122
- consumer.on_eofed
123
- end
124
-
125
- # Runs code needed before revoked job is scheduled
126
- def before_schedule_revoked
127
- consumer.on_before_schedule_revoked if @consumer
128
- end
129
-
130
- # Runs the controller `#revoked` method that should be triggered when a given consumer is
131
- # no longer needed due to partitions reassignment.
132
- #
133
- # @note Clearing the consumer will ensure, that if we get the partition back, it will be
134
- # handled with a consumer with a clean state.
135
- #
136
- # @note We run it only when consumer was present, because presence indicates, that at least
137
- # a single message has been consumed.
138
- #
139
- # @note We do not reset the consumer but we indicate need for recreation instead, because
140
- # after the revocation, there still may be `#after_consume` running that needs a given
141
- # consumer instance.
142
- def revoked
143
- consumer.on_revoked if @consumer
144
- end
145
-
146
- # Runs code needed before shutdown job is scheduled
147
- def before_schedule_shutdown
148
- consumer.on_before_schedule_shutdown if @consumer
149
- end
150
-
151
- # Runs the controller `#shutdown` method that should be triggered when a given consumer is
152
- # no longer needed as we're closing the process.
153
- #
154
- # @note While we do not need to clear the consumer here, it's a good habit to clean after
155
- # work is done.
156
- def shutdown
157
- # There is a case, where the consumer no longer exists because it was revoked, in case like
158
- # that we do not build a new instance and shutdown should not be triggered.
159
- consumer.on_shutdown if @consumer
160
- end
161
-
162
- private
163
-
164
- # @return [Object] cached consumer instance
165
- def consumer
166
- @consumer ||= begin
167
- topic = @coordinator.topic
168
-
169
- strategy = strategy_selector.find(topic)
170
-
171
- consumer = topic.consumer_class.new
172
- # We use singleton class as the same consumer class may be used to process different
173
- # topics with different settings
174
- consumer.singleton_class.include(strategy)
175
-
176
- # Specific features may expand consumer API beyond the injected strategy. The difference
177
- # here is that strategy impacts the flow of states while extra APIs just provide some
178
- # extra methods with informations, etc but do no deviate the flow behavior
179
- expansions = expansions_selector.find(topic)
180
- expansions.each { |expansion| consumer.singleton_class.include(expansion) }
181
-
182
- consumer.client = @client
183
- consumer.coordinator = @coordinator
184
- # We assign producer only when not available already. It may already be available if
185
- # user redefined the `#producer` method for example. This can be useful for example when
186
- # having a multi-cluster setup and using a totally custom producer
187
- consumer.producer ||= Karafka::App.producer
188
- # Since we have some message-less flows (idle, etc), we initialize consumer with empty
189
- # messages set. In production we have persistent consumers, so this is not a performance
190
- # overhead as this will happen only once per consumer lifetime
191
- consumer.messages = empty_messages
192
-
193
- # Run the post-initialization hook for users that need to run some actions when consumer
194
- # is built and ready (all basic state and info).
195
- # Users should **not** overwrite the `#initialize` because it won't have all the needed
196
- # data assigned yet.
197
- consumer.on_initialized
198
-
199
- consumer
200
- end
201
- end
202
-
203
- # Initializes the messages set in case given operation would happen before any processing
204
- # This prevents us from having no messages object at all as the messages object and
205
- # its metadata may be used for statistics
206
- def empty_messages
207
- Messages::Builders::Messages.call(
208
- [],
209
- topic,
210
- partition,
211
- Time.now
212
- )
213
- end
214
- end
215
- end
216
- end
@@ -1,90 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Karafka
4
- module Processing
5
- # Buffer for executors of a given subscription group. It wraps around the concept of building
6
- # and caching them, so we can re-use them instead of creating new each time.
7
- class ExecutorsBuffer
8
- include Helpers::ConfigImporter.new(
9
- executor_class: %i[internal processing executor_class]
10
- )
11
-
12
- # @param client [Connection::Client]
13
- # @param subscription_group [Routing::SubscriptionGroup]
14
- # @return [ExecutorsBuffer]
15
- def initialize(client, subscription_group)
16
- @subscription_group = subscription_group
17
- @client = client
18
- # We need two layers here to keep track of topics, partitions and processing groups
19
- @buffer = Hash.new { |h, k| h[k] = Hash.new { |h2, k2| h2[k2] = {} } }
20
- end
21
-
22
- # Finds or creates an executor based on the provided details
23
- #
24
- # @param topic [String] topic name
25
- # @param partition [Integer] partition number
26
- # @param parallel_key [String] parallel group key
27
- # @param coordinator [Karafka::Processing::Coordinator]
28
- # @return [Executor, Pro::Processing::Executor] consumer executor
29
- def find_or_create(topic, partition, parallel_key, coordinator)
30
- @buffer[topic][partition][parallel_key] ||= executor_class.new(
31
- @subscription_group.id,
32
- @client,
33
- coordinator
34
- )
35
- end
36
-
37
- # Finds all existing executors for given topic partition or creates one for it
38
- # @param topic [String] topic name
39
- # @param partition [Integer] partition number
40
- # @param coordinator [Karafka::Processing::Coordinator]
41
- # @return [Array<Executor, Pro::Processing::Executor>]
42
- def find_all_or_create(topic, partition, coordinator)
43
- existing = find_all(topic, partition)
44
-
45
- return existing unless existing.empty?
46
-
47
- [find_or_create(topic, partition, 0, coordinator)]
48
- end
49
-
50
- # Revokes executors of a given topic partition, so they won't be used anymore for incoming
51
- # messages
52
- #
53
- # @param topic [String] topic name
54
- # @param partition [Integer] partition number
55
- def revoke(topic, partition)
56
- @buffer[topic][partition].clear
57
- end
58
-
59
- # Finds all the executors available for a given topic partition
60
- #
61
- # @param topic [String] topic name
62
- # @param partition [Integer] partition number
63
- # @return [Array<Executor, Pro::Processing::Executor>] executors in use for this
64
- # topic + partition
65
- def find_all(topic, partition)
66
- @buffer[topic][partition].values
67
- end
68
-
69
- # Iterates over all available executors and yields them together with topic and partition
70
- # info
71
- # @yieldparam [Routing::Topic] karafka routing topic object
72
- # @yieldparam [Integer] partition number
73
- # @yieldparam [Executor, Pro::Processing::Executor] given executor
74
- def each
75
- @buffer.each_value do |partitions|
76
- partitions.each_value do |executors|
77
- executors.each_value do |executor|
78
- yield(executor)
79
- end
80
- end
81
- end
82
- end
83
-
84
- # Clears the executors buffer. Useful for critical errors recovery.
85
- def clear
86
- @buffer.clear
87
- end
88
- end
89
- end
90
- end
@@ -1,22 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Karafka
4
- module Processing
5
- # Selector of appropriate topic setup based features enhancements.
6
- #
7
- # Those expansions to the consumer API are NOT about the flow of processing. For this we have
8
- # strategies. Those are suppose to provide certain extra APIs that user can use to get some
9
- # extra non-flow related functionalities.
10
- class ExpansionsSelector
11
- # @param topic [Karafka::Routing::Topic] topic with settings based on which we find
12
- # expansions
13
- # @return [Array<Module>] modules with proper expansions we're suppose to use to enhance the
14
- # consumer
15
- def find(topic)
16
- expansions = []
17
- expansions << Processing::InlineInsights::Consumer if topic.inline_insights?
18
- expansions
19
- end
20
- end
21
- end
22
- end
@@ -1,43 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Karafka
4
- module Processing
5
- # Namespace of the Inline Insights feature "non routing" related components
6
- #
7
- # @note We use both `#insights` because it is the feature name but also `#statistics` to make
8
- # it consistent with the fact that we publish and operate on statistics. User can pick
9
- # whichever name they prefer.
10
- module InlineInsights
11
- # Module that adds extra methods to the consumer that allow us to fetch the insights
12
- module Consumer
13
- # @return [Hash] empty hash or hash with given partition insights if already present
14
- # @note We cache insights on the consumer, as in some scenarios we may no longer have them
15
- # inside the Tracker, for example under involuntary revocation, incoming statistics may
16
- # no longer have lost partition insights. Since we want to be consistent during single
17
- # batch operations, we want to ensure, that if we have insights they are available
18
- # throughout the whole processing.
19
- def insights
20
- insights = Tracker.find(topic, partition)
21
-
22
- # If we no longer have new insights but we still have them locally, we can use them
23
- return @insights if @insights && insights.empty?
24
- # If insights are still the same, we can use them
25
- return @insights if @insights.equal?(insights)
26
-
27
- # If we've received new insights that are not empty, we can cache them
28
- @insights = insights
29
- end
30
-
31
- # @return [Boolean] true if there are insights to work with, otherwise false
32
- def insights?
33
- !insights.empty?
34
- end
35
-
36
- alias_method :statistics, :insights
37
- alias_method :statistics?, :insights?
38
- alias_method :inline_insights, :insights
39
- alias_method :inline_insights?, :insights?
40
- end
41
- end
42
- end
43
- end
@@ -1,19 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Karafka
4
- module Processing
5
- module InlineInsights
6
- # Listener that adds statistics to our inline tracker
7
- class Listener
8
- # Adds statistics to the tracker
9
- # @param event [Karafka::Core::Monitoring::Event] event with statistics
10
- def on_statistics_emitted(event)
11
- Tracker.add(
12
- event[:consumer_group_id],
13
- event[:statistics]
14
- )
15
- end
16
- end
17
- end
18
- end
19
- end
@@ -1,129 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Karafka
4
- module Processing
5
- module InlineInsights
6
- # Object used to track statistics coming from librdkafka in a way that can be accessible by
7
- # the consumers
8
- #
9
- # We use a single tracker because we do not need state management here as our consumer groups
10
- # clients identified by statistics name value are unique. On top of that, having a per
11
- # process one that is a singleton allows us to use tracker easily also from other places like
12
- # filtering API etc.
13
- #
14
- # @note We include cache of 5 minutes for revoked partitions to compensate for cases where
15
- # when using LRJ a lost partition data would not be present anymore, however we would still
16
- # be in the processing phase. Since those metrics are published with each `poll`, regular
17
- # processing is not a subject of this issue. For LRJ we keep the reference. The only case
18
- # where this could be switched midway is when LRJ is running for an extended period of time
19
- # after the involuntary revocation. Having a time based cache instead of tracking
20
- # simplifies the design as we do not have to deal with state tracking, especially since
21
- # we would have to track also operations running in a revoked state.
22
- #
23
- # @note This tracker keeps in memory data about all topics and partitions that it encounters
24
- # because in case of routing patterns, we may start getting statistics prior to registering
25
- # given topic via dynamic routing expansions. In such case we would not have insights
26
- # where they were actually available for us to use.
27
- #
28
- # @note Memory usage is negligible as long as we can evict expired data. Single metrics set
29
- # for a single partition contains around 4KB of data. This means, that in case of an
30
- # assignment of 1000 partitions, we use around 4MB of space for tracking those metrics.
31
- class Tracker
32
- include Singleton
33
- include Karafka::Core::Helpers::Time
34
-
35
- # Empty hash we want to return in any case where we could not locate appropriate topic
36
- # partition statistics.
37
- EMPTY_HASH = {}.freeze
38
-
39
- # Empty array to save on memory allocations.
40
- EMPTY_ARRAY = [].freeze
41
-
42
- # 5 minutes of cache. We cache last result per consumer group topic partition so we are
43
- # not affected by involuntary rebalances during LRJ execution.
44
- TTL = 5 * 60 * 1_000
45
-
46
- private_constant :EMPTY_HASH, :EMPTY_ARRAY, :TTL
47
-
48
- class << self
49
- extend Forwardable
50
-
51
- def_delegators :instance, :find, :add, :exists?, :clear
52
- end
53
-
54
- # Initializes the tracker with empty accumulator
55
- def initialize
56
- @accu = {}
57
- @mutex = Mutex.new
58
- end
59
-
60
- # Adds each partition statistics into internal accumulator. Single statistics set may
61
- # contain data from multiple topics and their partitions because a single client can
62
- # operate on multiple topics and partitions.
63
- #
64
- # We iterate over those topics and partitions and store topics partitions data only.
65
- #
66
- # @param consumer_group_id [String] id of the consumer group for which statistics were
67
- # emitted.
68
- # @param statistics [Hash] librdkafka enriched statistics
69
- def add(consumer_group_id, statistics)
70
- @mutex.synchronize do
71
- statistics.fetch("topics", EMPTY_HASH).each do |topic_name, t_details|
72
- t_details.fetch("partitions", EMPTY_HASH).each do |partition_id, p_details|
73
- next unless track?(partition_id, p_details)
74
-
75
- key = "#{consumer_group_id}_#{topic_name}_#{partition_id}"
76
- @accu[key] = [monotonic_now, p_details]
77
- end
78
- end
79
-
80
- evict
81
- end
82
- end
83
-
84
- # Finds statistics about requested consumer group topic partition
85
- #
86
- # @param topic [Karafka::Routing::Topic]
87
- # @param partition [Integer]
88
- # @return [Hash] hash with given topic partition statistics or empty hash if not present
89
- #
90
- # @note We do not enclose it with a mutex mainly because the only thing that could happen
91
- # here that would be a race-condition is a miss that anyhow we need to support due to
92
- # how librdkafka ships metrics and a potential removal of data on heavily revoked LRJ.
93
- def find(topic, partition)
94
- key = "#{topic.consumer_group.id}_#{topic.name}_#{partition}"
95
- @accu.fetch(key, EMPTY_ARRAY).last || EMPTY_HASH
96
- end
97
-
98
- # Clears the tracker
99
- def clear
100
- @mutex.synchronize { @accu.clear }
101
- end
102
-
103
- private
104
-
105
- # Evicts expired data from the cache
106
- def evict
107
- @accu.delete_if { |_, details| monotonic_now - details.first > TTL }
108
- end
109
-
110
- # Should we track given partition
111
- #
112
- # We do not track stopped partitions and the once we do not work with actively
113
- # @param partition_id [String] partition id as a string
114
- # @param p_details [Hash] partition statistics details
115
- # @return [Boolean] true if we should track given partition
116
- def track?(partition_id, p_details)
117
- return false if partition_id == "-1"
118
-
119
- fetch_state = p_details.fetch("fetch_state")
120
-
121
- return false if fetch_state == "stopped"
122
- return false if fetch_state == "none"
123
-
124
- true
125
- end
126
- end
127
- end
128
- end
129
- end