sc4ry 0.2.0 → 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,57 +1,58 @@
1
- Dir[File.dirname(__FILE__) + '/*.rb'].sort.each { |file| require file unless File.basename(file) == 'init.rb' }
1
+ # frozen_string_literal: true
2
+
3
+ Dir["#{File.dirname(__FILE__)}/*.rb"].sort.each { |file| require file unless File.basename(file) == 'init.rb' }
2
4
 
3
5
  # Sc4ry module
4
6
  # @note namespace
5
- module Sc4ry
6
-
7
- # Sc4ry::Notifiers module
8
- # @note namespace
9
- module Notifiers
10
-
7
+ module Sc4ry
8
+ # Sc4ry::Notifiers module
9
+ # @note namespace
10
+ module Notifiers
11
11
  # default notifiers specifications
12
- DEFAULT_NOTIFIERS = {:prometheus => {:class => Sc4ry::Notifiers::Prometheus, :config => {:url => 'http://localhost:9091'}},
13
- :mattermost => {:class => Sc4ry::Notifiers::Mattermost, :config => {:url => 'http://localhost:9999', :token => "<CHANGE_ME>"}}
14
- }
15
- @@notifiers_list = DEFAULT_NOTIFIERS.dup
16
-
12
+ DEFAULT_NOTIFIERS = { prometheus: { class: Sc4ry::Notifiers::Prometheus, config: { url: 'http://localhost:9091' } },
13
+ mattermost: { class: Sc4ry::Notifiers::Mattermost, config: { url: 'http://localhost:9999', token: '<CHANGE_ME>' } } }
14
+ @@notifiers_list = DEFAULT_NOTIFIERS.dup
15
+
17
16
  # class method how display a specific notifier config
18
17
  # @param notifier [Symbol] a notifier name
19
- # @return [Hash] the config
20
- def Notifiers.display_config(notifier: )
21
- raise Sc4ry::Exceptions::Sc4ryNotifierError, "Notifier #{notifier} not found" unless @@notifiers_list.include? notifier
22
- return @@notifiers_list[notifier][:config]
18
+ # @return [Hash] the config
19
+ def self.display_config(notifier:)
20
+ unless @@notifiers_list.include? notifier
21
+ raise Sc4ry::Exceptions::Sc4ryNotifierError,
22
+ "Notifier #{notifier} not found"
23
+ end
24
+
25
+ @@notifiers_list[notifier][:config]
23
26
  end
24
27
 
25
28
  # class method how return the list of known notifiers
26
29
  # @return [Array] a list of [Symbol] notifiers name
27
- def Notifiers.list
28
- return @@notifiers_list.keys
30
+ def self.list
31
+ @@notifiers_list.keys
29
32
  end
30
33
 
31
34
  # class method how return a specific notifier by name
32
35
  # @param name [Symbol] a notifier name
33
- # @return [Hash] the notifier structure
34
- def Notifiers.get(name: )
35
- return @@notifiers_list[name]
36
+ # @return [Hash] the notifier structure
37
+ def self.get(name:)
38
+ @@notifiers_list[name]
36
39
  end
37
40
 
38
- # class method how register a specific notifier
41
+ # class method how register a specific notifier
39
42
  # @param name [Symbol] a notifier name
40
- # @param definition [Hash] a notifier definition
41
- # @return [Hash] the notifier structure
42
- def Notifiers.register(name: , definition: )
43
+ # @param definition [Hash] a notifier definition
44
+ # @return [Hash] the notifier structure
45
+ def self.register(name:, definition:)
43
46
  @@notifiers_list[name] = definition
44
47
  end
45
48
 
46
-
47
- # class method how configure a specific notifier
49
+ # class method how configure a specific notifier
48
50
  # @param name [Symbol] a notifier name
49
- # @param config [Hash] a notifier config
50
- # @return [Hash] the notifier structure
51
- def Notifiers.config(name:, config: )
51
+ # @param config [Hash] a notifier config
52
+ # @return [Hash] the notifier structure
53
+ def self.config(name:, config:)
52
54
  @@notifiers_list[name][:config] = config
53
- return config
55
+ config
54
56
  end
55
- end
57
+ end
56
58
  end
