cmdx 1.21.0 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (195) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +118 -1
  3. data/README.md +37 -24
  4. data/lib/cmdx/.DS_Store +0 -0
  5. data/lib/cmdx/callbacks.rb +179 -0
  6. data/lib/cmdx/chain.rb +78 -175
  7. data/lib/cmdx/coercions/array.rb +19 -33
  8. data/lib/cmdx/coercions/big_decimal.rb +12 -29
  9. data/lib/cmdx/coercions/boolean.rb +25 -45
  10. data/lib/cmdx/coercions/coerce.rb +32 -0
  11. data/lib/cmdx/coercions/complex.rb +12 -27
  12. data/lib/cmdx/coercions/date.rb +29 -33
  13. data/lib/cmdx/coercions/date_time.rb +29 -33
  14. data/lib/cmdx/coercions/float.rb +8 -29
  15. data/lib/cmdx/coercions/hash.rb +17 -43
  16. data/lib/cmdx/coercions/integer.rb +8 -32
  17. data/lib/cmdx/coercions/rational.rb +12 -33
  18. data/lib/cmdx/coercions/string.rb +6 -24
  19. data/lib/cmdx/coercions/symbol.rb +12 -26
  20. data/lib/cmdx/coercions/time.rb +31 -35
  21. data/lib/cmdx/coercions.rb +174 -0
  22. data/lib/cmdx/configuration.rb +45 -237
  23. data/lib/cmdx/context.rb +264 -243
  24. data/lib/cmdx/deprecation.rb +67 -0
  25. data/lib/cmdx/deprecators/error.rb +22 -0
  26. data/lib/cmdx/deprecators/log.rb +22 -0
  27. data/lib/cmdx/deprecators/warn.rb +21 -0
  28. data/lib/cmdx/deprecators.rb +101 -0
  29. data/lib/cmdx/errors.rb +145 -79
  30. data/lib/cmdx/executors/fiber.rb +42 -0
  31. data/lib/cmdx/executors/thread.rb +36 -0
  32. data/lib/cmdx/executors.rb +95 -0
  33. data/lib/cmdx/fault.rb +85 -78
  34. data/lib/cmdx/i18n_proxy.rb +104 -0
  35. data/lib/cmdx/input.rb +294 -0
  36. data/lib/cmdx/inputs.rb +218 -0
  37. data/lib/cmdx/log_formatters/json.rb +9 -20
  38. data/lib/cmdx/log_formatters/key_value.rb +10 -21
  39. data/lib/cmdx/log_formatters/line.rb +7 -19
  40. data/lib/cmdx/log_formatters/logstash.rb +8 -21
  41. data/lib/cmdx/log_formatters/raw.rb +8 -20
  42. data/lib/cmdx/logger_proxy.rb +30 -0
  43. data/lib/cmdx/mergers/deep_merge.rb +23 -0
  44. data/lib/cmdx/mergers/last_write_wins.rb +23 -0
  45. data/lib/cmdx/mergers/no_merge.rb +20 -0
  46. data/lib/cmdx/mergers.rb +95 -0
  47. data/lib/cmdx/middlewares.rb +128 -0
  48. data/lib/cmdx/output.rb +115 -0
  49. data/lib/cmdx/outputs.rb +66 -0
  50. data/lib/cmdx/pipeline.rb +144 -131
  51. data/lib/cmdx/railtie.rb +10 -36
  52. data/lib/cmdx/result.rb +247 -524
  53. data/lib/cmdx/retriers/bounded_random.rb +24 -0
  54. data/lib/cmdx/retriers/decorrelated_jitter.rb +28 -0
  55. data/lib/cmdx/retriers/exponential.rb +23 -0
  56. data/lib/cmdx/retriers/fibonacci.rb +39 -0
  57. data/lib/cmdx/retriers/full_random.rb +23 -0
  58. data/lib/cmdx/retriers/half_random.rb +24 -0
  59. data/lib/cmdx/retriers/linear.rb +23 -0
  60. data/lib/cmdx/retriers.rb +106 -0
  61. data/lib/cmdx/retry.rb +117 -138
  62. data/lib/cmdx/runtime.rb +251 -0
  63. data/lib/cmdx/settings.rb +68 -200
  64. data/lib/cmdx/signal.rb +165 -0
  65. data/lib/cmdx/task.rb +443 -343
  66. data/lib/cmdx/telemetry.rb +108 -0
  67. data/lib/cmdx/util.rb +73 -0
  68. data/lib/cmdx/validators/absence.rb +10 -39
  69. data/lib/cmdx/validators/exclusion.rb +33 -52
  70. data/lib/cmdx/validators/format.rb +19 -49
  71. data/lib/cmdx/validators/inclusion.rb +33 -54
  72. data/lib/cmdx/validators/length.rb +125 -127
  73. data/lib/cmdx/validators/numeric.rb +123 -123
  74. data/lib/cmdx/validators/presence.rb +10 -39
  75. data/lib/cmdx/validators/validate.rb +31 -0
  76. data/lib/cmdx/validators.rb +161 -0
  77. data/lib/cmdx/version.rb +2 -4
  78. data/lib/cmdx/workflow.rb +71 -96
  79. data/lib/cmdx.rb +111 -42
  80. data/lib/generators/cmdx/install_generator.rb +7 -17
  81. data/lib/generators/cmdx/task_generator.rb +12 -29
  82. data/lib/generators/cmdx/templates/install.rb +120 -48
  83. data/lib/generators/cmdx/templates/task.rb.tt +1 -1
  84. data/lib/generators/cmdx/templates/workflow.rb.tt +1 -2
  85. data/lib/generators/cmdx/workflow_generator.rb +12 -29
  86. data/lib/locales/en.yml +8 -7
  87. data/mkdocs.yml +25 -23
  88. metadata +39 -138
  89. data/lib/cmdx/attribute.rb +0 -440
  90. data/lib/cmdx/attribute_registry.rb +0 -185
  91. data/lib/cmdx/attribute_value.rb +0 -252
  92. data/lib/cmdx/callback_registry.rb +0 -169
  93. data/lib/cmdx/coercion_registry.rb +0 -138
  94. data/lib/cmdx/deprecator.rb +0 -77
  95. data/lib/cmdx/exception.rb +0 -46
  96. data/lib/cmdx/executor.rb +0 -378
  97. data/lib/cmdx/identifier.rb +0 -30
  98. data/lib/cmdx/locale.rb +0 -78
  99. data/lib/cmdx/middleware_registry.rb +0 -148
  100. data/lib/cmdx/middlewares/correlate.rb +0 -140
  101. data/lib/cmdx/middlewares/runtime.rb +0 -77
  102. data/lib/cmdx/middlewares/timeout.rb +0 -78
  103. data/lib/cmdx/parallelizer.rb +0 -100
  104. data/lib/cmdx/utils/call.rb +0 -53
  105. data/lib/cmdx/utils/condition.rb +0 -71
  106. data/lib/cmdx/utils/format.rb +0 -82
  107. data/lib/cmdx/utils/normalize.rb +0 -52
  108. data/lib/cmdx/utils/wrap.rb +0 -38
  109. data/lib/cmdx/validator_registry.rb +0 -143
  110. data/lib/generators/cmdx/locale_generator.rb +0 -39
  111. data/lib/locales/af.yml +0 -55
  112. data/lib/locales/ar.yml +0 -55
  113. data/lib/locales/az.yml +0 -55
  114. data/lib/locales/be.yml +0 -55
  115. data/lib/locales/bg.yml +0 -55
  116. data/lib/locales/bn.yml +0 -55
  117. data/lib/locales/bs.yml +0 -55
  118. data/lib/locales/ca.yml +0 -55
  119. data/lib/locales/cnr.yml +0 -55
  120. data/lib/locales/cs.yml +0 -55
  121. data/lib/locales/cy.yml +0 -55
  122. data/lib/locales/da.yml +0 -55
  123. data/lib/locales/de.yml +0 -55
  124. data/lib/locales/dz.yml +0 -55
  125. data/lib/locales/el.yml +0 -55
  126. data/lib/locales/eo.yml +0 -55
  127. data/lib/locales/es.yml +0 -55
  128. data/lib/locales/et.yml +0 -55
  129. data/lib/locales/eu.yml +0 -55
  130. data/lib/locales/fa.yml +0 -55
  131. data/lib/locales/fi.yml +0 -55
  132. data/lib/locales/fr.yml +0 -55
  133. data/lib/locales/fy.yml +0 -55
  134. data/lib/locales/gd.yml +0 -55
  135. data/lib/locales/gl.yml +0 -55
  136. data/lib/locales/he.yml +0 -55
  137. data/lib/locales/hi.yml +0 -55
  138. data/lib/locales/hr.yml +0 -55
  139. data/lib/locales/hu.yml +0 -55
  140. data/lib/locales/hy.yml +0 -55
  141. data/lib/locales/id.yml +0 -55
  142. data/lib/locales/is.yml +0 -55
  143. data/lib/locales/it.yml +0 -55
  144. data/lib/locales/ja.yml +0 -55
  145. data/lib/locales/ka.yml +0 -55
  146. data/lib/locales/kk.yml +0 -55
  147. data/lib/locales/km.yml +0 -55
  148. data/lib/locales/kn.yml +0 -55
  149. data/lib/locales/ko.yml +0 -55
  150. data/lib/locales/lb.yml +0 -55
  151. data/lib/locales/lo.yml +0 -55
  152. data/lib/locales/lt.yml +0 -55
  153. data/lib/locales/lv.yml +0 -55
  154. data/lib/locales/mg.yml +0 -55
  155. data/lib/locales/mk.yml +0 -55
  156. data/lib/locales/ml.yml +0 -55
  157. data/lib/locales/mn.yml +0 -55
  158. data/lib/locales/mr-IN.yml +0 -55
  159. data/lib/locales/ms.yml +0 -55
  160. data/lib/locales/nb.yml +0 -55
  161. data/lib/locales/ne.yml +0 -55
  162. data/lib/locales/nl.yml +0 -55
  163. data/lib/locales/nn.yml +0 -55
  164. data/lib/locales/oc.yml +0 -55
  165. data/lib/locales/or.yml +0 -55
  166. data/lib/locales/pa.yml +0 -55
  167. data/lib/locales/pl.yml +0 -55
  168. data/lib/locales/pt.yml +0 -55
  169. data/lib/locales/rm.yml +0 -55
  170. data/lib/locales/ro.yml +0 -55
  171. data/lib/locales/ru.yml +0 -55
  172. data/lib/locales/sc.yml +0 -55
  173. data/lib/locales/sk.yml +0 -55
  174. data/lib/locales/sl.yml +0 -55
  175. data/lib/locales/sq.yml +0 -55
  176. data/lib/locales/sr.yml +0 -55
  177. data/lib/locales/st.yml +0 -55
  178. data/lib/locales/sv.yml +0 -55
  179. data/lib/locales/sw.yml +0 -55
  180. data/lib/locales/ta.yml +0 -55
  181. data/lib/locales/te.yml +0 -55
  182. data/lib/locales/th.yml +0 -55
  183. data/lib/locales/tl.yml +0 -55
  184. data/lib/locales/tr.yml +0 -55
  185. data/lib/locales/tt.yml +0 -55
  186. data/lib/locales/ug.yml +0 -55
  187. data/lib/locales/uk.yml +0 -55
  188. data/lib/locales/ur.yml +0 -55
  189. data/lib/locales/uz.yml +0 -55
  190. data/lib/locales/vi.yml +0 -55
  191. data/lib/locales/wo.yml +0 -55
  192. data/lib/locales/zh-CN.yml +0 -55
  193. data/lib/locales/zh-HK.yml +0 -55
  194. data/lib/locales/zh-TW.yml +0 -55
  195. data/lib/locales/zh-YUE.yml +0 -55
