breaker_machines 0.9.2-aarch64-linux

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 (58) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE.txt +21 -0
  3. data/README.md +184 -0
  4. data/ext/breaker_machines_native/extconf.rb +3 -0
  5. data/lib/breaker_machines/async_circuit.rb +47 -0
  6. data/lib/breaker_machines/async_support.rb +104 -0
  7. data/lib/breaker_machines/cascading_circuit.rb +177 -0
  8. data/lib/breaker_machines/circuit/async_state_management.rb +71 -0
  9. data/lib/breaker_machines/circuit/base.rb +59 -0
  10. data/lib/breaker_machines/circuit/callbacks.rb +135 -0
  11. data/lib/breaker_machines/circuit/configuration.rb +67 -0
  12. data/lib/breaker_machines/circuit/coordinated_state_management.rb +117 -0
  13. data/lib/breaker_machines/circuit/execution.rb +231 -0
  14. data/lib/breaker_machines/circuit/hedged_execution.rb +115 -0
  15. data/lib/breaker_machines/circuit/introspection.rb +93 -0
  16. data/lib/breaker_machines/circuit/native.rb +127 -0
  17. data/lib/breaker_machines/circuit/state_callbacks.rb +72 -0
  18. data/lib/breaker_machines/circuit/state_management.rb +59 -0
  19. data/lib/breaker_machines/circuit.rb +8 -0
  20. data/lib/breaker_machines/circuit_group.rb +153 -0
  21. data/lib/breaker_machines/console.rb +345 -0
  22. data/lib/breaker_machines/coordinated_circuit.rb +10 -0
  23. data/lib/breaker_machines/dsl/cascading_circuit_builder.rb +20 -0
  24. data/lib/breaker_machines/dsl/circuit_builder.rb +209 -0
  25. data/lib/breaker_machines/dsl/hedged_builder.rb +21 -0
  26. data/lib/breaker_machines/dsl/parallel_fallback_wrapper.rb +20 -0
  27. data/lib/breaker_machines/dsl.rb +283 -0
  28. data/lib/breaker_machines/errors.rb +71 -0
  29. data/lib/breaker_machines/hedged_async_support.rb +88 -0
  30. data/lib/breaker_machines/native_extension.rb +81 -0
  31. data/lib/breaker_machines/native_speedup.rb +10 -0
  32. data/lib/breaker_machines/registry.rb +243 -0
  33. data/lib/breaker_machines/storage/backend_state.rb +69 -0
  34. data/lib/breaker_machines/storage/base.rb +52 -0
  35. data/lib/breaker_machines/storage/bucket_memory.rb +176 -0
  36. data/lib/breaker_machines/storage/cache.rb +169 -0
  37. data/lib/breaker_machines/storage/fallback_chain.rb +294 -0
  38. data/lib/breaker_machines/storage/memory.rb +140 -0
  39. data/lib/breaker_machines/storage/native.rb +93 -0
  40. data/lib/breaker_machines/storage/null.rb +54 -0
  41. data/lib/breaker_machines/storage.rb +8 -0
  42. data/lib/breaker_machines/types.rb +41 -0
  43. data/lib/breaker_machines/version.rb +5 -0
  44. data/lib/breaker_machines.rb +200 -0
  45. data/lib/breaker_machines_native/breaker_machines_native.so +0 -0
  46. data/sig/README.md +74 -0
  47. data/sig/all.rbs +25 -0
  48. data/sig/breaker_machines/circuit.rbs +154 -0
  49. data/sig/breaker_machines/console.rbs +32 -0
  50. data/sig/breaker_machines/dsl.rbs +50 -0
  51. data/sig/breaker_machines/errors.rbs +24 -0
  52. data/sig/breaker_machines/interfaces.rbs +46 -0
  53. data/sig/breaker_machines/registry.rbs +30 -0
  54. data/sig/breaker_machines/storage.rbs +65 -0
  55. data/sig/breaker_machines/types.rbs +97 -0
  56. data/sig/breaker_machines.rbs +42 -0
  57. data/sig/manifest.yaml +5 -0
  58. metadata +224 -0
