text: # Copyright (c) 2015 Telefonica I+D.
  
  # Licensed under the Apache License, Version 2.0 (the "License");
  # you may not use this file except in compliance with the License.
  # You may obtain a copy of the License at
  #
  # http://www.apache.org/licenses/LICENSE-2.0
  #
  # Unless required by applicable law or agreed to in writing, software
  # distributed under the License is distributed on an "AS IS" BASIS,
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
  # implied.
  # See the License for the specific language governing permissions and
  # limitations under the License.
  
  import json
  
  from oslo_config import cfg
  from oslo_utils import timeutils
  
  from murano.api.v1 import templates
  from murano.common import config
  from murano.db import models
  import murano.tests.unit.api.base as tb
  import murano.tests.unit.utils as test_utils
  
  
  class TestEnvTemplateApi(tb.ControllerTest, tb.MuranoApiTestCase):
      def setUp(self):
          super(TestEnvTemplateApi, self).setUp()
          self.controller = templates.Controller()
          self.uuids = ['env_template_id', 'other', 'network_id',
                        'environment_id', 'session_id']
          self.mock_uuid = self._stub_uuid(self.uuids)
  
      def test_list_empty_env_templates(self):
          """Check that with no templates an empty list is returned."""
          self._set_policy_rules(
              {'list_env_templates': '@'}
          )
          self.expect_policy_check('list_env_templates')
  
          req = self._get('/templates')
          result = req.get_response(self.api)
          self.assertEqual({'templates': []}, json.loads(result.body))
  
      def test_create_env_templates(self):
          """Create an template, test template.show()."""
          self._set_policy_rules(
              {'list_env_templates': '@',
               'create_env_template': '@',
               'show_env_template': '@'}
          )
          self.expect_policy_check('create_env_template')
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
  
          expected = {'tenant_id': self.tenant,
                      'id': 'env_template_id',
                      'name': 'mytemp',
                      'networking': {},
                      'version': 0,
                      'created': timeutils.isotime(fake_now)[:-1],
                      'updated': timeutils.isotime(fake_now)[:-1]}
  
          body = {'name': 'mytemp'}
          req = self._post('/templates', json.dumps(body))
          result = req.get_response(self.api)
  
          self.assertEqual(expected, json.loads(result.body))
  
          # Reset the policy expectation
          self.expect_policy_check('list_env_templates')
  
          req = self._get('/templates')
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
          self.assertEqual({'templates': [expected]}, json.loads(result.body))
  
          expected['services'] = []
  
          self.expect_policy_check('show_env_template',
                                   {'env_template_id': self.uuids[0]})
          req = self._get('/templates/%s' % self.uuids[0])
          result = req.get_response(self.api)
          self.assertEqual(expected, json.loads(result.body))
  
      def test_illegal_template_name_create(self):
          """Check that an illegal temp name results in an HTTPClientError."""
          self._set_policy_rules(
              {'list_env_templates': '@',
               'create_env_template': '@',
               'show_env_template': '@'}
          )
          self.expect_policy_check('create_env_template')
  
          body = {'name': 'my+#temp'}
          req = self._post('/templates', json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(400, result.status_code)
  
      def test_mallformed_body(self):
          """Check that an illegal temp name results in an HTTPClientError."""
          self._set_policy_rules(
              {'create_env_template': '@'}
          )
          self.expect_policy_check('create_env_template')
  
          body = {'invalid': 'test'}
          req = self._post('/templates', json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(400, result.status_code)
  
      def test_missing_env_template(self):
          """Check that a missing environment template
          results in an HTTPNotFound.
          """
          self._set_policy_rules(
              {'show_env_template': '@'}
          )
          self.expect_policy_check('show_env_template',
                                   {'env_template_id': 'no-such-id'})
  
          req = self._get('/templates/no-such-id')
          result = req.get_response(self.api)
          self.assertEqual(404, result.status_code)
  
      def test_update_env_template(self):
          """Check that environment rename works."""
          self._set_policy_rules(
              {'show_env_template': '@',
               'update_env_template': '@'}
          )
          self.expect_policy_check('update_env_template',
                                   {'env_template_id': '12345'})
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
  
          expected = dict(
              id='12345',
              name='my-temp',
              version=0,
              networking={},
              created=fake_now,
              updated=fake_now,
              tenant_id=self.tenant,
              description={
                  'name': 'my-temp',
                  '?': {'id': '12345'}
              }
          )
          e = models.EnvironmentTemplate(**expected)
          test_utils.save_models(e)
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
  
          del expected['description']
          expected['services'] = []
          expected['name'] = 'renamed_temp'
          expected['updated'] = fake_now
  
          body = {
              'name': 'renamed_temp'
          }
          req = self._put('/templates/12345', json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          self.expect_policy_check('show_env_template',
                                   {'env_template_id': '12345'})
          req = self._get('/templates/12345')
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          expected['created'] = timeutils.isotime(expected['created'])[:-1]
          expected['updated'] = timeutils.isotime(expected['updated'])[:-1]
  
          self.assertEqual(expected, json.loads(result.body))
  
      def test_delete_env_templates(self):
          """Test that environment deletion results in the correct rpc call."""
          self._set_policy_rules(
              {'delete_env_template': '@'}
          )
          self.expect_policy_check(
              'delete_env_template', {'env_template_id': '12345'}
          )
  
          fake_now = timeutils.utcnow()
          expected = dict(
              id='12345',
              name='my-temp',
              version=0,
              networking={},
              created=fake_now,
              updated=fake_now,
              tenant_id=self.tenant,
              description={
                  'name': 'my-temp',
                  '?': {'id': '12345'}
              }
          )
          e = models.EnvironmentTemplate(**expected)
          test_utils.save_models(e)
  
          req = self._delete('/templates/12345')
          result = req.get_response(self.api)
  
          # Should this be expected behavior?
          self.assertEqual('', result.body)
          self.assertEqual(200, result.status_code)
  
      def test_create_env_templates_with_applications(self):
          """Create an template, test template.show()."""
          self._set_policy_rules(
              {'list_env_templates': '@',
               'create_env_template': '@',
               'show_env_template': '@'}
          )
          self.expect_policy_check('create_env_template')
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
          expected = {'tenant_id': self.tenant,
                      'id': self.uuids[0],
                      'name': 'env_template_name',
                      'networking': {},
                      'version': 0,
                      'created': timeutils.isotime(fake_now)[:-1],
                      'updated': timeutils.isotime(fake_now)[:-1]}
  
          services = [
              {
                  "instance": {
                      "assignFloatingIp": "true",
                      "keyname": "mykeyname",
                      "image": "cloud-fedora-v3",
                      "flavor": "m1.medium",
                      "?": {
                          "type": "io.murano.resources.Linux",
                          "id": "ef984a74-29a4-45c0-b1dc-2ab9f075732e"
                      }
                  },
                  "name": "orion",
                  "port": "8080",
                  "?": {
                      "type": "io.murano.apps.apache.Tomcat",
                      "id": "54cea43d-5970-4c73-b9ac-fea656f3c722"
                  }
              }
          ]
          expected['services'] = services
  
          body = {
              "name": "env_template_name",
              "services": [
                  {
                      "instance": {
                          "assignFloatingIp": "true",
                          "keyname": "mykeyname",
                          "image": "cloud-fedora-v3",
                          "flavor": "m1.medium",
                          "?": {
                              "type": "io.murano.resources.Linux",
                              "id": "ef984a74-29a4-45c0-b1dc-2ab9f075732e"
                          }
                      },
                      "name": "orion",
                      "port": "8080",
                      "?": {
                          "type": "io.murano.apps.apache.Tomcat",
                          "id": "54cea43d-5970-4c73-b9ac-fea656f3c722"
                      }
                  }
              ]
          }
  
          req = self._post('/templates', json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(expected, json.loads(result.body))
  
          # Reset the policy expectation
          self.expect_policy_check('list_env_templates')
  
          req = self._get('/templates')
          result = req.get_response(self.api)
          del expected['services']
          self.assertEqual(200, result.status_code)
          self.assertEqual({'templates': [expected]}, json.loads(result.body))
  
          # Reset the policy expectation
          self.expect_policy_check('show_env_template',
                                   {'env_template_id': self.uuids[0]})
          expected['services'] = services
          req = self._get('/templates/%s' % self.uuids[0])
          result = req.get_response(self.api)
          self.assertEqual(expected, json.loads(result.body))
  
      def test_add_application_to_template(self):
          """Create an template, test template.show()."""
          self._set_policy_rules(
              {'create_env_template': '@',
               'add_application': '@'}
          )
          self.expect_policy_check('create_env_template')
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
          services = [
              {
                  "instance": {
                      "assignFloatingIp": "true",
                      "keyname": "mykeyname",
                      "image": "cloud-fedora-v3",
                      "flavor": "m1.medium",
                      "?": {
                          "type": "io.murano.resources.Linux",
                          "id": "ef984a74-29a4-45c0-b1dc-2ab9f075732e"
                      }
                  },
                  "name": "orion",
                  "port": "8080",
                  "?": {
                      "type": "io.murano.apps.apache.Tomcat",
                      "id": "54cea43d-5970-4c73-b9ac-fea656f3c722"
                  }
              }
          ]
  
          body = {
              "name": "template_name",
          }
  
          req = self._post('/templates', json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          body = services
          req = self._post('/templates/%s/services' % self.uuids[0],
                           json.dumps(body))
          result = req.get_response(self.api)
  
          self.assertEqual(200, result.status_code)
          self.assertEqual(services, json.loads(result.body))
          req = self._get('/templates/%s/services' % self.uuids[0])
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
          self.assertEqual(1, len(json.loads(result.body)))
  
          service_no_instance = [
              {
                  "instance": "ef984a74-29a4-45c0-b1dc-2ab9f075732e",
                  "name": "tomcat",
                  "port": "8080",
                  "?": {
                      "type": "io.murano.apps.apache.Tomcat",
                      "id": "54cea43d-5970-4c73-b9ac-fea656f3c722"
                  }
              }
          ]
  
          req = self._post('/templates/%s/services' % self.uuids[0],
                           json.dumps(service_no_instance))
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          req = self._get('/templates/%s/services' % self.uuids[0])
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
          self.assertEqual(2, len(json.loads(result.body)))
  
      def test_delete_application_in_template(self):
          """Create an template, test template.show()."""
          self._set_policy_rules(
              {'create_env_template': '@',
               'delete_env_application': '@'}
          )
          self.expect_policy_check('create_env_template')
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
  
          body = {
              "name": "mytemplate",
              "services": [
                  {
                      "name": "tomcat",
                      "port": "8080",
                      "?": {
                          "type": "io.murano.apps.apache.Tomcat",
                          "id": "54cea43d-5970-4c73-b9ac-fea656f3c722"
                      }
                  }
              ]
          }
  
          req = self._post('/templates', json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          req = self._get('/templates/%s/services' % self.uuids[0])
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
          self.assertEqual(1, len(json.loads(result.body)))
  
          service_id = '54cea43d-5970-4c73-b9ac-fea656f3c722'
          req = self._get('/templates/' + self.uuids[0] +
                          '/services/' + service_id)
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          req = self._delete('/templates/' + self.uuids[0] +
                             '/services/' + service_id)
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
          req = self._get('/templates/' + self.uuids[0] +
                          '/services/' + service_id)
          result = req.get_response(self.api)
          self.assertEqual(404, result.status_code)
  
      def test_create_environment(self):
          """Test that environment is created, session configured."""
  
          opts = [
              cfg.StrOpt('config_dir'),
              cfg.StrOpt('config_file', default='murano.conf'),
              cfg.StrOpt('project', default='murano'),
          ]
          config.CONF.register_opts(opts)
          self._set_policy_rules(
              {'create_env_template': '@',
               'create_environment': '@'}
          )
  
          self._create_env_template_no_service()
          body_env = {'name': 'my_template'}
  
          self.expect_policy_check('create_environment',
                                   {'env_template_id': self.uuids[0]})
          req = self._post('/templates/%s/create-environment' %
                           self.uuids[0], json.dumps(body_env))
          session_result = req.get_response(self.api)
          self.assertEqual(200, session_result.status_code)
          self.assertIsNotNone(session_result)
          body_returned = json.loads(session_result.body)
          self.assertEqual(self.uuids[4], body_returned['session_id'])
          self.assertEqual(self.uuids[3], body_returned['environment_id'])
  
      def test_create_env_with_template_no_services(self):
          """Test that environment is created and session with template
          without services.
          """
          opts = [
              cfg.StrOpt('config_dir'),
              cfg.StrOpt('config_file', default='murano.conf'),
              cfg.StrOpt('project', default='murano'),
          ]
          config.CONF.register_opts(opts)
          self._set_policy_rules(
              {'create_env_template': '@',
               'create_environment': '@'}
          )
          self._create_env_template_no_service()
  
          self.expect_policy_check('create_environment',
                                   {'env_template_id': self.uuids[0]})
          body = {'name': 'my_template'}
  
          req = self._post('/templates/%s/create-environment' %
                           self.uuids[0], json.dumps(body))
          result = req.get_response(self.api)
          self.assertIsNotNone(result)
          self.assertEqual(200, result.status_code)
          body_returned = json.loads(result.body)
          self.assertEqual(self.uuids[4], body_returned['session_id'])
          self.assertEqual(self.uuids[3], body_returned['environment_id'])
  
      def test_mallformed_env_body(self):
          """Check that an illegal temp name results in an HTTPClientError."""
          self._set_policy_rules(
              {'create_env_template': '@',
               'create_environment': '@'}
          )
          self. _create_env_template_no_service()
  
          self.expect_policy_check('create_environment',
                                   {'env_template_id': self.uuids[0]})
          body = {'invalid': 'test'}
          req = self._post('/templates/%s/create-environment' %
                           self.uuids[0], json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(400, result.status_code)
  
      def test_create_env_notexisting_templatebody(self):
          """Check that an illegal temp name results in an HTTPClientError."""
          self._set_policy_rules(
              {'create_environment': '@'}
          )
          env_template_id = 'noexisting'
          self.expect_policy_check('create_environment',
                                   {'env_template_id': env_template_id})
  
          body = {'name': 'test'}
          req = self._post('/templates/%s/create-environment'
                           % env_template_id, json.dumps(body))
          result = req.get_response(self.api)
          self.assertEqual(404, result.status_code)
  
      def _create_env_template_no_service(self):
          self.expect_policy_check('create_env_template')
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
  
          req = self._post('/templates', json.dumps({'name': 'name'}))
          result = req.get_response(self.api)
          self.assertEqual(200, result.status_code)
  
      def _create_env_template_services(self):
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
  
          self.expect_policy_check('create_env_template')
  
          fake_now = timeutils.utcnow()
          timeutils.utcnow.override_time = fake_now
          body = {
              "name": "env_template_name",
              "services": [
                  {
                      "instance": {
                          "assignFloatingIp": "true",
                          "keyname": "mykeyname",
                          "image": "cloud-fedora-v3",
                          "flavor": "m1.medium",
                          "?": {
                              "type": "io.murano.resources.Linux",
                              "id": "ef984a74-29a4-45c0-b1dc-2ab9f075732e"
                          }
                      },
                      "name": "orion",
                      "port": "8080",
                      "?": {
                          "type": "io.murano.apps.apache.Tomcat",
                          "id": "54cea43d-5970-4c73-b9ac-fea656f3c722"
                      }
                  }
              ]
          }
  
          req = self._post('/templates', json.dumps(body))
          req.get_response(self.api)
  