@@ -2,188 +2,36 @@
2
2
 
3
3
  module CMDx
4
4
 
5
- # Configuration class that manages global settings for CMDx including middlewares,
6
- # callbacks, coercions, validators, breakpoints, backtraces, and logging.
5
+ # Global defaults used by every task unless the task overrides via
6
+ # `Task.settings`/register DSL. A fresh `Task` subclass inherits the current
7
+ # configuration's registries (via `#dup`) at the time its accessor is first
8
+ # called, so changes to configuration only apply to tasks that haven't
9
+ # cached their copy yet.
7
10
  class Configuration
8
11
 
9
- # @rbs DEFAULT_BREAKPOINTS: Array[String]
10
- DEFAULT_BREAKPOINTS = %w[failed].freeze
12
+ attr_accessor :middlewares, :callbacks, :coercions, :validators, :executors,
13
+ :mergers, :retriers, :deprecators, :telemetry, :correlation_id, :default_locale,
14
+ :strict_context, :backtrace_cleaner, :log_exclusions, :log_formatter,
15
+ :log_level, :logger
11
16
 
12
- # @rbs DEFAULT_ROLLPOINTS: Array[String]
13
- DEFAULT_ROLLPOINTS = %w[failed].freeze
14
-
15
- # Returns the middleware registry for task execution.
16
- #
17
- # @return [MiddlewareRegistry] The middleware registry
18
- #
19
- # @example
20
- # config.middlewares.register(CustomMiddleware)
21
- #
22
- # @rbs @middlewares: MiddlewareRegistry
23
- attr_accessor :middlewares
24
-
25
- # Returns the callback registry for task lifecycle hooks.
26
- #
27
- # @return [CallbackRegistry] The callback registry
28
- #
29
- # @example
30
- # config.callbacks.register(:before_execution, :log_start)
31
- #
32
- # @rbs @callbacks: CallbackRegistry
33
- attr_accessor :callbacks
34
-
35
- # Returns the coercion registry for type conversions.
36
- #
37
- # @return [CoercionRegistry] The coercion registry
38
- #
39
- # @example
40
- # config.coercions.register(:custom, CustomCoercion)
41
- #
42
- # @rbs @coercions: CoercionRegistry
43
- attr_accessor :coercions
44
-
45
- # Returns the validator registry for attribute validation.
46
- #
47
- # @return [ValidatorRegistry] The validator registry
48
- #
49
- # @example
50
- # config.validators.register(:email, EmailValidator)
51
- #
52
- # @rbs @validators: ValidatorRegistry
53
- attr_accessor :validators
54
-
55
- # Returns the breakpoint statuses for task execution interruption.
56
- #
57
- # @return [Array<String>] Array of status names that trigger breakpoints
58
- #
59
- # @example
60
- # config.task_breakpoints = ["failed", "skipped"]
61
- #
62
- # @rbs @task_breakpoints: Array[String]
63
- attr_accessor :task_breakpoints
64
-
65
- # Returns the breakpoint statuses for workflow execution interruption.
66
- #
67
- # @return [Array<String>] Array of status names that trigger breakpoints
68
- #
69
- # @example
70
- # config.workflow_breakpoints = ["failed", "skipped"]
71
- #
72
- # @rbs @task_breakpoints: Array[String]
73
- # @rbs @workflow_breakpoints: Array[String]
74
- attr_accessor :workflow_breakpoints
75
-
76
- # Returns the logger instance for CMDx operations.
77
- #
78
- # @return [Logger] The logger instance
79
- #
80
- # @example
81
- # config.logger.level = Logger::DEBUG
82
- #
83
- # @rbs @logger: Logger
84
- attr_accessor :logger
85
-
86
- # Returns whether to log backtraces for failed tasks.
87
- #
88
- # @return [Boolean] true if backtraces should be logged
89
- #
90
- # @example
91
- # config.backtrace = true
92
- #
93
- # @rbs @backtrace: bool
94
- attr_accessor :backtrace
95
-
96
- # Returns the proc used to clean backtraces before logging.
97
- #
98
- # @return [Proc, nil] The backtrace cleaner proc, or nil if not set
99
- #
100
- # @example
101
- # config.backtrace_cleaner = ->(bt) { bt.first(5) }
102
- #
103
- # @rbs @backtrace_cleaner: (Proc | nil)
104
- attr_accessor :backtrace_cleaner
105
-
106
- # Returns the proc called when exceptions occur during execution.
107
- #
108
- # @return [Proc, nil] The exception handler proc, or nil if not set
109
- #
110
- # @example
111
- # config.exception_handler = ->(task, error) { Sentry.capture_exception(error) }
112
- #
113
- # @rbs @exception_handler: (Proc | nil)
114
- attr_accessor :exception_handler
115
-
116
- # Returns the statuses that trigger a task execution rollback.
117
- #
118
- # @return [Array<String>] Array of status names that trigger rollback
119
- #
120
- # @example
121
- # config.rollback_on = ["failed", "skipped"]
122
- #
123
- # @rbs @rollback_on: Array[String]
124
- attr_accessor :rollback_on
125
-
126
- # Returns whether to include context data in hash representation output.
127
- #
128
- # @return [Boolean] true if context should be included (default: false)
129
- #
130
- # @example
131
- # config.dump_context = true
132
- #
133
- # @rbs @dump_context: bool
134
- attr_accessor :dump_context
135
-
136
- # Returns whether to freeze task results after execution.
137
- # Set to false in test environments to allow stubbing on result objects.
138
- #
139
- # @return [Boolean] true if results should be frozen (default: true)
140
- #
141
- # @example
142
- # config.freeze_results = false
143
- #
144
- # @rbs @freeze_results: bool
145
- attr_accessor :freeze_results
146
-
147
- # Returns the default locale used for built-in translation lookups.
148
- # Must match the basename of a YAML file in lib/locales/ (e.g. "en", "es", "ja").
149
- #
150
- # @return [String] The locale identifier (default: "en")
151
- #
152
- # @example
153
- # config.default_locale = "es"
154
- #
155
- # @rbs @locale: String
156
- attr_accessor :default_locale
157
-
158
- # Initializes a new Configuration instance with default values.
159
- #
160
- # Creates new registry instances for middlewares, callbacks, coercions, and
161
- # validators. Sets default breakpoints and configures a basic logger.
162
- #
163
- # @return [Configuration] a new Configuration instance
164
- #
165
- # @example
166
- # config = Configuration.new
167
- # config.middlewares.class # => MiddlewareRegistry
168
- # config.task_breakpoints # => ["failed"]
169
- #
170
- # @rbs () -> void
171
17
  def initialize