57
-
@@ -1,43 +1,42 @@
1
+ # frozen_string_literal: true
2
+
1
3
  # Sc4ry module
2
- # @note namespace
4
+ # @note namespace
3
5
  module Sc4ry
4
- # Sc4ry::Notifiers module
5
- # @note namespace
6
- module Notifiers
7
-
8
- # Mattermost Notifier class
9
- class Mattermost
10
-
11
- # send metrics to Prometheus PushGateway
12
- # @return [Bool]
13
- def Mattermost.notify(options = {})
14
- config = Sc4ry::Notifiers.get(name: :mattermost)[:config]
15
- status = options[:config][:status][:general]
16
- circuit = options[:circuit]
17
- status_map = {:open => 0, :half_open => 1, :closed => 2}
18
- begin
19
- uri = URI.parse("#{config[:url]}/hooks/#{config[:token]}")
20
- message = "notifying for circuit #{circuit.to_s}, state : #{status.to_s}."
21
- if Sc4ry::Helpers::verify_service url: config[:url] then
22
- request = ::Net::HTTP::Post.new(uri)
23
- request.content_type = "application/json"
24
- req_options = {
25
- use_ssl: uri.scheme == "https",
26
- }
27
- payload = { "text" => "message : #{message } from #{Socket.gethostname}", "username" => "Sc4ry" }
28
- Sc4ry::Helpers.log level: :debug, message: "Mattermost Notifying : #{message}"
29
- request.body = ::JSON.dump(payload)
30
- response = ::Net::HTTP.start(uri.hostname, uri.port, req_options) do |http|
31
- http.request(request)
32
- end
33
-
34
- else
35
- Sc4ry::Helpers.log level: :warn, message: "Mattermost Notifier : can't notify Mattermost not reachable."
36
- end
37
- rescue URI::InvalidURIError
38
- Sc4ry::Helpers.log level: :warn, message: "Mattermost Notifier : URL malformed"
39
- end
6
+ # Sc4ry::Notifiers module
7
+ # @note namespace
8
+ module Notifiers
9
+ # Mattermost Notifier class
10
+ class Mattermost
11
+ # send metrics to Prometheus PushGateway
12
+ # @return [Bool]
13
+ def self.notify(options = {})
14
+ config = Sc4ry::Notifiers.get(name: :mattermost)[:config]
15
+ status = options[:config][:status][:general]
16
+ circuit = options[:circuit]
17
+ begin
18
+ uri = URI.parse("#{config[:url]}/hooks/#{config[:token]}")
19
+ message = "notifying for circuit #{circuit}, state : #{status}."
20
+ if Sc4ry::Helpers.verify_service url: config[:url]
21
+ request = ::Net::HTTP::Post.new(uri)
22
+ request.content_type = 'application/json'
23
+ req_options = {
24
+ use_ssl: uri.scheme == 'https'
25
+ }
26
+ payload = { 'text' => "message : #{message} from #{Socket.gethostname}", 'username' => 'Sc4ry' }
27
+ Sc4ry::Helpers.log level: :debug, message: "Mattermost Notifying : #{message}"
28
+ request.body = ::JSON.dump(payload)
29
+ ::Net::HTTP.start(uri.hostname, uri.port, req_options) do |http|
30
+ http.request(request)
40
31
  end
32
+
33
+ else
34
+ Sc4ry::Helpers.log level: :warn, message: "Mattermost Notifier : can't notify Mattermost not reachable."
35
+ end
36
+ rescue URI::InvalidURIError
37
+ Sc4ry::Helpers.log level: :warn, message: 'Mattermost Notifier : URL malformed'
41
38
  end
39
+ end
42
40
  end
43
- end
41
+ end
42
+ end
@@ -1,43 +1,39 @@
1
+ # frozen_string_literal: true
2
+
1
3
  # Sc4ry module
2
4
  # @note namespace
3
5
  module Sc4ry
4
-
5
6
  # Sc4ry::Notifiers module
6
7
  # @note namespace
7
8
  module Notifiers
8
-
9
-
10
9
  # Prometheus notifier class
11
10
  class Prometheus
