the-maestro 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.
- data/.document +5 -0
- data/.gitignore +25 -0
- data/LICENSE +23 -0
- data/README.rdoc +378 -0
- data/Rakefile +116 -0
- data/VERSION +1 -0
- data/lib/maestro.rb +354 -0
- data/lib/maestro/cloud.rb +384 -0
- data/lib/maestro/cloud/aws.rb +1231 -0
- data/lib/maestro/dsl_property.rb +15 -0
- data/lib/maestro/log4r/console_formatter.rb +18 -0
- data/lib/maestro/log4r/file_formatter.rb +24 -0
- data/lib/maestro/node.rb +123 -0
- data/lib/maestro/operating_system.rb +53 -0
- data/lib/maestro/operating_system/cent_os.rb +23 -0
- data/lib/maestro/operating_system/debian.rb +40 -0
- data/lib/maestro/operating_system/fedora.rb +23 -0
- data/lib/maestro/operating_system/ubuntu.rb +100 -0
- data/lib/maestro/role.rb +36 -0
- data/lib/maestro/tasks.rb +52 -0
- data/lib/maestro/validator.rb +32 -0
- data/rails/init.rb +1 -0
- data/test/integration/base_aws.rb +156 -0
- data/test/integration/fixtures/config/maestro/cookbooks/emacs/metadata.json +41 -0
- data/test/integration/fixtures/config/maestro/cookbooks/emacs/metadata.rb +3 -0
- data/test/integration/fixtures/config/maestro/cookbooks/emacs/recipes/default.rb +21 -0
- data/test/integration/fixtures/config/maestro/roles/default.json +9 -0
- data/test/integration/fixtures/config/maestro/roles/web.json +9 -0
- data/test/integration/helper.rb +8 -0
- data/test/integration/test_aws_cloud.rb +805 -0
- data/test/integration/test_cent_os.rb +104 -0
- data/test/integration/test_debian.rb +119 -0
- data/test/integration/test_fedora.rb +104 -0
- data/test/integration/test_ubuntu.rb +149 -0
- data/test/unit/fixtures/invalid-clouds-not-a-directory/config/maestro/clouds +1 -0
- data/test/unit/fixtures/invalid-cookbooks-not-a-directory/config/maestro/cookbooks +0 -0
- data/test/unit/fixtures/invalid-maestro-not-a-directory/config/maestro +0 -0
- data/test/unit/fixtures/invalid-missing-cookbooks/config/maestro/clouds/valid.yml +21 -0
- data/test/unit/fixtures/invalid-missing-roles/config/maestro/clouds/valid.yml +21 -0
- data/test/unit/fixtures/invalid-roles-not-a-directory/config/maestro/roles +1 -0
- data/test/unit/fixtures/ssh/id_rsa-maestro-test-keypair +27 -0
- data/test/unit/helper.rb +6 -0
- data/test/unit/test_aws_cloud.rb +133 -0
- data/test/unit/test_aws_ec2_node.rb +76 -0
- data/test/unit/test_aws_elb_node.rb +221 -0
- data/test/unit/test_aws_rds_node.rb +380 -0
- data/test/unit/test_cent_os.rb +28 -0
- data/test/unit/test_cloud.rb +142 -0
- data/test/unit/test_debian.rb +62 -0
- data/test/unit/test_fedora.rb +28 -0
- data/test/unit/test_invalid_mode.rb +11 -0
- data/test/unit/test_maestro.rb +140 -0
- data/test/unit/test_node.rb +50 -0
- data/test/unit/test_operating_system.rb +19 -0
- data/test/unit/test_rails_mode.rb +77 -0
- data/test/unit/test_role.rb +59 -0
- data/test/unit/test_standalone_mode.rb +75 -0
- data/test/unit/test_ubuntu.rb +95 -0
- data/the-maestro.gemspec +150 -0
- metadata +228 -0
@@ -0,0 +1 @@
|
|
1
|
+
hi
|
File without changes
|
File without changes
|
@@ -0,0 +1,21 @@
|
|
1
|
+
provider: ec2
|
2
|
+
provider_config:
|
3
|
+
aws_account_id: XXXX-XXXX-XXXX
|
4
|
+
aws_access_key: XXXXXXXXXXXXXXXXXXXX
|
5
|
+
aws_secret_access_key: XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
|
6
|
+
keypair_name: maestro-test-keypair
|
7
|
+
keypair_file: /home/foo/id_rsa-maestro-test-keypair
|
8
|
+
|
9
|
+
roles:
|
10
|
+
web:
|
11
|
+
public_ports: [80, 443]
|
12
|
+
db-master: {}
|
13
|
+
|
14
|
+
nodes:
|
15
|
+
test-1.maestro-rails-test.node:
|
16
|
+
# Node -> Role mapping
|
17
|
+
roles: [web, db-master]
|
18
|
+
provider_config:
|
19
|
+
ami: ami-XXXXXXXX
|
20
|
+
instance_type: m1.small
|
21
|
+
availability_zone: us-east-1b
|
@@ -0,0 +1,21 @@
|
|
1
|
+
provider: ec2
|
2
|
+
provider_config:
|
3
|
+
aws_account_id: XXXX-XXXX-XXXX
|
4
|
+
aws_access_key: XXXXXXXXXXXXXXXXXXXX
|
5
|
+
aws_secret_access_key: XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
|
6
|
+
keypair_name: maestro-test-keypair
|
7
|
+
keypair_file: /home/foo/id_rsa-maestro-test-keypair
|
8
|
+
|
9
|
+
roles:
|
10
|
+
web:
|
11
|
+
public_ports: [80, 443]
|
12
|
+
db-master: {}
|
13
|
+
|
14
|
+
nodes:
|
15
|
+
test-1.maestro-rails-test.node:
|
16
|
+
# Node -> Role mapping
|
17
|
+
roles: [web, db-master]
|
18
|
+
provider_config:
|
19
|
+
ami: ami-XXXXXXXX
|
20
|
+
instance_type: m1.small
|
21
|
+
availability_zone: us-east-1b
|
@@ -0,0 +1 @@
|
|
1
|
+
hi
|
@@ -0,0 +1,27 @@
|
|
1
|
+
-----BEGIN RSA PRIVATE KEY-----
|
2
|
+
MIIEowIBAAKCAQEApiOBafftYOaMlJkP+xrVf/0ULMCZ0VUk42EigDA6t8cloejW
|
3
|
+
HAR5NJ8k6wlOiszvoSpb2Pi+tLPfDOwHzJCl3DSvn1kVpmozC7CyZwz0+67JBRus
|
4
|
+
LgJMR2zzlBnFql55MV9a0XxYlOGNnvvYlSqrgwzSnMONU9X8br9AX7Ivjt5Dkk95
|
5
|
+
+bnShrSVop0vF0K1dWkWFFbmaKnYBkzKD2Rt6w1Wblm5geW74FLQYIxWzKiz0WZI
|
6
|
+
lX74A1BsYpvp6viVZXX3hw7LYuLTHYIyz/sKgupzItw+kaKJK8B1reP/RKuD1Alg
|
7
|
+
AWxuAEcH2zSDU+2FxDYfJKoMELN4BgVZF1gFBQIDAQABAoIBADcsK1oJn6dCaQUg
|
8
|
+
H5KAQs6SORTzkSFXaTypkU+ItLc7R2ARdqkvQyEaiKQVHyQxEpMvAfl4Abz4zuX3
|
9
|
+
rE9e6fXK+Vetuebd9b24HEbkoqbCULeFjRRqZvKBWBKizGXbodunkv1mkfQ/Q0y8
|
10
|
+
zhwbY4HNzFOLDW/97CrLEJG3FtwWorcugYr2acilVV6z4R5uxcuuDGSK1GM7dvwR
|
11
|
+
tMZ2tJCRwpNuw3fH7nW+zcjk/x8fhC69IvtjuCaQPdMhuUeuRAEi4lC/ryka9WQ+
|
12
|
+
kNuGlPrLPsDAQtfJHL40XEUH/MH4GvCg4v002OD8XaDpYxASWuHrHv3a1o5KFG8r
|
13
|
+
hHARtwECgYEA11+SKqE2PM2avHSS37sEee/FVWjW6wCn7vT3V63yqKrMLkhwkwHw
|
14
|
+
zDzBC+XYsbilRwKHQNIJ8vhXEWurqJie4c/ZmUa/rpT76PWOKubUFxc1oQf37mrj
|
15
|
+
jM+N6jmbK7f9+odmpJET1nyc8s3ROV4c4iom+ftHEkX8sS0vxeTxbrECgYEAxXph
|
16
|
+
7hNl1yJEvAIgtT5qIKyxcYBFHIFehrD3hlPydtOusx7KWG/rc+CUICL3reAJ+SHa
|
17
|
+
KfZ5iruMegZsXmHV0tUwTOTd9TnPaEKJfxByFYQTX5XAXxzdtA1UD/pr553vZVgq
|
18
|
+
Pb5DWQKXU1TqatTE44ot/9bi2nFzytTh9CwSGJUCgYAoTZIkuBZWOoOCUK5Lf8vO
|
19
|
+
pbffy8asI2tJpD3FAqAuQAgFgTjPycUt8xCNEW4Dk/IZ37c/wg5qkV55vBRbcHQK
|
20
|
+
/cJSlJK6MNcTOSBpltiJmaZHhB45V3dNmmmMM0t+WugEQeJLWXrE4HzeUvWcLqhp
|
21
|
+
CkpQ7VzXZpFq9nHCLp2fgQKBgBeh/MREGAT1+enSC14FWSgN4rJlml+977UIyqaN
|
22
|
+
t0+XJ6oR/j81LaVRdAighqmNTUQ+U+B/ua3rofUcfa2R4cf4cW5SWWm2gGbGx7Oo
|
23
|
+
IS8H/lWLE1mOl82rZqr+2hj+4p5rParj8SVe1QNI/0DHs8RTTgv3CHEB8MyOS3gw
|
24
|
+
Kf49AoGBALhv8PiSNyMtDj3BGtB6Mfs/8tg0Zbk+c4P0A52ppNA7414OqVx0A1ML
|
25
|
+
VIw2kOU19Yj6CmRyzBZLeTDaWArwEYyDEblWs9tklI7HNAR3KfW/ptp8XrYT+w98
|
26
|
+
N5BkWOgV7Zcr90vj9WbAMr4bQHi2SoXG2zSKagUuoQ6hblDdUZxT
|
27
|
+
-----END RSA PRIVATE KEY-----
|
data/test/unit/helper.rb
ADDED
@@ -0,0 +1,133 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
# Unit tests for Maestro::Cloud::Aws
|
4
|
+
class TestAwsCloud < Test::Unit::TestCase
|
5
|
+
|
6
|
+
context "Maestro::Cloud::Aws" do
|
7
|
+
setup do
|
8
|
+
@cloud = aws_cloud :test do
|
9
|
+
keypair_name "XXXXXXX-keypair"
|
10
|
+
keypair_file "/path/to/id_rsa-XXXXXXX-keypair"
|
11
|
+
aws_account_id "XXXX-XXXX-XXXX"
|
12
|
+
aws_access_key "XXXXXXXXXXXXXXXXXXXX"
|
13
|
+
aws_secret_access_key "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
|
14
|
+
chef_bucket "maestro.mydomain.com"
|
15
|
+
|
16
|
+
roles do
|
17
|
+
role "web" do
|
18
|
+
public_ports [80, 443]
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
nodes do
|
23
|
+
ec2_node "web-1" do
|
24
|
+
roles ["web"]
|
25
|
+
ami "ami-bb709dd2"
|
26
|
+
ssh_user "ubuntu"
|
27
|
+
instance_type "m1.small"
|
28
|
+
availability_zone "us-east-1b"
|
29
|
+
elastic_ip "111.111.11.111"
|
30
|
+
ebs_volume_id "vol-XXXXXXXX"
|
31
|
+
ebs_device "/dev/sdh"
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
should "be invalid due to duplicate ec2 nodes" do
|
38
|
+
cloud = aws_cloud :test do
|
39
|
+
keypair_name "XXXXXXX-keypair"
|
40
|
+
keypair_file "/path/to/id_rsa-XXXXXXX-keypair"
|
41
|
+
aws_account_id "XXXX-XXXX-XXXX"
|
42
|
+
aws_access_key "XXXXXXXXXXXXXXXXXXXX"
|
43
|
+
aws_secret_access_key "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
|
44
|
+
chef_bucket "maestro.mydomain.com"
|
45
|
+
|
46
|
+
roles {}
|
47
|
+
|
48
|
+
nodes do
|
49
|
+
ec2_node "web-1" do
|
50
|
+
roles ["web"]
|
51
|
+
ami "ami-bb709dd2"
|
52
|
+
ssh_user "ubuntu"
|
53
|
+
instance_type "m1.small"
|
54
|
+
availability_zone "us-east-1b"
|
55
|
+
elastic_ip "111.111.11.111"
|
56
|
+
ebs_volume_id "vol-XXXXXXXX"
|
57
|
+
ebs_device "/dev/sdh"
|
58
|
+
end
|
59
|
+
ec2_node "web-1" do
|
60
|
+
roles ["web"]
|
61
|
+
ami "ami-bb709dd2"
|
62
|
+
ssh_user "ubuntu"
|
63
|
+
instance_type "m1.small"
|
64
|
+
availability_zone "us-east-1b"
|
65
|
+
elastic_ip "111.111.11.111"
|
66
|
+
ebs_volume_id "vol-XXXXXXXX"
|
67
|
+
ebs_device "/dev/sdh"
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
cloud.validate
|
72
|
+
assert !cloud.valid?
|
73
|
+
assert cloud.validation_errors.any? {|message| !message.index("Duplicate node definition: web-1").nil?}
|
74
|
+
end
|
75
|
+
|
76
|
+
should "be invalid due to duplicate elb nodes" do
|
77
|
+
cloud = aws_cloud :test do
|
78
|
+
keypair_name "XXXXXXX-keypair"
|
79
|
+
keypair_file "/path/to/id_rsa-XXXXXXX-keypair"
|
80
|
+
aws_account_id "XXXX-XXXX-XXXX"
|
81
|
+
aws_access_key "XXXXXXXXXXXXXXXXXXXX"
|
82
|
+
aws_secret_access_key "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
|
83
|
+
chef_bucket "maestro.mydomain.com"
|
84
|
+
|
85
|
+
roles {}
|
86
|
+
|
87
|
+
nodes do
|
88
|
+
elb_node "lb-1" do
|
89
|
+
end
|
90
|
+
elb_node "lb-1" do
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
cloud.validate
|
95
|
+
assert !cloud.valid?
|
96
|
+
assert cloud.validation_errors.any? {|message| !message.index("Duplicate node definition: lb-1").nil?}
|
97
|
+
end
|
98
|
+
|
99
|
+
should "be invalid due to missing aws access key" do
|
100
|
+
@cloud.aws_access_key nil
|
101
|
+
@cloud.validate
|
102
|
+
assert !@cloud.valid?
|
103
|
+
assert @cloud.validation_errors.any? {|message| !message.index("Missing aws_access_key").nil? }
|
104
|
+
end
|
105
|
+
|
106
|
+
should "be invalid due to missing aws account id" do
|
107
|
+
@cloud.aws_account_id nil
|
108
|
+
@cloud.validate
|
109
|
+
assert !@cloud.valid?
|
110
|
+
assert @cloud.validation_errors.any? {|message| !message.index("Missing aws_account_id").nil? }
|
111
|
+
end
|
112
|
+
|
113
|
+
should "be invalid due to missing aws secret access key" do
|
114
|
+
@cloud.aws_secret_access_key nil
|
115
|
+
@cloud.validate
|
116
|
+
assert !@cloud.valid?
|
117
|
+
assert @cloud.validation_errors.any? {|message| !message.index("Missing aws_secret_access_key").nil? }
|
118
|
+
end
|
119
|
+
|
120
|
+
should "be invalid due to missing chef bucket" do
|
121
|
+
@cloud.chef_bucket nil
|
122
|
+
@cloud.validate
|
123
|
+
assert !@cloud.valid?
|
124
|
+
assert @cloud.validation_errors.any? {|message| !message.index("Missing chef_bucket").nil? }
|
125
|
+
end
|
126
|
+
|
127
|
+
should "be valid" do
|
128
|
+
@cloud.validate
|
129
|
+
assert @cloud.valid?
|
130
|
+
assert @cloud.validation_errors.empty?
|
131
|
+
end
|
132
|
+
end
|
133
|
+
end
|
@@ -0,0 +1,76 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
# Unit tests for Maestro::Node::Aws::Ec2
|
4
|
+
class TestAwsEc2Node < Test::Unit::TestCase
|
5
|
+
|
6
|
+
context "Maestro::Node::Aws::Ec2" do
|
7
|
+
setup do
|
8
|
+
@cloud = aws_cloud :test do
|
9
|
+
roles do
|
10
|
+
role "web" do
|
11
|
+
public_ports [80, 443]
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
nodes do
|
16
|
+
ec2_node "web-1" do
|
17
|
+
roles ["web"]
|
18
|
+
ami "ami-bb709dd2"
|
19
|
+
ssh_user "ubuntu"
|
20
|
+
instance_type "m1.small"
|
21
|
+
availability_zone "us-east-1b"
|
22
|
+
elastic_ip "111.111.11.111"
|
23
|
+
ebs_volume_id "vol-XXXXXXXX"
|
24
|
+
ebs_device "/dev/sdh"
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
@node = @cloud.nodes["web-1"]
|
29
|
+
end
|
30
|
+
|
31
|
+
should "be an Ec2 node" do
|
32
|
+
assert @node.is_a? Maestro::Node::Aws::Ec2
|
33
|
+
end
|
34
|
+
|
35
|
+
should "be invalid due to node missing ami" do
|
36
|
+
@node.ami nil
|
37
|
+
@node.validate
|
38
|
+
assert !@node.valid?
|
39
|
+
assert @node.validation_errors.any? {|message| !message.index("missing ami").nil? }
|
40
|
+
end
|
41
|
+
|
42
|
+
should "be invalid due to node missing instance type" do
|
43
|
+
@node.instance_type nil
|
44
|
+
@node.validate
|
45
|
+
assert !@node.valid?
|
46
|
+
assert @node.validation_errors.any? {|message| !message.index("missing instance_type").nil? }
|
47
|
+
end
|
48
|
+
|
49
|
+
should "be invalid due to node missing availability zone" do
|
50
|
+
@node.availability_zone nil
|
51
|
+
@node.validate
|
52
|
+
assert !@node.valid?
|
53
|
+
assert @node.validation_errors.any? {|message| !message.index("missing availability_zone").nil? }
|
54
|
+
end
|
55
|
+
|
56
|
+
should "be invalid due to node missing ebs_device" do
|
57
|
+
@node.ebs_device nil
|
58
|
+
@node.validate
|
59
|
+
assert !@node.valid?
|
60
|
+
assert @node.validation_errors.any? {|message| !message.index("missing ebs_device").nil? }
|
61
|
+
end
|
62
|
+
|
63
|
+
should "be invalid due to node missing ebs_volume_id" do
|
64
|
+
@node.ebs_volume_id nil
|
65
|
+
@node.validate
|
66
|
+
assert !@node.valid?
|
67
|
+
assert @node.validation_errors.any? {|message| !message.index("missing ebs_volume_id").nil? }
|
68
|
+
end
|
69
|
+
|
70
|
+
should "be valid" do
|
71
|
+
@node.validate
|
72
|
+
assert @node.valid?
|
73
|
+
assert @node.validation_errors.empty?
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
@@ -0,0 +1,221 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
# Unit tests for Maestro::Node::Aws::Elb
|
4
|
+
class TestAwsElbNode < Test::Unit::TestCase
|
5
|
+
|
6
|
+
context "Maestro::Node::Aws::Elb" do
|
7
|
+
setup do
|
8
|
+
@cloud = aws_cloud :test do
|
9
|
+
roles {}
|
10
|
+
|
11
|
+
nodes do
|
12
|
+
ec2_node "web-1" do end
|
13
|
+
|
14
|
+
elb_node "lb-1" do
|
15
|
+
availability_zones ["us-east-1b"]
|
16
|
+
listeners [{:load_balancer_port => 80, :instance_port => 80, :protocol => "http"}]
|
17
|
+
ec2_nodes ["web-1"]
|
18
|
+
health_check(:target => "TCP:80", :timeout => 15, :interval => 60, :unhealthy_threshold => 5, :healthy_threshold => 3)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
@node = @cloud.nodes["lb-1"]
|
23
|
+
end
|
24
|
+
|
25
|
+
should "be an Elb node" do
|
26
|
+
assert @node.is_a? Maestro::Node::Aws::Elb
|
27
|
+
end
|
28
|
+
|
29
|
+
should "be invalid due to name too long" do
|
30
|
+
cloud = aws_cloud :test do
|
31
|
+
roles {}
|
32
|
+
nodes do
|
33
|
+
ec2_node "web-1" do end
|
34
|
+
elb_node "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX123" do end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
node = cloud.nodes["XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX123"]
|
38
|
+
node.validate
|
39
|
+
assert !node.valid?
|
40
|
+
assert node.validation_errors.any? {|message| !message.index("name must be less than 32 characters").nil?}
|
41
|
+
end
|
42
|
+
|
43
|
+
should "be invalid due to name containing invalid characters" do
|
44
|
+
"!@\#$%^&*()_=+~`\"{[}]\\|/?.>,<".each_char do |char|
|
45
|
+
cloud = aws_cloud :test do
|
46
|
+
roles {}
|
47
|
+
nodes do
|
48
|
+
ec2_node "web-1" do end
|
49
|
+
elb_node "#{char}" do end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
node = cloud.nodes["#{char}"]
|
53
|
+
node.validate
|
54
|
+
assert !node.valid?
|
55
|
+
assert node.validation_errors.any? {|message| !message.index("name may only contain alphanumerics and hyphens").nil?}
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
should "be invalid due to name not starting with a letter" do
|
60
|
+
"0123456789!@\#$%^&*()_=+~`\"{[}]\\|/?.>,<".each_char do |char|
|
61
|
+
cloud = aws_cloud :test do
|
62
|
+
roles {}
|
63
|
+
nodes do
|
64
|
+
ec2_node "web-1" do end
|
65
|
+
elb_node "#{char}" do end
|
66
|
+
end
|
67
|
+
end
|
68
|
+
node = cloud.nodes["#{char}"]
|
69
|
+
node.validate
|
70
|
+
assert !node.valid?
|
71
|
+
assert node.validation_errors.any? {|message| !message.index("name must start with a letter").nil?}
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
should "be invalid due to name ending with hyphen" do
|
76
|
+
cloud = aws_cloud :test do
|
77
|
+
roles {}
|
78
|
+
nodes do
|
79
|
+
ec2_node "web-1" do end
|
80
|
+
elb_node "test-" do end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
node = cloud.nodes["test-"]
|
84
|
+
node.validate
|
85
|
+
assert !node.valid?
|
86
|
+
assert node.validation_errors.any? {|message| !message.index("name must not end with a hypen").nil?}
|
87
|
+
end
|
88
|
+
|
89
|
+
should "be invalid due to name containing two consecutive hyphens" do
|
90
|
+
cloud = aws_cloud :test do
|
91
|
+
roles {}
|
92
|
+
nodes do
|
93
|
+
ec2_node "web-1" do end
|
94
|
+
elb_node "te--st" do end
|
95
|
+
end
|
96
|
+
end
|
97
|
+
node = cloud.nodes["te--st"]
|
98
|
+
node.validate
|
99
|
+
assert !node.valid?
|
100
|
+
assert node.validation_errors.any? {|message| !message.index("name must not contain two consecutive hyphens").nil?}
|
101
|
+
end
|
102
|
+
|
103
|
+
should "be invalid due to missing listeners" do
|
104
|
+
@node.listeners nil
|
105
|
+
@node.validate
|
106
|
+
assert !@node.valid?
|
107
|
+
assert @node.validation_errors.any? {|message| !message.index("node missing listeners").nil? }
|
108
|
+
end
|
109
|
+
|
110
|
+
should "be invalid due to listeners not an array" do
|
111
|
+
@node.listeners "foo"
|
112
|
+
@node.validate
|
113
|
+
assert !@node.valid?
|
114
|
+
assert @node.validation_errors.any? {|message| !message.index("node's listeners must be an Array of Hashes").nil? }
|
115
|
+
end
|
116
|
+
|
117
|
+
should "be invalid due to listeners element not a Hash" do
|
118
|
+
@node.listeners[0] = "foo"
|
119
|
+
@node.validate
|
120
|
+
assert !@node.valid?
|
121
|
+
assert @node.validation_errors.any? {|message| !message.index("node's listeners must be an Array of Hashes").nil? }
|
122
|
+
end
|
123
|
+
|
124
|
+
should "be invalid due to missing load_balancer_port" do
|
125
|
+
@node.listeners[0].delete(:load_balancer_port)
|
126
|
+
@node.validate
|
127
|
+
assert !@node.valid?
|
128
|
+
assert @node.validation_errors.any? {|message| !message.index("node's listeners Hash missing :load_balancer_port key").nil? }
|
129
|
+
end
|
130
|
+
|
131
|
+
should "be invalid due to missing instance_port" do
|
132
|
+
@node.listeners[0].delete(:instance_port)
|
133
|
+
@node.validate
|
134
|
+
assert !@node.valid?
|
135
|
+
assert @node.validation_errors.any? {|message| !message.index("node's listeners Hash missing :instance_port key").nil? }
|
136
|
+
end
|
137
|
+
|
138
|
+
should "be invalid due to missing protocol" do
|
139
|
+
@node.listeners[0].delete(:protocol)
|
140
|
+
@node.validate
|
141
|
+
assert !@node.valid?
|
142
|
+
assert @node.validation_errors.any? {|message| !message.index("node's listeners Hash missing :protocol key").nil? }
|
143
|
+
end
|
144
|
+
|
145
|
+
should "be invalid due to missing ec2_nodes" do
|
146
|
+
@node.ec2_nodes nil
|
147
|
+
@node.validate
|
148
|
+
assert !@node.valid?
|
149
|
+
assert @node.validation_errors.any? {|message| !message.index("node missing ec2_nodes collection").nil? }
|
150
|
+
end
|
151
|
+
|
152
|
+
should "be invalid due to ec2_nodes not an array" do
|
153
|
+
@node.ec2_nodes 1
|
154
|
+
@node.validate
|
155
|
+
assert !@node.valid?
|
156
|
+
assert @node.validation_errors.any? {|message| !message.index("node ec2_nodes collection is not an Array ").nil? }
|
157
|
+
end
|
158
|
+
|
159
|
+
should "be invalid due to missing availability_zones" do
|
160
|
+
@node.availability_zones nil
|
161
|
+
@node.validate
|
162
|
+
assert !@node.valid?
|
163
|
+
assert @node.validation_errors.any? {|message| !message.index("node missing availability_zones collection").nil? }
|
164
|
+
end
|
165
|
+
|
166
|
+
should "be invalid due to availability_zones not an array" do
|
167
|
+
@node.availability_zones 1
|
168
|
+
@node.validate
|
169
|
+
assert !@node.valid?
|
170
|
+
assert @node.validation_errors.any? {|message| !message.index("node availability_zones collection is not an Array ").nil? }
|
171
|
+
end
|
172
|
+
|
173
|
+
should "be invalid due to health_check element not a Hash" do
|
174
|
+
@node.health_check "foo"
|
175
|
+
@node.validate
|
176
|
+
assert !@node.valid?
|
177
|
+
assert @node.validation_errors.any? {|message| !message.index("node's health_check must be a Hash").nil? }
|
178
|
+
end
|
179
|
+
|
180
|
+
should "be invalid due to missing target" do
|
181
|
+
@node.health_check.delete(:target)
|
182
|
+
@node.validate
|
183
|
+
assert !@node.valid?
|
184
|
+
assert @node.validation_errors.any? {|message| !message.index("node's health_check Hash missing :target key").nil? }
|
185
|
+
end
|
186
|
+
|
187
|
+
should "be invalid due to missing timeout" do
|
188
|
+
@node.health_check.delete(:timeout)
|
189
|
+
@node.validate
|
190
|
+
assert !@node.valid?
|
191
|
+
assert @node.validation_errors.any? {|message| !message.index("node's health_check Hash missing :timeout key").nil? }
|
192
|
+
end
|
193
|
+
|
194
|
+
should "be invalid due to missing interval" do
|
195
|
+
@node.health_check.delete(:interval)
|
196
|
+
@node.validate
|
197
|
+
assert !@node.valid?
|
198
|
+
assert @node.validation_errors.any? {|message| !message.index("node's health_check Hash missing :interval key").nil? }
|
199
|
+
end
|
200
|
+
|
201
|
+
should "be invalid due to missing unhealthy_threshold" do
|
202
|
+
@node.health_check.delete(:unhealthy_threshold)
|
203
|
+
@node.validate
|
204
|
+
assert !@node.valid?
|
205
|
+
assert @node.validation_errors.any? {|message| !message.index("node's health_check Hash missing :unhealthy_threshold key").nil? }
|
206
|
+
end
|
207
|
+
|
208
|
+
should "be invalid due to missing healthy_threshold" do
|
209
|
+
@node.health_check.delete(:healthy_threshold)
|
210
|
+
@node.validate
|
211
|
+
assert !@node.valid?
|
212
|
+
assert @node.validation_errors.any? {|message| !message.index("node's health_check Hash missing :healthy_threshold key").nil? }
|
213
|
+
end
|
214
|
+
|
215
|
+
should "be valid" do
|
216
|
+
@node.validate
|
217
|
+
assert @node.valid?
|
218
|
+
assert @node.validation_errors.empty?
|
219
|
+
end
|
220
|
+
end
|
221
|
+
end
|