dendrite 0.0.1 → 0.2.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.
- checksums.yaml +4 -4
- data/conf/config.yaml +2 -1
- data/conf/services/service.yml +27 -13
- data/lib/dendrite/generators/base.rb +1 -0
- data/lib/dendrite/generators/nerve.rb +3 -2
- data/lib/dendrite/generators/synapse.rb +8 -7
- data/lib/dendrite/io.rb +7 -4
- data/lib/dendrite/service_graph.rb +6 -9
- data/lib/dendrite/service_node.rb +62 -11
- data/lib/dendrite/version.rb +1 -1
- data/lib/dendrite.rb +3 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e10396502c8af59086c5bf3f6d3b414679830200
|
4
|
+
data.tar.gz: f11e24cc3410edc382a309d4d66c5a2e4a902865
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c20ba4b8a03ebf55457f9b650ea360687a8c679458b3a5aa1b27bec0e3574d5c67523c199966abe28eb8a2e2c79bcddc0bb8ebb6e4a6f288c3a30ce56ba69461
|
7
|
+
data.tar.gz: f30b865221e2e1f79c97362675df5c7fc1cc67e06f745a78651955415b94638670b64bcfced495eb78a6b429bf42fa5615fbfa1687241c20b3192837868c33a4
|
data/conf/config.yaml
CHANGED
@@ -1,11 +1,12 @@
|
|
1
1
|
dendrite:
|
2
|
+
organization: sd
|
2
3
|
dc: ggn1
|
3
4
|
env: dev
|
4
5
|
zk_hosts:
|
5
6
|
- localhost:2181
|
6
7
|
nerve_config_path: /opt/smartstack/conf/nerve.yml
|
7
8
|
synapse_config_path: /opt/smartstack/conf/synapse.yml
|
8
|
-
services_source:
|
9
|
+
services_source: /vagrant/services/services/
|
9
10
|
|
10
11
|
synapse:
|
11
12
|
haproxy:
|
data/conf/services/service.yml
CHANGED
@@ -1,34 +1,48 @@
|
|
1
|
+
dendrite_version: 1
|
2
|
+
organization: sd
|
1
3
|
namespace: cams
|
2
4
|
lead_email: vp@foobar.com
|
3
5
|
team_email: team@foobar.com
|
4
6
|
services:
|
5
7
|
- name: foobar
|
6
8
|
type: tomcat
|
7
|
-
|
8
|
-
|
9
|
+
deploy:
|
10
|
+
repository: git@github.com:yagnik/dendrite
|
11
|
+
package: dendrite
|
12
|
+
scale:
|
13
|
+
min_instance_count: 1
|
14
|
+
max_instance_count: 5
|
9
15
|
ports:
|
10
16
|
advertised_port: 8081
|
11
|
-
|
17
|
+
listening_port: 8080
|
12
18
|
dependancies:
|
13
|
-
-
|
19
|
+
- namespace: cams
|
20
|
+
name: cat
|
14
21
|
latency: foo
|
15
22
|
- name: cat
|
16
23
|
type: tomcat
|
17
|
-
|
18
|
-
|
19
|
-
|
24
|
+
deploy:
|
25
|
+
repository: git@github.com:yagnik/dendrite
|
26
|
+
package: dendrite
|
27
|
+
scale:
|
28
|
+
min_instance_count: 1
|
29
|
+
max_instance_count: 5
|
20
30
|
ports:
|
21
31
|
advertised_port: 8081
|
22
|
-
|
32
|
+
listening_port: 8080
|
23
33
|
dependancies:
|
24
|
-
-
|
34
|
+
- namespace: cams
|
35
|
+
name: foobar
|
25
36
|
latency: foo
|
26
37
|
- name: baz
|
27
38
|
type: tomcat
|
28
|
-
|
29
|
-
|
30
|
-
|
39
|
+
deploy:
|
40
|
+
repository: git@github.com:yagnik/dendrite
|
41
|
+
package: dendrite
|
42
|
+
scale:
|
43
|
+
min_instance_count: 1
|
44
|
+
max_instance_count: 5
|
31
45
|
ports:
|
32
46
|
advertised_port: 8081
|
33
|
-
|
47
|
+
listening_port: 8080
|
34
48
|
dependancies: []
|
@@ -4,7 +4,7 @@ module Dendrite
|
|
4
4
|
|
5
5
|
def initialize(graph:, service_names:)
|
6
6
|
super
|
7
|
-
@services = @services.collect { |
|
7
|
+
@services = @services.collect { |service| ServiceConfig.new(service)}
|
8
8
|
end
|
9
9
|
|
10
10
|
def to_h
|
@@ -22,6 +22,7 @@ module Dendrite
|
|
22
22
|
extend Forwardable
|
23
23
|
def_delegator :service, :name, :name
|
24
24
|
def_delegator :service, :namespace, :namespace
|
25
|
+
def_delegator :service, :organization, :organization
|
25
26
|
|
26
27
|
def to_h
|
27
28
|
{
|
@@ -38,7 +39,7 @@ module Dendrite
|
|
38
39
|
{
|
39
40
|
reporter_type: 'zookeeper',
|
40
41
|
zk_hosts: Dendrite::Config.zk_hosts,
|
41
|
-
zk_path: "/smartstack/services/#{
|
42
|
+
zk_path: "/smartstack/services/#{organization}/#{namespace}/#{service.real_name}/instances"
|
42
43
|
}
|
43
44
|
end
|
44
45
|
end
|
@@ -3,14 +3,14 @@ module Dendrite
|
|
3
3
|
class Synapse < Base
|
4
4
|
def initialize(graph:, service_names:)
|
5
5
|
super
|
6
|
-
dep =
|
7
|
-
@services.each do |
|
8
|
-
service.dependancies.each do |
|
9
|
-
dep
|
6
|
+
dep = []
|
7
|
+
@services.each do |service|
|
8
|
+
service.dependancies.each do |_, dependancy|
|
9
|
+
dep << dependancy.service
|
10
10
|
end
|
11
11
|
end
|
12
|
-
@services = dep
|
13
|
-
@services = @services.collect { |
|
12
|
+
@services = dep.uniq
|
13
|
+
@services = @services.collect { |service| ServiceConfig.new(service)}
|
14
14
|
end
|
15
15
|
|
16
16
|
def to_h
|
@@ -33,6 +33,7 @@ module Dendrite
|
|
33
33
|
extend Forwardable
|
34
34
|
def_delegator :service, :name, :name
|
35
35
|
def_delegator :service, :namespace, :namespace
|
36
|
+
def_delegator :service, :organization, :organization
|
36
37
|
|
37
38
|
def to_h
|
38
39
|
discovery_config.merge(haproxy_config)
|
@@ -43,7 +44,7 @@ module Dendrite
|
|
43
44
|
discovery: {
|
44
45
|
method: 'zookeeper',
|
45
46
|
hosts: Dendrite::Config.zk_hosts,
|
46
|
-
path: "/smartstack/services/#{namespace}/#{
|
47
|
+
path: "/smartstack/services/#{organization}/#{namespace}/#{service.real_name}/instances"
|
47
48
|
}
|
48
49
|
}
|
49
50
|
end
|
data/lib/dendrite/io.rb
CHANGED
@@ -12,8 +12,10 @@ module Dendrite
|
|
12
12
|
end
|
13
13
|
|
14
14
|
services.each do |service|
|
15
|
+
node = ServiceNode.new(service)
|
15
16
|
service[:dependancies].each do |deps|
|
16
|
-
|
17
|
+
dependancy_name = "#{service[:organization]}_#{deps[:namespace]}_#{deps[:name]}"
|
18
|
+
graph[node.name].add_dependancy(service: graph[dependancy_name], latency: deps[:latency])
|
17
19
|
end
|
18
20
|
end
|
19
21
|
|
@@ -34,9 +36,10 @@ module Dendrite
|
|
34
36
|
def services_from_file(source:)
|
35
37
|
data = read(source: source)
|
36
38
|
data[:services].collect do |service|
|
37
|
-
service[:
|
38
|
-
service[:
|
39
|
-
service[:
|
39
|
+
service[:organization] = data[:organization]
|
40
|
+
service[:namespace] = data[:namespace]
|
41
|
+
service[:lead_email] = data[:lead_email]
|
42
|
+
service[:team_email] = data[:team_email]
|
40
43
|
service
|
41
44
|
end
|
42
45
|
end
|
@@ -11,24 +11,21 @@ module Dendrite
|
|
11
11
|
|
12
12
|
def <<(service)
|
13
13
|
raise KeyError unless service.name
|
14
|
-
|
14
|
+
raise DuplicateService if services.keys.include?(service.name)
|
15
|
+
services[service.name] = service
|
15
16
|
end
|
16
17
|
|
17
18
|
def [](name)
|
18
|
-
|
19
|
-
end
|
20
|
-
|
21
|
-
def fetch(name)
|
22
|
-
@services.fetch(name)
|
19
|
+
services.fetch(name)
|
23
20
|
end
|
24
21
|
|
25
22
|
def valid?
|
26
|
-
|
23
|
+
services.values.collect(&:valid?).all?
|
27
24
|
end
|
28
25
|
|
29
26
|
def errors
|
30
|
-
|
31
|
-
hash[name] = service.errors.messages
|
27
|
+
services.inject({}) do |hash, (name, service)|
|
28
|
+
hash[name] = service.errors.messages if service.errors.messages.length > 0
|
32
29
|
hash
|
33
30
|
end
|
34
31
|
end
|
@@ -3,7 +3,7 @@ module Dendrite
|
|
3
3
|
def valid?
|
4
4
|
super
|
5
5
|
|
6
|
-
|
6
|
+
dependancies.each do |depname, dep|
|
7
7
|
if dep.invalid?
|
8
8
|
dep.errors.each do |key, value|
|
9
9
|
errors.add "dependancy_#{key}", value
|
@@ -11,7 +11,7 @@ module Dendrite
|
|
11
11
|
end
|
12
12
|
end
|
13
13
|
|
14
|
-
|
14
|
+
ports.each do |depname, dep|
|
15
15
|
if dep.invalid?
|
16
16
|
dep.errors.each do |key, value|
|
17
17
|
errors.add "port_#{key}", value
|
@@ -19,6 +19,18 @@ module Dendrite
|
|
19
19
|
end
|
20
20
|
end
|
21
21
|
|
22
|
+
if deploy && deploy.invalid?
|
23
|
+
deploy.errors.each do |key, value|
|
24
|
+
errors.add "deploy_#{key}", value
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
if scale && scale.invalid?
|
29
|
+
scale.errors.each do |key, value|
|
30
|
+
errors.add "scale_#{key}", value
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
22
34
|
return errors.count == 0
|
23
35
|
end
|
24
36
|
end
|
@@ -38,6 +50,27 @@ module Dendrite
|
|
38
50
|
include ActiveModel::Validations
|
39
51
|
validates_presence_of :service
|
40
52
|
validates_presence_of :latency
|
53
|
+
validate :service_type
|
54
|
+
|
55
|
+
def service_type
|
56
|
+
unless service.is_a?(ServiceNode)
|
57
|
+
errors.add(:service, "service has to be a Service Node")
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
Scale = Struct.new(:max_instance_count, :min_instance_count) do
|
63
|
+
include ActiveModel::Validations
|
64
|
+
validates_presence_of :max_instance_count
|
65
|
+
validates_presence_of :min_instance_count
|
66
|
+
validates :max_instance_count, numericality: { only_integer: true }
|
67
|
+
validates :min_instance_count, numericality: { only_integer: true }
|
68
|
+
end
|
69
|
+
|
70
|
+
Deploy = Struct.new(:repository, :package) do
|
71
|
+
include ActiveModel::Validations
|
72
|
+
validates_presence_of :repository
|
73
|
+
validates_presence_of :package
|
41
74
|
end
|
42
75
|
|
43
76
|
VALID_TYPE = %w(
|
@@ -48,24 +81,34 @@ module Dendrite
|
|
48
81
|
cassandra
|
49
82
|
)
|
50
83
|
|
51
|
-
|
52
|
-
:name, :type, :repo, :package_name,
|
53
|
-
:ports, :dependancies
|
84
|
+
VALID_EMAIL_REGEX = /\A[\w+\-.]+@[a-z\d\-]+(\.[a-z]+)*\.[a-z]+\z/i
|
54
85
|
|
55
|
-
|
56
|
-
|
86
|
+
attr_reader :organization, :namespace, :lead_email, :team_email,
|
87
|
+
:type, :deploy, :scale, :ports, :dependancies
|
88
|
+
# :name is set but magically
|
57
89
|
|
58
|
-
|
90
|
+
validates_presence_of :organization, :namespace, :lead_email, :team_email,
|
91
|
+
:name, :type, :deploy, :scale
|
92
|
+
|
93
|
+
validates :organization, format: { with: /\A[a-z]+\z/, message: "only allows lowercase letters" }
|
94
|
+
validates :namespace, format: { with: /\A[a-z]+\z/, message: "only allows lowercase letters" }
|
95
|
+
validates :lead_email, format: { with: VALID_EMAIL_REGEX, message: "invalid email format" }
|
96
|
+
validates :team_email, format: { with: VALID_EMAIL_REGEX, message: "invalid email format" }
|
59
97
|
validates :name, format: { with: /\A[a-z_]+\z/, message: "only allows lowercase letters" }
|
60
98
|
validates :type, inclusion: { in: VALID_TYPE, message: "%{value} is not a valid type" }
|
61
99
|
|
62
100
|
def initialize(**args)
|
63
101
|
@ports = {}
|
64
102
|
args.each do |k,v|
|
65
|
-
|
103
|
+
case k
|
104
|
+
when :ports
|
66
105
|
v.each do |name, port|
|
67
106
|
@ports[name] = Port.new(name, port)
|
68
107
|
end
|
108
|
+
when :deploy
|
109
|
+
@deploy = Deploy.new(v[:repository], v[:package]) if v != nil
|
110
|
+
when :scale
|
111
|
+
@scale = Scale.new(v[:max_instance_count], v[:min_instance_count]) if v != nil
|
69
112
|
else
|
70
113
|
instance_variable_set("@#{k}", v)
|
71
114
|
end
|
@@ -73,12 +116,20 @@ module Dendrite
|
|
73
116
|
@dependancies = {}
|
74
117
|
end
|
75
118
|
|
119
|
+
def real_name
|
120
|
+
@name
|
121
|
+
end
|
122
|
+
|
123
|
+
def name
|
124
|
+
"#{organization}_#{namespace}_#{@name}" if @name
|
125
|
+
end
|
126
|
+
|
76
127
|
def listening_port
|
77
|
-
ports[:
|
128
|
+
ports[:listening_port].port if ports[:listening_port]
|
78
129
|
end
|
79
130
|
|
80
131
|
def advertised_port
|
81
|
-
ports[:advertised_port].port
|
132
|
+
ports[:advertised_port].port if ports[:advertised_port]
|
82
133
|
end
|
83
134
|
|
84
135
|
def add_dependancy(service:, latency:)
|
data/lib/dendrite/version.rb
CHANGED
data/lib/dendrite.rb
CHANGED
@@ -14,6 +14,7 @@ module Dendrite
|
|
14
14
|
Error = Class.new(StandardError)
|
15
15
|
InvalidData = Class.new(Error)
|
16
16
|
UnknownService = Class.new(Error)
|
17
|
+
DuplicateService = Class.new(Error)
|
17
18
|
|
18
19
|
class Config
|
19
20
|
class << self
|
@@ -50,7 +51,8 @@ module Dendrite
|
|
50
51
|
end
|
51
52
|
|
52
53
|
def public_ip
|
53
|
-
ip = Socket.ip_address_list.detect{|intf| intf.ipv4_private?}
|
54
|
+
ip = Socket.ip_address_list.detect{|intf| intf.ipv4_private?} ||
|
55
|
+
Socket.ip_address_list.detect{|intf| intf.ipv4? && !intf.ipv4_loopback? && !intf.ipv4_multicast? && !intf.ipv4_private?}
|
54
56
|
ip.ip_address if ip
|
55
57
|
end
|
56
58
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: dendrite
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Yagnik
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-05-
|
11
|
+
date: 2016-05-04 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|