172
- @middlewares = MiddlewareRegistry.new
173
- @callbacks = CallbackRegistry.new
174
- @coercions = CoercionRegistry.new
175
- @validators = ValidatorRegistry.new
176
-
177
- @task_breakpoints = DEFAULT_BREAKPOINTS
178
- @workflow_breakpoints = DEFAULT_BREAKPOINTS
179
- @rollback_on = DEFAULT_ROLLPOINTS
180
- @dump_context = false
181
- @freeze_results = true
182
- @default_locale = "en"
183
-
184
- @backtrace = false
18
+ @middlewares = Middlewares.new
19
+ @callbacks = Callbacks.new
20
+ @coercions = Coercions.new
21
+ @validators = Validators.new
22
+ @executors = Executors.new
23
+ @mergers = Mergers.new
24
+ @retriers = Retriers.new
25
+ @deprecators = Deprecators.new
26
+ @telemetry = Telemetry.new
27
+
28
+ @correlation_id = nil
29
+ @default_locale = "en"
30
+ @strict_context = false
185
31
  @backtrace_cleaner = nil
186
- @exception_handler = nil
32
+ @log_exclusions = EMPTY_ARRAY
33
+ @log_formatter = nil
34
+ @log_level = nil
187
35
 
188
36
  @logger = Logger.new(
189
37
  $stdout,
@@ -193,69 +41,22 @@ module CMDx
193
41
  )