12
-
13
- @@registry = ::Prometheus::Client::Registry::new
14
- @@metric_circuit_state = ::Prometheus::Client::Gauge.new(:cuircuit_state, docstring: 'Sc4ry metric : state of a circuit', labels: [:circuit])
11
+ @@registry = ::Prometheus::Client::Registry.new
12
+ @@metric_circuit_state = ::Prometheus::Client::Gauge.new(:cuircuit_state,
13
+ docstring: 'Sc4ry metric : state of a circuit',
14
+ labels: [:circuit])
15
15
 
16
16
  @@registry.register(@@metric_circuit_state)
17
17
 
18
-
19
-
20
18
  # send metrics to Prometheus PushGateway
21
19
  # @return [Bool]
22
- def Prometheus.notify(options = {})
20
+ def self.notify(options = {})
23
21
  @config = Sc4ry::Notifiers.get(name: :prometheus)[:config]
24
22
  status = options[:config][:status][:general]
25
23
  circuit = options[:circuit]
26
- status_map = {:open => 0, :half_open => 1, :closed => 2}
27
- if Sc4ry::Helpers::verify_service url: @config[:url] then
28
-
29
- @@metric_circuit_state.set(status_map[status], labels: {circuit: circuit.to_s })
30
- Sc4ry::Helpers.log level: :debug, message: "Prometheus Notifier : notifying for circuit #{circuit.to_s}, state : #{status.to_s}."
24
+ status_map = { open: 0, half_open: 1, closed: 2 }
25
+ if Sc4ry::Helpers.verify_service url: @config[:url]
26
+
27
+ @@metric_circuit_state.set(status_map[status], labels: { circuit: circuit.to_s })
28
+ Sc4ry::Helpers.log level: :debug,
29
+ message: "Prometheus Notifier : notifying for circuit #{circuit}, state : #{status}."
31
30
 
32
- return ::Prometheus::Client::Push.new(job: "Sc4ry", instance: Socket.gethostname, gateway: @config[:url]).add(@@registry)
31
+ ::Prometheus::Client::Push.new(job: 'Sc4ry', instance: Socket.gethostname,
32
+ gateway: @config[:url]).add(@@registry)
33
33
  else
34
34
  Sc4ry::Helpers.log level: :warn, message: "Prometheus Notifier : can't notify Push Gateway not reachable."
35
35
  end
36
36
  end
37
37
  end
38
-
39
-
40
-
41
38
  end
42
-
43
39
  end
@@ -1,16 +1,15 @@
1
+ # frozen_string_literal: true
1
2
 
2
3
  # Sc4ry module
3
- # @note namespace
4
+ # @note namespace
4
5
  module Sc4ry
5
-
6
6
  # class Facility to run and update values/status for a circuit Proc
7
7
  class RunController
8
-
9
8
  # return the execution time of the proc
10
9
  attr_reader :execution_time
11
10
 
12
11
  # constructor
13
- # @param [Hash] circuit the data of the circuit
12
+ # @param [Hash] circuit the data of the circuit
14
13
  def initialize(circuit = {})
15
14
  @circuit = circuit
16
15
  @execution_time = 0
@@ -22,59 +21,53 @@ module Sc4ry
22
21
  # return if the Proc failed on a covered exception by this circuit
23
22
  # @return [Boolean]
24
23
  def failed?
25
- return @failure
26
- end
24
+ @failure
25
+ end
27
26
 
28
27
  # return if the Proc overtime the specified time of the circuit
29
28
  # @return [Boolean]
30
- def overtimed?
31
- return @overtime
29
+ def overtimed?
30
+ @overtime
32
31
  end
33
32
 
34
33
  # return if the Proc timeout the timeout defined value of the circuit, if timeout is active
35
34
  # @return [Boolean]
36
- def timeout?
37
- return @timeout
35
+ def timeout?
36
+ @timeout
38
37
  end
39
38
 
40
39
  # run and update values for the bloc given by keyword
41
40
  # @param [Proc] block a block to run and calculate
42
41
  # @return [Hash] a result Hash
43
- def run(block: )
42
+ def run(block:)
44
43
  start_time = Process.clock_gettime(Process::CLOCK_MONOTONIC)
45
- begin
44
+ begin
46
45
  if @circuit[:timeout] == true