@@ -0,0 +1,65 @@
1
+ module BreakerMachines
2
+ module Storage
3
+ class Base
4
+ @options: Hash[Symbol, untyped]
5
+
6
+ def initialize: (**untyped options) -> void
7
+
8
+ # Status management
9
+ def get_status: (String circuit_name) -> { status: (:open | :closed | :half_open), opened_at: Float? }?
10
+ def set_status: (String circuit_name, (:open | :closed | :half_open) status, ?Float? opened_at) -> void
11
+
12
+ # Metrics tracking
13
+ def record_success: (String circuit_name, Float duration) -> void
14
+ def record_failure: (String circuit_name, Float duration) -> void
15
+ def success_count: (String circuit_name, Integer window_seconds) -> Integer
16
+ def failure_count: (String circuit_name, Integer window_seconds) -> Integer
17
+
18
+ # Cleanup
19
+ def clear: (String circuit_name) -> void
20
+ def clear_all: () -> void
21
+ end
22
+
23
+ class Memory < Base
24
+ @circuits: Concurrent::Map[String, untyped]
25
+ @events: Concurrent::Map[String, Concurrent::Array[untyped]]
26
+ @event_logs: Concurrent::Map[String, Concurrent::Array[untyped]]
27
+ @max_events: Integer
28
+
29
+ def initialize: (**untyped options) -> void
30
+ def record_event_with_details: (String circuit_name, (:success | :failure | :state_change) type, Float duration, ?error: StandardError?, ?new_state: (:open | :closed | :half_open)?) -> void
31
+ def event_log: (String circuit_name, Integer limit) -> Array[event_record]
32
+
33
+ private
34
+
35
+ def record_event: (String circuit_name, (:success | :failure) type, Float duration) -> void
36
+ def count_events: (String circuit_name, (:success | :failure) type, Integer window_seconds) -> Integer
37
+ def monotonic_time: () -> Float
38
+ end
39
+
40
+ class BucketMemory < Base
41
+ @buckets: Concurrent::Map[String, untyped]
42
+ @bucket_duration: Integer
43
+ @bucket_count: Integer
44
+ @lock: Concurrent::ReentrantReadWriteLock
45
+ @last_cleanup: Concurrent::AtomicReference[Float]
46
+ @cleanup_interval: Integer
47
+
48
+ def record_event_with_details: (String circuit_name, (:success | :failure | :state_change) event_type, Float duration, ?Hash[Symbol, untyped] details) -> void
49
+ def event_log: (String circuit_name, ?Integer limit) -> Array[event_record]
50
+
51
+ private
52
+
53
+ def circuit_buckets: (String circuit_name) -> Hash[Symbol, untyped]
54
+ def current_bucket_index: () -> Integer
55
+ def bucket_indices_for_window: (Integer window_seconds) -> Array[Integer]
56
+ def cleanup_old_buckets: (Hash[Symbol, untyped] buckets) -> void
57
+ def maybe_cleanup_all_buckets: () -> void
58
+ end
59
+
60
+ class Null < Base
61
+ def record_event_with_details: (String circuit_name, Symbol event_type, Float duration, ?Hash[Symbol, untyped] metadata) -> void
62
+ def event_log: (String circuit_name, ?Integer limit) -> Array[untyped]
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,97 @@
1
+ # Common type aliases used throughout BreakerMachines
2
+
3
+ # External dependencies type declarations not included in their gems
4
+ module Concurrent
5
+ class AtomicReference[T]
6
+ def initialize: (?T initial_value) -> void
7
+ def value: () -> T
8
+ def value=: (T value) -> T
9
+ def get: () -> T
10
+ def set: (T value) -> T
11
+ end
12
+
13
+ class AtomicFixnum
14
+ def initialize: (?Integer initial_value) -> void
15
+ def value: () -> Integer
16
+ def value=: (Integer value) -> Integer
17
+ def increment: (?Integer delta) -> Integer
18
+ def decrement: (?Integer delta) -> Integer
19
+ end
20
+
21
+ class ReentrantReadWriteLock
22
+ def initialize: () -> void
23
+ def with_read_lock: [T] () { () -> T } -> T
24
+ def with_write_lock: [T] () { () -> T } -> T
25
+ end
26
+ end
27
+
28
+ class WeakRef[T]
29
+ def initialize: (T object) -> void
30
+ def weakref_alive?: () -> bool
31
+ def __getobj__: () -> T
32
+ end
33
+
34
+ module Zeitwerk
35
+ class Loader
36
+ def push_dir: (String path) -> void
37
+ def setup: () -> void
38
+ def eager_load: () -> void
39
+ end
40
+ end
41
+
42
+ module BreakerMachines
43
+ # Circuit states
44
+ type circuit_state = :open | :closed | :half_open
45
+
46
+ # Event types
47
+ type event_type = :success | :failure | :state_change | :rejection
48
+
49
+ # Callback names
50
+ type callback_name = :on_open | :on_close | :on_half_open | :on_reject
51
+
52
+ # Storage backend symbols
53
+ type storage_backend = :memory | :bucket_memory | :null | :redis
54
+
55
+ # Generic callback proc
56
+ type callback_proc = Proc | nil
57
+
58
+ # Fallback can be a proc, array of procs/values, or any static value
59
+ type fallback_value = Proc | Array[Proc | untyped] | untyped
60
+
61
+ # Options hash for circuits
62
+ type circuit_options = {
63
+ failure_threshold: Integer?,
64
+ failure_window: Integer?,
65
+ success_threshold: Integer?,
66
+ timeout: Integer?,
67
+ reset_timeout: Integer?,
68
+ reset_timeout_jitter: Float?,
69
+ half_open_calls: Integer?,
70
+ storage: (Storage::Base | storage_backend | Class)?,
71
+ metrics: untyped,
72
+ fallback: fallback_value?,
73
+ on_open: callback_proc,
74
+ on_close: callback_proc,
75
+ on_half_open: callback_proc,
76
+ on_reject: callback_proc,
77
+ exceptions: Array[Class]?,
78
+ owner: untyped
79
+ }
80
+
81
+ # Event record structure
82
+ type event_record = {
83
+ timestamp: Float,
84
+ type: event_type,
85
+ duration: Float,
86
+ duration_ms: Float?,
87
+ error_class: String?,
88
+ new_state: circuit_state?,
89
+ details: Hash[Symbol, untyped]?
90
+ }
91
+
92
+ # Status record from storage
93
+ type status_record = {
94
+ status: circuit_state,
95
+ opened_at: Float?
96
+ }
97
+ end
@@ -0,0 +1,42 @@
1
+ module BreakerMachines
2
+ VERSION: String
3
+
4
+ class Configuration
5
+ attr_accessor default_storage: (:memory | :bucket_memory | :null | untyped)
6
+ attr_accessor default_timeout: Integer?
7
+ attr_accessor default_reset_timeout: Integer
8
+ attr_accessor default_failure_threshold: Integer
9
+ attr_accessor log_events: bool
10
+ attr_accessor fiber_safe: bool
11
+
12
+ def initialize: () -> void
13
+ end
14
+
15
+ # Global configuration
16
+ self.@config: Configuration?
17
+ def self.config: () -> Configuration
18
+
19
+ # Class methods
20
+ def self.configure: () { (Configuration config) -> void } -> void
21
+
22
+ # Delegated config accessors for backward compatibility
23
+ def self.default_storage: () -> (:memory | :bucket_memory | :null | untyped)
24
+ def self.default_storage=: ((:memory | :bucket_memory | :null | untyped) value) -> void
25
+ def self.default_timeout: () -> Integer?
26
+ def self.default_timeout=: (Integer? value) -> void
27
+ def self.default_reset_timeout: () -> Integer
28
+ def self.default_reset_timeout=: (Integer value) -> void
29
+ def self.default_failure_threshold: () -> Integer
30
+ def self.default_failure_threshold=: (Integer value) -> void
31
+ def self.log_events: () -> bool
32
+ def self.log_events=: (bool value) -> void
33
+ def self.fiber_safe: () -> bool
34
+ def self.fiber_safe=: (bool value) -> void
35
+ def self.setup_notifications: () -> void
36
+ def self.logger: () -> ActiveSupport::Logger?
37
+ def self.logger=: (ActiveSupport::Logger? logger) -> void
38
+ def self.instrument: (String event, ?Hash[Symbol, untyped] payload) -> void
39
+ def self.console: () -> void
40
+ def self.registry: () -> Registry
41
+ def self.loader: () -> Zeitwerk::Loader
42
+ end
data/sig/manifest.yaml ADDED
@@ -0,0 +1,5 @@
1
+ dependencies:
2
+ - name: activesupport
3
+ - name: concurrent-ruby
4
+ - name: state_machines
5
+ - name: zeitwerk
metadata ADDED
@@ -0,0 +1,224 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: breaker_machines
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.9.2
5
+ platform: aarch64-linux
6
+ authors:
7
+ - Abdelkader Boudih
8
+ bindir: bin
9
+ cert_chain: []
10
+ date: 1980-01-02 00:00:00.000000000 Z
11
+ dependencies:
12
+ - !ruby/object:Gem::Dependency
13
+ name: activesupport
14
+ requirement: !ruby/object:Gem::Requirement
15
+ requirements:
16
+ - - ">="
17
+ - !ruby/object:Gem::Version
18
+ version: '8.0'
19
+ type: :runtime
20
+ prerelease: false
21
+ version_requirements: !ruby/object:Gem::Requirement
22
+ requirements:
23
+ - - ">="
24
+ - !ruby/object:Gem::Version
25
+ version: '8.0'
26
+ - !ruby/object:Gem::Dependency
27
+ name: chrono_machines
28
+ requirement: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - "~>"
31
+ - !ruby/object:Gem::Version
32
+ version: '0.2'
33
+ type: :runtime
34
+ prerelease: false
35
+ version_requirements: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - "~>"
38
+ - !ruby/object:Gem::Version
39
+ version: '0.2'
40
+ - !ruby/object:Gem::Dependency
41
+ name: concurrent-ruby
42
+ requirement: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - "~>"
45
+ - !ruby/object:Gem::Version
46
+ version: '1.3'
47
+ type: :runtime
48
+ prerelease: false
49
+ version_requirements: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - "~>"
52
+ - !ruby/object:Gem::Version
53
+ version: '1.3'
54
+ - !ruby/object:Gem::Dependency
55
+ name: state_machines
56
+ requirement: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ version: 0.100.4
61
+ type: :runtime
62
+ prerelease: false
63
+ version_requirements: !ruby/object:Gem::Requirement
64
+ requirements:
65
+ - - ">="
66
+ - !ruby/object:Gem::Version
67
+ version: 0.100.4
68
+ - !ruby/object:Gem::Dependency
69
+ name: zeitwerk
70
+ requirement: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - "~>"
73
+ - !ruby/object:Gem::Version
74
+ version: '2.7'
75
+ type: :runtime
76
+ prerelease: false
77
+ version_requirements: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - "~>"
80
+ - !ruby/object:Gem::Version
81
+ version: '2.7'
82
+ - !ruby/object:Gem::Dependency
83
+ name: minitest
84
+ requirement: !ruby/object:Gem::Requirement
85
+ requirements:
86
+ - - "~>"
87
+ - !ruby/object:Gem::Version
88
+ version: '5.16'
89
+ type: :development
90
+ prerelease: false
91
+ version_requirements: !ruby/object:Gem::Requirement
92
+ requirements:
93
+ - - "~>"
94
+ - !ruby/object:Gem::Version
95
+ version: '5.16'
96
+ - !ruby/object:Gem::Dependency
97
+ name: rake
98
+ requirement: !ruby/object:Gem::Requirement
99
+ requirements:
100
+ - - "~>"
101
+ - !ruby/object:Gem::Version
102
+ version: '13.0'
103
+ type: :development
104
+ prerelease: false
105
+ version_requirements: !ruby/object:Gem::Requirement
106
+ requirements:
107
+ - - "~>"
108
+ - !ruby/object:Gem::Version
109
+ version: '13.0'
110
+ - !ruby/object:Gem::Dependency
111
+ name: rake-compiler
112
+ requirement: !ruby/object:Gem::Requirement
113
+ requirements:
114
+ - - "~>"
115
+ - !ruby/object:Gem::Version
116
+ version: '1.3'
117
+ type: :development
118
+ prerelease: false
119
+ version_requirements: !ruby/object:Gem::Requirement
120
+ requirements:
121
+ - - "~>"
122
+ - !ruby/object:Gem::Version
123
+ version: '1.3'
124
+ description: |
125
+ BreakerMachines is a production-ready circuit breaker implementation for Ruby that prevents
126
+ cascade failures in distributed systems. Built on the battle-tested state_machines gem, it
127
+ provides a clean DSL, thread-safe operations, multiple storage backends, and comprehensive
128
+ introspection tools. Unlike other solutions, BreakerMachines prioritizes safety by avoiding
129
+ dangerous forceful timeouts while supporting fallback chains, jitter, and event callbacks.
130
+ email:
131
+ - terminale@gmail.com
132
+ executables: []
133
+ extensions: []
134
+ extra_rdoc_files: []
135
+ files:
136
+ - LICENSE.txt
137
+ - README.md
138
+ - ext/breaker_machines_native/extconf.rb
139
+ - lib/breaker_machines.rb
140
+ - lib/breaker_machines/async_circuit.rb
141
+ - lib/breaker_machines/async_support.rb
142
+ - lib/breaker_machines/cascading_circuit.rb
143
+ - lib/breaker_machines/circuit.rb
144
+ - lib/breaker_machines/circuit/async_state_management.rb
145
+ - lib/breaker_machines/circuit/base.rb
146
+ - lib/breaker_machines/circuit/callbacks.rb
147
+ - lib/breaker_machines/circuit/configuration.rb
148
+ - lib/breaker_machines/circuit/coordinated_state_management.rb
149
+ - lib/breaker_machines/circuit/execution.rb
150
+ - lib/breaker_machines/circuit/hedged_execution.rb
151
+ - lib/breaker_machines/circuit/introspection.rb
152
+ - lib/breaker_machines/circuit/native.rb
153
+ - lib/breaker_machines/circuit/state_callbacks.rb
154
+ - lib/breaker_machines/circuit/state_management.rb
155
+ - lib/breaker_machines/circuit_group.rb
156
+ - lib/breaker_machines/console.rb
157
+ - lib/breaker_machines/coordinated_circuit.rb
158
+ - lib/breaker_machines/dsl.rb
159
+ - lib/breaker_machines/dsl/cascading_circuit_builder.rb
160
+ - lib/breaker_machines/dsl/circuit_builder.rb
161
+ - lib/breaker_machines/dsl/hedged_builder.rb
162
+ - lib/breaker_machines/dsl/parallel_fallback_wrapper.rb
163
+ - lib/breaker_machines/errors.rb
164
+ - lib/breaker_machines/hedged_async_support.rb
165
+ - lib/breaker_machines/native_extension.rb
166
+ - lib/breaker_machines/native_speedup.rb
167
+ - lib/breaker_machines/registry.rb
168
+ - lib/breaker_machines/storage.rb
169
+ - lib/breaker_machines/storage/backend_state.rb
170
+ - lib/breaker_machines/storage/base.rb
171
+ - lib/breaker_machines/storage/bucket_memory.rb
172
+ - lib/breaker_machines/storage/cache.rb
173
+ - lib/breaker_machines/storage/fallback_chain.rb
174
+ - lib/breaker_machines/storage/memory.rb
175
+ - lib/breaker_machines/storage/native.rb
176
+ - lib/breaker_machines/storage/null.rb
177
+ - lib/breaker_machines/types.rb
178
+ - lib/breaker_machines/version.rb
179
+ - lib/breaker_machines_native/breaker_machines_native.so
180
+ - sig/README.md
181
+ - sig/all.rbs
182
+ - sig/breaker_machines.rbs
183
+ - sig/breaker_machines/circuit.rbs
184
+ - sig/breaker_machines/console.rbs
185
+ - sig/breaker_machines/dsl.rbs
186
+ - sig/breaker_machines/errors.rbs
187
+ - sig/breaker_machines/interfaces.rbs
188
+ - sig/breaker_machines/registry.rbs
189
+ - sig/breaker_machines/storage.rbs
190
+ - sig/breaker_machines/types.rbs
191
+ - sig/manifest.yaml
192
+ homepage: https://github.com/seuros/breaker_machines
193
+ licenses:
194
+ - MIT
195
+ metadata:
196
+ homepage_uri: https://github.com/seuros/breaker_machines
197
+ source_code_uri: https://github.com/seuros/breaker_machines
198
+ bug_tracker_uri: https://github.com/seuros/breaker_machines/issues
199
+ documentation_uri: https://github.com/seuros/breaker_machines#readme
200
+ rubygems_mfa_required: 'true'
201
+ cargo_crate_name: breaker_machines_native
202
+ cargo_manifest_path: ext/breaker_machines_native/ffi/Cargo.toml
203
+ rdoc_options: []
204
+ require_paths:
205
+ - lib
206
+ required_ruby_version: !ruby/object:Gem::Requirement
207
+ requirements:
208
+ - - ">="
209
+ - !ruby/object:Gem::Version
210
+ version: '3.4'
211
+ - - "<"
212
+ - !ruby/object:Gem::Version
213
+ version: 3.5.dev
214
+ required_rubygems_version: !ruby/object:Gem::Requirement
215
+ requirements:
216
+ - - ">="
217
+ - !ruby/object:Gem::Version
218
+ version: '0'
219
+ requirements: []
220
+ rubygems_version: 3.6.9
221
+ specification_version: 4
222
+ summary: Circuit breaker implementation for Ruby with a clean DSL and state_machines
223
+ under the hood
224
+ test_files: []