194
42
  end
195
43
 
196
- # Converts the configuration to a hash representation.
197
- #
198
- # @return [Hash{Symbol => Object}] hash containing all configuration values
199
- #
200
- # @example
201
- # config = Configuration.new
202
- # config.to_h
203
- # # => { middlewares: #<MiddlewareRegistry>, callbacks: #<CallbackRegistry>, ... }
204
- #
205
- # @rbs () -> Hash[Symbol, untyped]
206
- def to_h
207
- {
208
- middlewares: @middlewares,
209
- callbacks: @callbacks,
210
- coercions: @coercions,
211
- validators: @validators,
212
- task_breakpoints: @task_breakpoints,
213
- workflow_breakpoints: @workflow_breakpoints,
214
- rollback_on: @rollback_on,
215
- freeze_results: @freeze_results,
216
- default_locale: @default_locale,
217
- backtrace: @backtrace,
218
- backtrace_cleaner: @backtrace_cleaner,
219
- exception_handler: @exception_handler,
220
- dump_context: @dump_context,
221
- logger: @logger
222
- }
223
- end
224
-
225
44
  end
226
45
 
227
46
  extend self
228
47
 
229
- # Returns the global configuration instance, creating it if it doesn't exist.
230
- #
231
- # @return [Configuration] the global configuration instance
232
- #
233
- # @example
234
- # config = CMDx.configuration
235
- # config.middlewares # => #<MiddlewareRegistry>
236
- #
237
- # @rbs () -> Configuration
48
+ # @return [Configuration] the lazily-initialized global configuration
238
49
  def configuration
