blob: 19fd1a8613d34e448fb8693471d95abf7e889d5e [file] [log] [blame]
Steve Bakerf6c8f122015-02-10 13:54:46 +13001# Licensed under the Apache License, Version 2.0 (the "License"); you may
2# not use this file except in compliance with the License. You may obtain
3# a copy of the License at
4#
5# http://www.apache.org/licenses/LICENSE-2.0
6#
7# Unless required by applicable law or agreed to in writing, software
8# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
9# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
10# License for the specific language governing permissions and limitations
11# under the License.
12
Steve Baker0b679bb2015-03-11 13:46:42 +130013from heatclient.common import template_utils
Steve Bakerf6c8f122015-02-10 13:54:46 +130014import six
15
16from heat_integrationtests.common import exceptions
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +040017from heat_integrationtests.scenario import scenario_base
Steve Bakerf6c8f122015-02-10 13:54:46 +130018
19CFG1_SH = '''#!/bin/sh
20echo "Writing to /tmp/$bar"
21echo $foo > /tmp/$bar
22echo -n "The file /tmp/$bar contains `cat /tmp/$bar` for server \
23$deploy_server_id during $deploy_action" > $heat_outputs_path.result
24echo "Written to /tmp/$bar"
25echo "Output to stderr" 1>&2
26'''
27
28CFG3_PP = '''file {'barfile':
29 ensure => file,
30 mode => 0644,
31 path => "/tmp/$::bar",
32 content => "$::foo",
33}
34file {'output_result':
35 ensure => file,
36 path => "$::heat_outputs_path.result",
37 mode => 0644,
38 content => "The file /tmp/$::bar contains $::foo for server \
39$::deploy_server_id during $::deploy_action",
40}'''
41
42
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +040043class SoftwareConfigIntegrationTest(scenario_base.ScenarioTestsBase):
Steve Bakerf6c8f122015-02-10 13:54:46 +130044
45 def setUp(self):
46 super(SoftwareConfigIntegrationTest, self).setUp()
47 if self.conf.skip_software_config_tests:
48 self.skipTest('Testing software config disabled in conf, '
49 'skipping')
Steve Bakerf6c8f122015-02-10 13:54:46 +130050 self.stack_name = self._stack_rand_name()
Steve Bakerf6c8f122015-02-10 13:54:46 +130051
Steve Baker8c9aee12015-03-10 16:17:45 +130052 def check_stack(self):
53 sid = self.stack_identifier
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +040054 # Check that all stack resources were created
Steve Bakerf6c8f122015-02-10 13:54:46 +130055 for res in ('cfg2a', 'cfg2b', 'cfg1', 'cfg3', 'server'):
56 self._wait_for_resource_status(
57 sid, res, 'CREATE_COMPLETE')
58
59 server_resource = self.client.resources.get(sid, 'server')
60 server_id = server_resource.physical_resource_id
61 server = self.compute_client.servers.get(server_id)
62
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +040063 # Waiting for each deployment to contribute their
64 # config to resource
Steve Bakerf6c8f122015-02-10 13:54:46 +130065 try:
Steve Bakerf6c8f122015-02-10 13:54:46 +130066 for res in ('dep2b', 'dep1', 'dep3'):
67 self._wait_for_resource_status(
68 sid, res, 'CREATE_IN_PROGRESS')
69
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +040070 server_metadata = self.client.resources.metadata(
71 sid, 'server')
Steve Bakerf6c8f122015-02-10 13:54:46 +130072 deployments = dict((d['name'], d) for d in
73 server_metadata['deployments'])
74
75 for res in ('dep2a', 'dep2b', 'dep1', 'dep3'):
76 self._wait_for_resource_status(
77 sid, res, 'CREATE_COMPLETE')
78 except (exceptions.StackResourceBuildErrorException,
79 exceptions.TimeoutException) as e:
Steve Bakerf6c8f122015-02-10 13:54:46 +130080 raise e
Steve Baker803f1502015-03-11 13:47:08 +130081 finally:
82 # attempt to log the server console regardless of deployments
83 # going to complete. This allows successful and failed boot
84 # logs to be compared
85 self._log_console_output(servers=[server])
Steve Bakerf6c8f122015-02-10 13:54:46 +130086
Steve Bakerf6c8f122015-02-10 13:54:46 +130087 complete_server_metadata = self.client.resources.metadata(
88 sid, 'server')
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +040089
90 # Ensure any previously available deployments haven't changed so
Steve Bakerf6c8f122015-02-10 13:54:46 +130091 # config isn't re-triggered
92 complete_deployments = dict((d['name'], d) for d in
93 complete_server_metadata['deployments'])
94 for k, v in six.iteritems(deployments):
95 self.assertEqual(v, complete_deployments[k])
96
97 stack = self.client.stacks.get(sid)
98
99 res1 = self._stack_output(stack, 'res1')
100 self.assertEqual(
101 'The file %s contains %s for server %s during %s' % (
102 '/tmp/baaaaa', 'fooooo', server_id, 'CREATE'),
103 res1['result'])
104 self.assertEqual(0, res1['status_code'])
105 self.assertEqual('Output to stderr\n', res1['stderr'])
106 self.assertTrue(len(res1['stdout']) > 0)
107
108 res2 = self._stack_output(stack, 'res2')
109 self.assertEqual(
110 'The file %s contains %s for server %s during %s' % (
111 '/tmp/cfn-init-foo', 'barrr', server_id, 'CREATE'),
112 res2['result'])
113 self.assertEqual(0, res2['status_code'])
114 self.assertEqual('', res2['stderr'])
115 self.assertEqual('', res2['stdout'])
116
117 res3 = self._stack_output(stack, 'res3')
118 self.assertEqual(
119 'The file %s contains %s for server %s during %s' % (
120 '/tmp/ba', 'fo', server_id, 'CREATE'),
121 res3['result'])
122 self.assertEqual(0, res3['status_code'])
123 self.assertEqual('', res3['stderr'])
124 self.assertTrue(len(res1['stdout']) > 0)
125
126 dep1_resource = self.client.resources.get(sid, 'dep1')
127 dep1_id = dep1_resource.physical_resource_id
128 dep1_dep = self.client.software_deployments.get(dep1_id)
Steve Baker8c9aee12015-03-10 16:17:45 +1300129 if hasattr(dep1_dep, 'updated_time'):
130 # Only check updated_time if the attribute exists.
131 # This allows latest heat agent code to be tested with
132 # Juno heat (which doesn't expose updated_time)
133 self.assertIsNotNone(dep1_dep.updated_time)
134 self.assertNotEqual(
135 dep1_dep.updated_time,
136 dep1_dep.creation_time)
Steve Bakerf6c8f122015-02-10 13:54:46 +1300137
138 def test_server_software_config(self):
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +0400139 """
140 Check that passed files with scripts are executed on created server.
141
142 The alternative scenario is the following:
143 1. Create a stack and pass files with scripts.
144 2. Check that all stack resources are created successfully.
145 3. Wait for all deployments.
146 4. Check that stack was created.
147 5. Check stack outputs.
148 """
149
150 parameters = {
151 'key_name': self.keypair_name,
152 'flavor': self.conf.instance_type,
153 'image': self.conf.image_ref,
154 'network': self.net['id']
155 }
156
157 files = {
158 'cfg1.sh': CFG1_SH,
159 'cfg3.pp': CFG3_PP
160 }
161
Steve Baker0b679bb2015-03-11 13:46:42 +1300162 env_files, env = template_utils.process_environment_and_files(
163 self.conf.boot_config_env)
164
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +0400165 # Launch stack
Steve Baker8c9aee12015-03-10 16:17:45 +1300166 self.stack_identifier = self.launch_stack(
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +0400167 stack_name=self.stack_name,
168 template_name='test_server_software_config.yaml',
169 parameters=parameters,
Steve Baker0b679bb2015-03-11 13:46:42 +1300170 files=dict(list(files.items()) + list(env_files.items())),
171 expected_status=None,
172 environment=env
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +0400173 )
174
Anastasia Kuznetsovae45bfff2015-02-25 12:50:34 +0400175 # Check stack
Steve Baker8c9aee12015-03-10 16:17:45 +1300176 self.check_stack()