47
- Timeout::timeout(@circuit[:timeout_value]) do
46
+ Timeout.timeout(@circuit[:timeout_value]) do
48
47
  block.call
49
48
  end
50
49
  @timeout = false
51
50
  else
52
51
  block.call
53
52
  end
54
- rescue Exception => e
53
+ rescue StandardError => e
55
54
  @last_exception = e.class.to_s
56
- if e.class == Timeout::Error then
55
+ if e.instance_of?(Timeout::Error)
57
56
  @timeout = true
58
57
  elsif @circuit[:exceptions].include? e.class
59
58
  @failure = true
60
- else
61
- if @circuit[:forward_unknown_exceptions] then
59
+ elsif @circuit[:forward_unknown_exceptions]
60
+ raise e.class, "Sc4ry forward: #{e.message}"
61
+ else
62
+ Sc4ry::Helpers.log level: :debug, message: "skipped : #{@last_exception}"
62
63
 
63
- raise e.class, "Sc4ry forward: #{e.message}"
64
- else
65
- Sc4ry::Helpers.log level: :debug, message: "skipped : #{@last_exception}"
66
- end
67
-
68
- end
64
+ end
69
65
  end
70
66
  @end_time = Process.clock_gettime(Process::CLOCK_MONOTONIC)
71
67
  @execution_time = @end_time - start_time
72
- @overtime = @execution_time > @circuit[:max_time]
73
- return {failure: @failure, overtime: @overtime, timeout: @timeout, execution_time: @execution_time, end_time: @end_time, last_exception: @last_exception}
74
-
68
+ @overtime = @execution_time > @circuit[:max_time]
69
+ { failure: @failure, overtime: @overtime, timeout: @timeout, execution_time: @execution_time,
70
+ end_time: @end_time, last_exception: @last_exception }
75
71
  end
76
-
77
-
78
-
79
72
  end
80
- end
73
+ end
data/lib/sc4ry/store.rb CHANGED
@@ -1,29 +1,29 @@
1
+ # frozen_string_literal: true
2
+
1
3
  # Sc4ry module
2
4
  # @note namespace
3
5
  module Sc4ry
4
-
5
- # Sc4ry::Store class
6
- # Store Class Provider/manager singleton Forwarder on {Sc4ry::Backends::Memory} or {Sc4ry::Backends::Redis}
7
- # @note must be accessed by {Sc4ry::Circuits.store}
6
+ # Sc4ry::Store class
7
+ # Store Class Provider/manager singleton Forwarder on {Sc4ry::Backends::Memory} or {Sc4ry::Backends::Redis}
8
+ # @note must be accessed by {Sc4ry::Circuits.store}
8
9
  class Store
9
-
10
10
  @@current = :memory
11
11
 
12
12
  extend Forwardable
13
13
  include Singleton
14
14
 
15
- @@backends = {:memory => {:class => Sc4ry::Backends::Memory, config: {}},
16
- :redis => {:class => Sc4ry::Backends::Redis, :config => {:host => 'localhost', :port => 6379, :db => 10 }}}
15
+ @@backends = { memory: { class: Sc4ry::Backends::Memory, config: {} },
16
+ redis: { class: Sc4ry::Backends::Redis, config: { host: 'localhost', port: 6379, db: 1 } } }
17
17
 
18
18
  # accessor on current backend (default :memory)
19
19
  attr_reader :be
20
-
20
+
21
21
  def_delegators :@be, :put, :get, :flush, :exist?, :del, :list
22
22
 
23
23
  # constructor pointing on :memory backend
24
24
  def initialize
25
- change_backend name: @@current
26
- end
25
+ change_backend name: @@current
26
+ end
27
27
 
28
28
  # return the current backend
29
29
  # @return [Object] in {Sc4ry::Backends::Memory} or {Sc4ry::Backends::Redis}
@@ -31,75 +31,81 @@ module Sc4ry
31
31
  # include Sc4ry
32
32
  # puts Circuits.store.current
33
33
  def current
34
- return @@current
34
+ @@current
35
35
  end
36
36
 
37
37
  # return the config of a specific backend