239
50
  return @configuration if @configuration
240
51
 
241
52
  @configuration ||= Configuration.new
242
53
  end
243
54
 
244
- # Configures CMDx using a block that receives the configuration instance.
245
- #
246
- # @yield [Configuration] the configuration instance to configure
247
- #
248
- # @return [Configuration] the configured configuration instance
249
- #
250
- # @raise [ArgumentError] when no block is provided
55
+ # Yields the global configuration for mutation.
251
56
  #
252
- # @example
253
- # CMDx.configure do |config|
254
- # config.task_breakpoints = ["failed", "skipped"]
255
- # config.logger.level = Logger::DEBUG
256
- # end
257
- #
258
- # @rbs () { (Configuration) -> void } -> Configuration
57
+ # @yield [Configuration]
58
+ # @return [Configuration]
59
+ # @raise [ArgumentError] when no block is given
259
60
  def configure
260
61
  raise ArgumentError, "block required" unless block_given?
261
62
 
@@ -264,17 +65,24 @@ module CMDx
264
65
  config
265
66
  end
266
67
 
267
- # Resets the global configuration to a new instance with default values.
268
- #
269
- # @return [Configuration] the new configuration instance
270
- #
271
- # @example
272
- # CMDx.reset_configuration!
273
- # # Configuration is now reset to defaults
68
+ # Replaces the global configuration with a fresh instance and invalidates
69
+ # the cached registries on `Task` so new lookups rebuild from the new config.
70
+ # Intended for test setup/teardown.
274
71
  #
275
- # @rbs () -> Configuration
72
+ # @return [void]
276
73
  def reset_configuration!
277
74
  @configuration = Configuration.new
75
+ return unless defined?(Task)
76
+
77
+ Task.instance_variable_set(:@middlewares, nil)
78
+ Task.instance_variable_set(:@callbacks, nil)
79
+ Task.instance_variable_set(:@coercions, nil)
80
+ Task.instance_variable_set(:@validators, nil)
81
+ Task.instance_variable_set(:@executors, nil)
82
+ Task.instance_variable_set(:@mergers, nil)
83
+ Task.instance_variable_set(:@retriers, nil)
84
+ Task.instance_variable_set(:@deprecators, nil)
85
+ Task.instance_variable_set(:@telemetry, nil)
278
86
  end
279
87
 
280
88
  end