imperium 0.2.2 → 0.2.3
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.
- checksums.yaml +4 -4
- data/bin/console +6 -0
- data/lib/imperium.rb +8 -2
- data/lib/imperium/agent.rb +48 -0
- data/lib/imperium/agent_list_checks_response.rb +24 -0
- data/lib/imperium/agent_list_services_response.rb +36 -0
- data/lib/imperium/api_object.rb +83 -0
- data/lib/imperium/catalog.rb +29 -0
- data/lib/imperium/catalog/service.rb +76 -0
- data/lib/imperium/http_client.rb +5 -1
- data/lib/imperium/kv_pair.rb +3 -23
- data/lib/imperium/refinements/hash_compact.rb +11 -0
- data/lib/imperium/response.rb +39 -0
- data/lib/imperium/service.rb +87 -0
- data/lib/imperium/service_check.rb +100 -0
- data/lib/imperium/version.rb +1 -1
- metadata +11 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 707891835377b95b0bbfad486145b8c3ab3394a6
|
4
|
+
data.tar.gz: b076560dd3acaa8327cc96459db5dcb63fecca03
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 509f7e2d9d6b888c3de92acc1a4472bb4df0c8032a060236db73bf169804553525ab94a2e9a3741f092cb0f4b53039eee236ecca2e2a704bfb5e0cfc64001d18
|
7
|
+
data.tar.gz: d0f25997c35f608f545a9470067cc4a8679799fa01683a2a52b0ec483f9ccc9792b60948da83be88cf552351b82826e56891f2c4c3bafb3d38a176caa757b65f
|
data/bin/console
CHANGED
@@ -10,5 +10,11 @@ require "imperium"
|
|
10
10
|
# require "pry"
|
11
11
|
# Pry.start
|
12
12
|
|
13
|
+
Imperium.configure do |conf|
|
14
|
+
conf.host = ENV.fetch('IMPERIUM_CONSUL_HOST', 'localhost')
|
15
|
+
conf.port = Integer(ENV.fetch('IMPERIUM_CONSUL_PORT', 8500))
|
16
|
+
conf.ssl = ENV.fetch('IMPERIUM_CONSUL_SSL', 'false') == 'true'
|
17
|
+
end
|
18
|
+
|
13
19
|
require "irb"
|
14
20
|
IRB.start
|
data/lib/imperium.rb
CHANGED
@@ -1,15 +1,21 @@
|
|
1
1
|
require 'imperium/error'
|
2
2
|
|
3
|
-
require 'imperium/
|
3
|
+
require 'imperium/agent'
|
4
|
+
require 'imperium/agent_list_checks_response'
|
5
|
+
require 'imperium/agent_list_services_response'
|
6
|
+
require 'imperium/catalog'
|
4
7
|
require 'imperium/client'
|
5
|
-
require 'imperium/
|
8
|
+
require 'imperium/configuration'
|
6
9
|
require 'imperium/event_fire_response'
|
7
10
|
require 'imperium/events'
|
11
|
+
require 'imperium/http_client'
|
8
12
|
require 'imperium/kv'
|
9
13
|
require 'imperium/kv_pair'
|
10
14
|
require 'imperium/kv_get_response'
|
11
15
|
require 'imperium/kv_put_response'
|
12
16
|
require 'imperium/response'
|
17
|
+
require 'imperium/service'
|
18
|
+
require 'imperium/service_check'
|
13
19
|
require 'imperium/version'
|
14
20
|
|
15
21
|
module Imperium
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require 'imperium/client'
|
2
|
+
|
3
|
+
module Imperium
|
4
|
+
# A client for the Agent API.
|
5
|
+
class Agent < Client
|
6
|
+
self.path_prefix = 'v1/agent'.freeze
|
7
|
+
|
8
|
+
# Deregister a service with the agent.
|
9
|
+
#
|
10
|
+
# @see https://www.consul.io/api/agent/service.html#deregister-service Consul's Documentation
|
11
|
+
#
|
12
|
+
# @param service_or_id [Service, String] The object or id representing the
|
13
|
+
# service to be removed from the services registry.
|
14
|
+
def deregister_service(service_or_id)
|
15
|
+
id = (service_or_id.is_a?(Service) ? service_or_id.id : service_or_id)
|
16
|
+
Response.new(@http_client.put(prefix_path("service/deregister/#{id}"), ''))
|
17
|
+
end
|
18
|
+
|
19
|
+
# Retreive a list of all checks registered to the local agent.
|
20
|
+
#
|
21
|
+
# @see https://www.consul.io/api/agent/check.html#list-checks Consul's Documentation
|
22
|
+
# @return [AgentListChecksResponse]
|
23
|
+
def list_checks
|
24
|
+
response = @http_client.get(prefix_path('checks'))
|
25
|
+
AgentListChecksResponse.new(response)
|
26
|
+
end
|
27
|
+
|
28
|
+
# Retreive a list of all services registered to the local agent.
|
29
|
+
#
|
30
|
+
# @see https://www.consul.io/api/agent/service.html#list-services Consul's Documentation
|
31
|
+
# @return [AgentListServicesResponse]
|
32
|
+
def list_services
|
33
|
+
response = @http_client.get(prefix_path('services'))
|
34
|
+
AgentListServicesResponse.new(response)
|
35
|
+
end
|
36
|
+
|
37
|
+
# Register a new service with the agent.
|
38
|
+
#
|
39
|
+
# @see https://www.consul.io/api/agent/service.html#register-service Consul's Documentation
|
40
|
+
#
|
41
|
+
# @param service [Serivce] A {Service} object containing the data to use
|
42
|
+
# for registration
|
43
|
+
def register_service(service)
|
44
|
+
Response.new(@http_client.put(prefix_path('service/register'), service.registration_data))
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
@@ -0,0 +1,24 @@
|
|
1
|
+
require_relative 'response'
|
2
|
+
require_relative 'service_check'
|
3
|
+
|
4
|
+
module Imperium
|
5
|
+
class AgentListChecksResponse < Response
|
6
|
+
self.default_response_object_class = ServiceCheck
|
7
|
+
|
8
|
+
def checks
|
9
|
+
@checks ||= checks_hash.values
|
10
|
+
end
|
11
|
+
|
12
|
+
def checks_hash
|
13
|
+
@checks_hash ||= (ok? ? coerced_body : {})
|
14
|
+
end
|
15
|
+
|
16
|
+
def [](key)
|
17
|
+
checks_hash[key]
|
18
|
+
end
|
19
|
+
|
20
|
+
def each(&block)
|
21
|
+
checks.each(&block)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
require_relative 'response'
|
2
|
+
require_relative 'service'
|
3
|
+
|
4
|
+
module Imperium
|
5
|
+
# AgentListServiceResponse is a wrapper for the raw HTTP::Message response
|
6
|
+
# from the API
|
7
|
+
#
|
8
|
+
# @note This class doesn't really make sense to be instantiated outside of
|
9
|
+
# {Agent#list_services}
|
10
|
+
#
|
11
|
+
# We've included Enumerable and implemented #each so it can be treated as an
|
12
|
+
# array of {Service} objects.
|
13
|
+
class AgentListServicesResponse < Response
|
14
|
+
self.default_response_object_class = Service
|
15
|
+
|
16
|
+
def each(&block)
|
17
|
+
services.each(&block)
|
18
|
+
end
|
19
|
+
|
20
|
+
# Build an array of {Service} objects from the response
|
21
|
+
#
|
22
|
+
# @return [Array<Service>] This array will be empty when the response is not
|
23
|
+
# a success
|
24
|
+
def services
|
25
|
+
@services ||= services_hash.values
|
26
|
+
end
|
27
|
+
|
28
|
+
# Build a hash of {Service} object from the response
|
29
|
+
#
|
30
|
+
# The keys are the service's id from the API response.
|
31
|
+
# @return [Hash<String => Service>]
|
32
|
+
def services_hash
|
33
|
+
@services_hash ||= (ok? ? coerced_body : {})
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,83 @@
|
|
1
|
+
require_relative 'refinements/hash_compact'
|
2
|
+
module Imperium
|
3
|
+
# Base class for handling data coming from the Consul API
|
4
|
+
class APIObject
|
5
|
+
using HashCompact
|
6
|
+
|
7
|
+
class << self
|
8
|
+
# The mapping of attribute names coming from Consul to names that are more
|
9
|
+
# Ruby friendly
|
10
|
+
# @return [Hash<String => Symbol>]
|
11
|
+
attr_reader :attribute_map
|
12
|
+
|
13
|
+
# The Ruby friendly names from {attribute_map}
|
14
|
+
# @return [Array<Symbol>]
|
15
|
+
attr_reader :ruby_attribute_names
|
16
|
+
|
17
|
+
def attribute_map=(val)
|
18
|
+
@attribute_map = val
|
19
|
+
@ruby_attribute_names = val.values.map(&:to_sym)
|
20
|
+
attr_accessor *@ruby_attribute_names
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
# Initialize a new object extracting attributes from the supplied hash
|
25
|
+
def initialize(attributes = {})
|
26
|
+
self.class.attribute_map.each do |key, attribute_name|
|
27
|
+
value = attributes[attribute_name] || attributes[key]
|
28
|
+
send("#{attribute_name}=", value) if value
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
def ==(other)
|
33
|
+
return false unless self.class == other.class
|
34
|
+
ruby_attribute_names.all? { |attr| self.send(attr) == other.send(attr) }
|
35
|
+
end
|
36
|
+
|
37
|
+
def attribute_map
|
38
|
+
self.class.attribute_map
|
39
|
+
end
|
40
|
+
|
41
|
+
# Shortcut method to access the class level attribute
|
42
|
+
# @return [Array<Symbol>]
|
43
|
+
def ruby_attribute_names
|
44
|
+
self.class.ruby_attribute_names
|
45
|
+
end
|
46
|
+
|
47
|
+
# Convert the object and any sub-objects into a hash
|
48
|
+
#
|
49
|
+
# @param consul_names_as_keys [Boolean] Use the Consul object attribute names
|
50
|
+
# as the keys when true (default) otherwise use the ruby attribute names.
|
51
|
+
def to_h(consul_names_as_keys: true)
|
52
|
+
if consul_names_as_keys
|
53
|
+
attribute_map.each_with_object({}) do |(consul, ruby), h|
|
54
|
+
h[consul] = maybe_hashified_attribute(ruby, true)
|
55
|
+
end.compact
|
56
|
+
else
|
57
|
+
ruby_attribute_names.each_with_object({}) do |attr, h|
|
58
|
+
h[attr] = maybe_hashified_attribute(attr, false)
|
59
|
+
end.compact
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
private
|
64
|
+
|
65
|
+
def maybe_hashified_attribute(attr_name, consul_names)
|
66
|
+
val = send(attr_name)
|
67
|
+
|
68
|
+
if val.nil?
|
69
|
+
nil
|
70
|
+
elsif val.is_a?(Array)
|
71
|
+
val.map { |elem| elem.respond_to?(:to_h) ? fancy_send_to_h(elem, consul_names) : elem }
|
72
|
+
elsif val.respond_to?(:to_h)
|
73
|
+
fancy_send_to_h(val, consul_names)
|
74
|
+
else
|
75
|
+
val
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
def fancy_send_to_h(obj, consul_names)
|
80
|
+
(obj.is_a?(APIObject) ? obj.to_h(consul_names_as_keys: consul_names) : obj.to_h)
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
require_relative 'client'
|
2
|
+
|
3
|
+
module Imperium
|
4
|
+
# A client for the Catalog API.
|
5
|
+
class Catalog < Client
|
6
|
+
self.path_prefix = 'v1/catalog'.freeze
|
7
|
+
|
8
|
+
# List services in the global catalog
|
9
|
+
#
|
10
|
+
# @return [Response]
|
11
|
+
def list_services
|
12
|
+
response = @http_client.get(prefix_path('services'))
|
13
|
+
Response.new(response)
|
14
|
+
end
|
15
|
+
|
16
|
+
# List the known nodes for the given service in the global catalog
|
17
|
+
#
|
18
|
+
# Returns a {Response} object that coerces the returned data into {Service}
|
19
|
+
# objects
|
20
|
+
#
|
21
|
+
# @param [String] :service
|
22
|
+
# @return [Array<Service>]
|
23
|
+
def list_nodes_for_service(service)
|
24
|
+
response = @http_client.get(prefix_path("service/#{service}"))
|
25
|
+
Response.new(response, response_object_class: Service)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
require_relative 'catalog/service'
|
@@ -0,0 +1,76 @@
|
|
1
|
+
require_relative '../api_object'
|
2
|
+
|
3
|
+
module Imperium
|
4
|
+
class Catalog
|
5
|
+
# Service is a container for data being received from and sent to the
|
6
|
+
# catalog APIs.
|
7
|
+
#
|
8
|
+
# @see https://www.consul.io/api/catalog.html#list-nodes-for-service The Consul Catalog Documentation
|
9
|
+
#
|
10
|
+
# @!attribute [rw] id
|
11
|
+
# @return [String]
|
12
|
+
# @!attribute [rw] node
|
13
|
+
# @return [String]
|
14
|
+
# @!attribute [rw] address
|
15
|
+
# @return [String]
|
16
|
+
# @!attribute [rw] datacenter
|
17
|
+
# @return [String]
|
18
|
+
# @!attribute [rw] tagged_addresses
|
19
|
+
# @return [Hash<String => String>]
|
20
|
+
# @!attribute [rw] node_meta
|
21
|
+
# @return [Hash<String => String>]
|
22
|
+
# @!attribute [rw] service_id
|
23
|
+
# @return [String]
|
24
|
+
# @!attribute [rw] service_name
|
25
|
+
# @return [String]
|
26
|
+
# @!attribute [rw] service_address
|
27
|
+
# @return [String]
|
28
|
+
# @!attribute [rw] service_tags
|
29
|
+
# @return [Array<String>]
|
30
|
+
# @!attribute [rw] service_port
|
31
|
+
# @return [String]
|
32
|
+
# @!attribute [rw] service_enable_tag_override
|
33
|
+
# @return [Boolean]
|
34
|
+
# @!attribute [rw] create_index
|
35
|
+
# @return [Integer]
|
36
|
+
# @!attribute [rw] modify_index
|
37
|
+
# @return [Integer]
|
38
|
+
class Service < APIObject
|
39
|
+
self.attribute_map = {
|
40
|
+
'ID' => :id,
|
41
|
+
'Node' => :node,
|
42
|
+
'Address' => :address,
|
43
|
+
'Datacenter' => :datacenter,
|
44
|
+
'TaggedAddresses' => :tagged_addresses,
|
45
|
+
'NodeMeta' => :node_meta,
|
46
|
+
'ServiceID' => :service_id,
|
47
|
+
'ServiceName' => :service_name,
|
48
|
+
'ServiceAddress' => :service_address,
|
49
|
+
'ServiceTags' => :service_tags,
|
50
|
+
'ServicePort' => :service_port,
|
51
|
+
'ServiceEnableTagOverride' => :service_enable_tag_override,
|
52
|
+
'CreateIndex' => :create_index,
|
53
|
+
'ModifyIndex' => :modify_index,
|
54
|
+
}
|
55
|
+
|
56
|
+
def initialize(*args)
|
57
|
+
@tagged_addresses = {}
|
58
|
+
@node_meta = {}
|
59
|
+
@service_tags = []
|
60
|
+
super
|
61
|
+
end
|
62
|
+
|
63
|
+
def tagged_addresses=(val)
|
64
|
+
@tagged_addresses = (val.nil? ? {} : val)
|
65
|
+
end
|
66
|
+
|
67
|
+
def node_meta=(val)
|
68
|
+
@node_meta = (val.nil? ? {} : val)
|
69
|
+
end
|
70
|
+
|
71
|
+
def service_tags=(val)
|
72
|
+
@service_tags = (val.nil? ? [] : val)
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
data/lib/imperium/http_client.rb
CHANGED
@@ -31,7 +31,11 @@ module Imperium
|
|
31
31
|
wrapping_exceptions do
|
32
32
|
url = config.url.join(path)
|
33
33
|
url.query_values = query
|
34
|
-
|
34
|
+
if value.is_a?(String)
|
35
|
+
@driver.put(url, body: value)
|
36
|
+
else
|
37
|
+
@driver.put(url, body: JSON.generate(value))
|
38
|
+
end
|
35
39
|
end
|
36
40
|
end
|
37
41
|
|
data/lib/imperium/kv_pair.rb
CHANGED
@@ -1,3 +1,4 @@
|
|
1
|
+
require_relative 'api_object'
|
1
2
|
require 'base64'
|
2
3
|
|
3
4
|
module Imperium
|
@@ -24,8 +25,8 @@ module Imperium
|
|
24
25
|
# @!attribute [rw] modify_index
|
25
26
|
# @return [Integer] The internal index value representing when the entry
|
26
27
|
# was last updated.
|
27
|
-
class KVPair
|
28
|
-
|
28
|
+
class KVPair < APIObject
|
29
|
+
self.attribute_map = {
|
29
30
|
'LockIndex' => :lock_index,
|
30
31
|
'Session' => :session,
|
31
32
|
'Key' => :key,
|
@@ -34,27 +35,6 @@ module Imperium
|
|
34
35
|
'CreateIndex' => :create_index,
|
35
36
|
'ModifyIndex' => :modify_index,
|
36
37
|
}.freeze
|
37
|
-
private_constant :ATTRIBUTE_MAP
|
38
|
-
|
39
|
-
ATTRIBUTE_NAMES = ATTRIBUTE_MAP.values
|
40
|
-
private_constant :ATTRIBUTE_NAMES
|
41
|
-
|
42
|
-
attr_accessor *ATTRIBUTE_NAMES
|
43
|
-
|
44
|
-
# Initialize a {KVPair}
|
45
|
-
#
|
46
|
-
# @param attributes [Hash] The attributes for this object as parsed from the
|
47
|
-
# API response.
|
48
|
-
def initialize(attributes = {})
|
49
|
-
ATTRIBUTE_MAP.each do |key, attribute_name|
|
50
|
-
send("#{attribute_name}=", attributes[key]) if attributes[key]
|
51
|
-
end
|
52
|
-
end
|
53
|
-
|
54
|
-
def ==(other)
|
55
|
-
return false unless self.class === other
|
56
|
-
ATTRIBUTE_NAMES.all? { |attr| self.send(attr) == other.send(attr )}
|
57
|
-
end
|
58
38
|
|
59
39
|
# Capture and base64 decode a value from the api.
|
60
40
|
#
|
data/lib/imperium/response.rb
CHANGED
@@ -8,6 +8,26 @@ module Imperium
|
|
8
8
|
# It exposes, through a convenient API, headers common to all interactions
|
9
9
|
# with the Consul HTTP API
|
10
10
|
class Response < SimpleDelegator
|
11
|
+
include Enumerable
|
12
|
+
|
13
|
+
class << self
|
14
|
+
attr_accessor :default_response_object_class
|
15
|
+
end
|
16
|
+
|
17
|
+
# Construct a new response
|
18
|
+
#
|
19
|
+
# @param response [HTTP::Message] The response as returned from the http client
|
20
|
+
# @param response_object_class [APIObject] The class to coerce values into,
|
21
|
+
# if left the default (:none) no coersion will be attempted.
|
22
|
+
def initialize(response, response_object_class: :none)
|
23
|
+
super(response)
|
24
|
+
@klass = if response_object_class == :none
|
25
|
+
self.class.default_response_object_class
|
26
|
+
else
|
27
|
+
response_object_class
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
11
31
|
# Indicates if the contacted server has a known leader.
|
12
32
|
#
|
13
33
|
# @return [TrueClass] When the response indicates there is a known leader
|
@@ -41,6 +61,25 @@ module Imperium
|
|
41
61
|
headers.key?('X-Consul-Translate-Addresses')
|
42
62
|
end
|
43
63
|
|
64
|
+
# Iterate over the values contained in the structure returned from {#coerced_body}
|
65
|
+
def each(&block)
|
66
|
+
coerced_body.each(&block)
|
67
|
+
end
|
68
|
+
|
69
|
+
# Parse the response JSON and initialize objects using the class passed to the constructor.
|
70
|
+
#
|
71
|
+
# @return [Array<Hash, APIObject>, Hash<String => APIObject>]
|
72
|
+
def coerced_body
|
73
|
+
return parsed_body if @klass == :none || @klass.nil?
|
74
|
+
@coerced_body ||= if parsed_body.is_a?(Array)
|
75
|
+
parsed_body.map { |attrs| @klass.new(attrs) }
|
76
|
+
else
|
77
|
+
parsed_body.each_with_object({}) { |(k, attrs), h|
|
78
|
+
h[k] = @klass.new(attrs)
|
79
|
+
}
|
80
|
+
end
|
81
|
+
end
|
82
|
+
|
44
83
|
private
|
45
84
|
|
46
85
|
def parsed_body
|
@@ -0,0 +1,87 @@
|
|
1
|
+
module Imperium
|
2
|
+
# Service is a container for data being received from and sent to the agent
|
3
|
+
# services APIs.
|
4
|
+
#
|
5
|
+
# @see https://www.consul.io/api/agent/service.html Agent Services API documentation
|
6
|
+
#
|
7
|
+
# @!attribute [rw] id
|
8
|
+
# @return [String] The service's id, when creating a new service this will
|
9
|
+
# be automatically assigned if not supplied, must be unique.
|
10
|
+
# @!attribute [rw] name
|
11
|
+
# @return [String] The service's name in the consul UI, required for
|
12
|
+
# creation, not required to be unique.
|
13
|
+
# @!attribute [rw] tags
|
14
|
+
# @return [Arary<String>] List of tags to be used for the service, can be
|
15
|
+
# used after creation for filtering in the API.
|
16
|
+
# @!attribute [rw] address
|
17
|
+
# @return [String] The network address to find the service at for DNS
|
18
|
+
# requests, defaults to the running agent's IP if left blank.
|
19
|
+
# @!attribute [rw] port
|
20
|
+
# @return [Integer] The port the service is bound to for network services.
|
21
|
+
# @!attribute [rw] checks
|
22
|
+
# @return [Array<ServiceCheck>] Specifies a list of checks to use for monitoring
|
23
|
+
# the service's health.
|
24
|
+
# @!attribute [rw] enable_tag_override
|
25
|
+
# @return [Boolean] Specifies to disable the anti-entropy feature for this
|
26
|
+
# service's tags. If EnableTagOverride is set to true then external agents
|
27
|
+
# can update this service in the catalog and modify the tags.
|
28
|
+
# @!attribute [r] create_index
|
29
|
+
# @return [Integer]
|
30
|
+
# @!attribute [r] modify_index
|
31
|
+
# @return [Integer]
|
32
|
+
class Service < APIObject
|
33
|
+
self.attribute_map = {
|
34
|
+
'ID' => :id,
|
35
|
+
'Name' => :name,
|
36
|
+
'Tags' => :tags,
|
37
|
+
'Address' => :address,
|
38
|
+
'Port' => :port,
|
39
|
+
'Check' => :check,
|
40
|
+
'Checks' => :checks,
|
41
|
+
'EnableTagOverride' => :enable_tag_override,
|
42
|
+
'CreateIndex' => :create_index,
|
43
|
+
'ModifyIndex' => :modify_index
|
44
|
+
}
|
45
|
+
|
46
|
+
def initialize(*args)
|
47
|
+
# So we can << onto these w/o having to nil check everywhere first
|
48
|
+
@tags ||= []
|
49
|
+
@checks ||= []
|
50
|
+
super
|
51
|
+
end
|
52
|
+
|
53
|
+
def add_check(val)
|
54
|
+
@checks << maybe_convert_service_check(val) unless val.nil?
|
55
|
+
end
|
56
|
+
alias check= add_check
|
57
|
+
|
58
|
+
|
59
|
+
def checks=(val)
|
60
|
+
@checks = (val || []).map { |obj| maybe_convert_service_check(obj) }
|
61
|
+
end
|
62
|
+
|
63
|
+
def tags=(val)
|
64
|
+
@tags = (val.nil? ? [] : val)
|
65
|
+
end
|
66
|
+
|
67
|
+
# Generate a hash containing the data necessary for registering this service.
|
68
|
+
#
|
69
|
+
# If both Check and Checks are present in the object they're coalesced into
|
70
|
+
# a single Checks key.
|
71
|
+
#
|
72
|
+
# @return [Hash<String => String,Integer,Hash<String => String>,Array<Hash<String => String>>]
|
73
|
+
def registration_data
|
74
|
+
to_h.tap do |h|
|
75
|
+
h.delete('CreateIndex')
|
76
|
+
h.delete('ModifyIndex')
|
77
|
+
h.delete('Checks') if checks.empty?
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
private
|
82
|
+
|
83
|
+
def maybe_convert_service_check(attrs_or_check)
|
84
|
+
attrs_or_check.is_a?(Hash) ? ServiceCheck.new(attrs_or_check) : attrs_or_check
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
@@ -0,0 +1,100 @@
|
|
1
|
+
require_relative 'api_object'
|
2
|
+
module Imperium
|
3
|
+
# ServiceCheck is a container for data being received from and sent to the
|
4
|
+
# agent services and checks apis.
|
5
|
+
#
|
6
|
+
# @see https://www.consul.io/api/agent/check.html Agent Checks API documentation
|
7
|
+
#
|
8
|
+
# @!attribute [rw] id
|
9
|
+
# @return [String] The service's id, when creating a new check this will
|
10
|
+
# be automatically assigned if not supplied, must be unique.
|
11
|
+
# @!attribute [rw] name
|
12
|
+
# @return [String] The check's name in the consul UI, required for
|
13
|
+
# creation, not required to be unique.
|
14
|
+
# @!attribute [rw] script
|
15
|
+
# @return [String] Specifies a script or path to a script to run on Interval
|
16
|
+
# to update the status of the check. If specifying a path, this path must
|
17
|
+
# exist on disk and be readable by the Consul agent.
|
18
|
+
# @!attribute [rw] docker_container_id
|
19
|
+
# @return [String] Specifies that the check is a Docker check, and Consul
|
20
|
+
# will evaluate the script every Interval in the given container using the
|
21
|
+
# specified Shell. Note that Shell is currently only supported for Docker checks.
|
22
|
+
# @!attribute [rw] shell
|
23
|
+
# @return [String] The shell to use for docker checks, only applies when
|
24
|
+
# docker_container_id is specified
|
25
|
+
# @!attribute [rw] interval
|
26
|
+
# @return [String] Specifies the frequency at which to run this check. This
|
27
|
+
# is required for HTTP and TCP checks.
|
28
|
+
# @!attribute [rw] timeout
|
29
|
+
# @return [String]
|
30
|
+
# @!attribute [rw] ttl
|
31
|
+
# @return [String] Specifies this is a TTL check, and the TTL endpoint must
|
32
|
+
# be used periodically to update the state of the check.
|
33
|
+
# @!attribute [rw] http
|
34
|
+
# @return [String] Specifies an HTTP check to perform a GET request against
|
35
|
+
# the value of HTTP (expected to be a URL) every Interval. If the response
|
36
|
+
# is any 2xx code, the check is passing. If the response is 429 Too Many
|
37
|
+
# Requests, the check is warning. Otherwise, the check is critical. HTTP
|
38
|
+
# checks also support SSL. By default, a valid SSL certificate is
|
39
|
+
# expected. Certificate verification can be controlled using the
|
40
|
+
# TLSSkipVerify.
|
41
|
+
# @!attribute [rw] headers
|
42
|
+
# @return [Hash<String => String>] Specifies a set of headers that should be
|
43
|
+
# set for HTTP checks. Each header can have multiple values.
|
44
|
+
# @!attribute [rw] method
|
45
|
+
# @return [String] Specifies a different HTTP method to be used for an HTTP
|
46
|
+
# check. When no value is specified, GET is used.
|
47
|
+
# @!attribute [rw] tcp
|
48
|
+
# @return [String] Specifies a TCP to connect against the value of TCP
|
49
|
+
# (expected to be an IP or hostname plus port combination) every Interval.
|
50
|
+
# If the connection attempt is successful, the check is passing. If the
|
51
|
+
# connection attempt is unsuccessful, the check is critical. In the case
|
52
|
+
# of a hostname that resolves to both IPv4 and IPv6 addresses, an attempt
|
53
|
+
# will be made to both addresses, and the first successful connection
|
54
|
+
# attempt will result in a successful check.
|
55
|
+
# @!attribute [rw] status
|
56
|
+
# @return [String] Specifies the initial status of the health check.
|
57
|
+
# @!attribute [rw] notes
|
58
|
+
# @return [String] Specifies arbitrary information for humans. This is not
|
59
|
+
# used by Consul internally.
|
60
|
+
# @!attribute [rw] tls_skip_verify
|
61
|
+
# @return [String] Specifies if the certificate for an HTTPS check should
|
62
|
+
# not be verified.
|
63
|
+
# @!attribute [rw] deregister_critical_service_after
|
64
|
+
# @return [String] Specifies that checks associated with a service should
|
65
|
+
# deregister after this time. This is specified as a time duration with
|
66
|
+
# suffix like "10m". If a check is in the critical state for more than
|
67
|
+
# this configured value, then its associated service (and all of its
|
68
|
+
# associated checks) will automatically be deregistered. The minimum
|
69
|
+
# timeout is 1 minute, and the process that reaps critical services runs
|
70
|
+
# every 30 seconds, so it may take slightly longer than the configured
|
71
|
+
# timeout to trigger the deregistration. This should generally be
|
72
|
+
# configured with a timeout that's much, much longer than any expected
|
73
|
+
# recoverable outage for the given service.
|
74
|
+
# @!attribute [rw] service_id
|
75
|
+
# @return [String] Specifies the ID of a service to associate the
|
76
|
+
# registered check with an existing service provided by the agent. Does
|
77
|
+
# not need to be set when registering the check at the same time as
|
78
|
+
# registering a service
|
79
|
+
class ServiceCheck < APIObject
|
80
|
+
self.attribute_map = {
|
81
|
+
'ID' => :id,
|
82
|
+
'Name' => :name,
|
83
|
+
'Script' => :script,
|
84
|
+
'DockerContainerID' => :docker_container_id,
|
85
|
+
'Shell' => :shell,
|
86
|
+
'Interval' => :interval,
|
87
|
+
'Timeout' => :timeout,
|
88
|
+
'TTL' => :ttl,
|
89
|
+
'HTTP' => :http,
|
90
|
+
'Header' => :headers,
|
91
|
+
'Method' => :method,
|
92
|
+
'TCP' => :tcp,
|
93
|
+
'Status' => :status,
|
94
|
+
'Notes' => :notes,
|
95
|
+
'TLSSkipVerify' => :tls_skip_verify,
|
96
|
+
'DeregisterCriticalServiceAfter' => :deregister_critical_service_after,
|
97
|
+
'ServiceID' => :service_id,
|
98
|
+
}
|
99
|
+
end
|
100
|
+
end
|
data/lib/imperium/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: imperium
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tyler Pickett
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-
|
11
|
+
date: 2017-10-12 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: addressable
|
@@ -157,6 +157,12 @@ files:
|
|
157
157
|
- docker-compose.yml
|
158
158
|
- imperium.gemspec
|
159
159
|
- lib/imperium.rb
|
160
|
+
- lib/imperium/agent.rb
|
161
|
+
- lib/imperium/agent_list_checks_response.rb
|
162
|
+
- lib/imperium/agent_list_services_response.rb
|
163
|
+
- lib/imperium/api_object.rb
|
164
|
+
- lib/imperium/catalog.rb
|
165
|
+
- lib/imperium/catalog/service.rb
|
160
166
|
- lib/imperium/client.rb
|
161
167
|
- lib/imperium/configuration.rb
|
162
168
|
- lib/imperium/error.rb
|
@@ -167,7 +173,10 @@ files:
|
|
167
173
|
- lib/imperium/kv_get_response.rb
|
168
174
|
- lib/imperium/kv_pair.rb
|
169
175
|
- lib/imperium/kv_put_response.rb
|
176
|
+
- lib/imperium/refinements/hash_compact.rb
|
170
177
|
- lib/imperium/response.rb
|
178
|
+
- lib/imperium/service.rb
|
179
|
+
- lib/imperium/service_check.rb
|
171
180
|
- lib/imperium/testing.rb
|
172
181
|
- lib/imperium/version.rb
|
173
182
|
homepage: https://github.com/instructure/imperium
|