38
- # @param [Symbol] backend the name the backend
39
- # @return [Hash] the config of the backend
38
+ # @param [Symbol] backend the name the backend
39
+ # @return [Hash] the config of the backend
40
40
  # @raise Sc4ry::Exceptions::Sc4ryBackendError if backend is not found
41
41
  # @example usage
42
42
  # include Sc4ry
43
43
  # puts Circuits.store.get_config backend: :redis
44
- def get_config(backend: )
44
+ def get_config(backend:)
45
45
  raise Sc4ry::Exceptions::Sc4ryBackendError, "backend #{backend} not found" unless @@backends.include? backend
46
- return @@backends[backend][:config]
46
+
47
+ @@backends[backend][:config]
47
48
  end
48
49
 
49
- # list backend available
50
+ # list backend available
50
51
  # @return [Array] of Symbol the list of backend name
51
52
  # @example usage
52
53
  # include Sc4ry
53
54
  # puts Circuits.store.list_backend
54
55
  def list_backend
55
- return @@backends.keys
56
+ @@backends.keys
56
57
  end
57
58
 
58
- # change the current backend
59
- # @note if changing form :memory to :redis => all values and result are lost and circuits will be lost
60
- # @note if changing to :redis, get all the define circuits with values and status (ideal) for distributed worker/instance/runner/services
59
+ # change the current backend
60
+ # @note if changing form :memory to :redis => all values and result are lost and circuits will be lost
61
+ # @note if changing to :redis, get all the define circuits with values and status (ideal)
62
+ # @note for distributed worker/instance/runner/services
61
63
  # @param [Symbol] name the name of the target backend
62
64
  # @return [Symbol] the name of the new current backend
63
65
  # @raise Sc4ry::Exceptions::Sc4ryBackendError if backend is not found
64
- def change_backend(name: )
66
+ def change_backend(name:)
65
67
  raise Sc4ry::Exceptions::Sc4ryBackendError, "backend #{name} not found" unless @@backends.include? name
68
+
66
69
  @@current = name
67
- @be = @@backends[@@current][:class]::new(@@backends[@@current][:config])
68
- return name
70
+ @be = @@backends[@@current][:class].new(@@backends[@@current][:config])
71
+ name
69
72
  end
70
73
 
71
- # register a new backend
74
+ # register a new backend
72
75
  # @param [Symbol] name the name of the backend
73
76
  # @param [Hash] config the config for this backend
74
- # @param [Class] backend_class the class name of the new backend
77
+ # @param [Class] backend_class the class name of the new backend
75
78
  # @raise Sc4ry::Exceptions::Sc4ryBackendError if backend already exist
76
- # @return [Symbol] the name of the backend
77
- def register_backend(name:, config: {}, backend_class:)
78
- raise Sc4ry::Exceptions::Sc4ryBackendError , "backend #{name} already exist" if @@backends.include? name
79
- @@backends[name] = {config: config, class: backend_class}
80
- return name
79
+ # @return [Symbol] the name of the backend
80
+ def register_backend(name:, backend_class:, config: {})
81
+ raise Sc4ry::Exceptions::Sc4ryBackendError, "backend #{name} already exist" if @@backends.include? name
82
+
83
+ @@backends[name] = { config: config, class: backend_class }
84
+ name
81
85
  end
82
86
 
83
87
  # delete the specified backend reference
84
88
  # @param [Symbol] name the name of the target backend
85
89
  # @raise Sc4ry::Exceptions::Sc4ryBackendError if backend is not found, or name == :memory or :redis
86
90
  # @return [Boolean]
87
- def delete_backend(name: )
88
- raise Sc4ry::Exceptions::Sc4ryBackendError , "Delete forbidden for backend in [:redis,:memory]" if [:memory,:redis].include? name
89
- raise Sc4ry::Exceptions::Sc4ryBackendError , "backend #{name} not found" unless @@backends.include? name
90
- return @@backends.delete(name)
91
+ def delete_backend(name:)
92
+ forbidden_mes = 'Delete forbidden for backend in [:redis,:memory]'
93
+ notfound_mes = "backend #{name} not found"
94
+ raise Sc4ry::Exceptions::Sc4ryBackendError, forbidden_mes if %i[memory redis].include? name
95
+ raise Sc4ry::Exceptions::Sc4ryBackendError, notfound_mes unless @@backends.include? name
96
+
97
+ @@backends.delete(name)
91
98
  end
92
-
99
+
93
100
  # change the specified backend config
94
101
  # @param [Symbol] name the name of the target backend
95
102
  # @param [Hash] config the config of the specified backend
96
103
  # @raise Sc4ry::Exceptions::Sc4ryBackendError if backend is not found, or name == :memory
97
104
  def config_backend(name:, config:)
98
105
  raise Sc4ry::Exceptions::Sc4ryBackendError, "backend #{name} not found" unless @@backends.include? name
99
- raise Sc4ry::Exceptions::Sc4ryBackendError, "backend :memory not need config" if name == :memory
106
+ raise Sc4ry::Exceptions::Sc4ryBackendError, 'backend :memory not need config' if name == :memory
107
+
100
108
  @@backends[name][:config] = config
101
109
  end
102
-
103
-
104
110
  end
105
- end
111
+ end
data/lib/sc4ry/version.rb CHANGED
@@ -1,9 +1,10 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'version'
2
4
 
3
5
  # Sc4ry module
4
6
  # @note namespace
5
7
  module Sc4ry
6
-
7
8
  # the version of Sc4ry
8
9
  VERSION = Version.current
9
10
  end
data/lib/sc4ry.rb CHANGED
@@ -1,10 +1,4 @@
1
- require "sc4ry/version"
2
- require "sc4ry/dependencies"
3
-
4
-
5
-
6
-
7
-
8
-
9
-
1
+ # frozen_string_literal: true
10
2
 
3
+ require 'sc4ry/version'
4
+ require 'sc4ry/dependencies'
data/samples/test.rb ADDED
@@ -0,0 +1,159 @@
1
+ require 'rubygems'
2
+ require 'sc4ry'
3
+
4
+ include Sc4ry
5
+
6
+ # display of default Sc4ry config
7
+ puts '1.1/ CONFIG : Initial default config'
8
+ Circuits.default_config.each do |item, value|
9
+ puts " * #{item} : #{value}"
10
+ end
11
+ puts ''
12
+
13
+ # testing the two ways to configure Sc4ry default config
14
+ puts '1.2/ CONFIG : modifying default config activate timout and set max_time to 12'
15
+ Circuits.merge_default_config diff: { timeout: true }
16
+ Circuits.configure do |spec|
17
+ spec.max_time = 12
18
+ end
19
+ puts ''
20
+
21
+ # display default config, must be override with a nested hash by calling default_config= method
22
+ puts '1.3/ CONFIG : Default config updated:'
23
+ Circuits.default_config.each do |item, value|
24
+ puts " * #{item} : #{value}"
25
+ end
26
+ puts ''
27
+
28
+ # display current data Store
29
+ print '2.1/ STORE : Current datastore backend : '
30
+ puts Circuits.store.current
31
+ puts ''
32
+
33
+ # display available backend
34
+ puts '2.2/ STORE : List of existing backends : '
35
+ Circuits.store.list_backend.each do |backend|
36
+ puts " - #{backend}"
37
+ end
38
+ puts ''
39
+
40
+ # display Redis backend config in store before change
41
+ puts '2.3/ STORE : display default config of redis backend'
42
+ Circuits.store.get_config(backend: :redis).each do |item, value|
43
+ puts " * #{item} : #{value}"
44
+ end
45
+ puts ''
46
+
47
+ # reconfigure a backend
48
+ puts '2.4/ STORE : reconfigure Redis backend'
49
+ Circuits.store.config_backend name: :redis, config: { host: 'localhost', port: 6379, db: 10 }
50
+ puts
51
+
52
+ # display after
53
+ puts '2.5/ STORE : display altered config of redis backend'
54
+ Circuits.store.get_config(backend: :redis).each do |item, value|
55
+ puts " * #{item} : #{value}"
56
+ end
57
+ puts ''
58
+
59
+ # change backend
60
+
61
+ puts '2.6/ STORE : change to redis backend (NEED a Redis installed) '
62
+ puts ' $ docker pull redis:latest'
63
+ puts ' $ docker run --rm -d -p 6379:6379/tcp redis:latest'
64
+ Circuits.store.change_backend name: :redis
65
+ puts ''
66
+
67
+ puts '2.7/ STORE : flush redis backend, just for test, and for idempotency (NEED a Redis installed) '
68
+ Circuits.store.flush
69
+ puts ''
70
+
71
+ # defining a circuit, config must be empty or override from default
72
+ puts '3.1/ CIRCUIT : registering a circuit by merge :'
73
+ Circuits.register circuit: :test, config: { notifiers: %i[prometheus mattermost], exceptions: [Errno::ECONNREFUSED, URI::InvalidURIError] }
74
+ puts ''
75
+
76
+ puts '3.2/ CIRCUIT : registering a circuit by block :'
77
+ Circuits.register circuit: :test2 do |spec|
78
+ spec.exceptions = [Errno::ECONNREFUSED]
79
+ end
80
+ puts ''
81
+
82
+ puts '3.3/ CIRCUIT : registering a circuit by default :'
83
+ Circuits.register circuit: :test3
84
+ puts ''
85
+
86
+ puts '3.4/ CIRCUITS : Circuits list'
87
+ Circuits.list.each do |circuit|
88
+ puts " * #{circuit}"
89
+ end
90
+ puts ''
91
+
92
+ puts '3.5/ CIRCUIT : display a circuit config :test3 :'
93
+ Circuits.get(circuit: :test3).each do |item, value|
94
+ puts " * #{item} : #{value}"
95
+ end
96
+ puts ''
97
+
98
+ puts '3.6/ CIRCUIT : update config of :test3 => :raise_on_opening == true :'
99
+ Circuits.update_config circuit: :test3, config: { raise_on_opening: true }
100
+ puts ''
101
+
102
+ puts '3.7/ CIRCUIT : display a circuit config :test3 after change :'
103
+ Circuits.get(circuit: :test3).each do |item, value|
104
+ puts " * #{item} : #{value}"
105
+ end
106
+ puts ''
107
+
108
+ puts '3.8/ unregister a circuit : :test2 :'
109
+ Circuits.unregister circuit: :test2
110
+ puts ''
111
+
112
+ puts '3.9/ CIRCUITS : Circuits list after unregister'
113
+ Circuits.list.each do |circuit|
114
+ puts " * #{circuit}"
115
+ end
116
+ puts ''
117
+
118
+ # Config an alternate logger
119
+
120
+ puts '4.1/ LOGGER : register a logger on file '
121
+ Circuits.loggers.register name: :perso, instance: ::Logger.new('/tmp/logfile.log')
122
+ puts ''
123
+
124
+ puts '4.2/ LOGGER : get the list of available loggers'
125
+ Circuits.loggers.list_available.each do |logger|
126
+ puts " * #{logger}"
127
+ end
128
+ puts ''
129
+
130
+ puts '4.3/ LOGGER : change logger to :perso'
131
+ Circuits.loggers.current = :perso
132
+ puts ''
133
+
134
+ # sample Mattermost notification
135
+ puts '5/ set notifier mattermost on dummy url, change with your slack or mattermost server'
136
+ Sc4ry::Notifiers.config name: :mattermost, config: { url: 'https://mattermost.mycorp.com', token: '<TOKEN>' }
137
+ puts ''
138
+
139
+ # sample loop
140
+ puts '6/ running circuits test, please wait ... (see /tmp/logfile.log for result)'
141
+ puts ' check endoint status for different result, you cloud use http://github.com/Ultragreen/MockWS for testing endpoint, on an other tty'
142
+ puts ' $ git clone https://github.com/Ultragreen/MockWS.git'
143
+ puts ' $ cd MockWS'
144
+ puts ' $ rackup'
145
+ begin
146
+ 10.times do
147
+ sleep 1
148
+ Circuits.run circuit: :test do
149
+ # for the test choose or build an endpoint you must shutdown
150
+ puts RestClient.get('http://localhost:9292/test2/data')
151
+ end
152
+ end
153
+ rescue Interrupt
154
+ puts 'Interrputed'
155
+ ensure
156
+ Circuits.store.flush
157
+ end
158
+
159
+ puts 'end'