Exemple #1
0
 def test_service(self):
     sot = orchestration_service.OrchestrationService()
     self.assertEqual('orchestration', sot.service_type)
     self.assertEqual('public', sot.interface)
     self.assertIsNone(sot.region)
     self.assertIsNone(sot.service_name)
     self.assertEqual(1, len(sot.valid_versions))
     self.assertEqual('v1', sot.valid_versions[0].module)
     self.assertEqual('v1', sot.valid_versions[0].path)
     self.assertTrue(sot.requires_project_id)
Exemple #2
0
    def __init__(self, plugins=None):
        """User preference for each service.

        :param list plugins: List of entry point namespaces to load.

        Create a new :class:`~ecl.profile.Profile`
        object with no preferences defined, but knowledge of the services.
        Services are identified by their service type, e.g.: 'identity',
        'compute', etc.
        """
        self._services = {}
        self._add_service(compute_service.ComputeService(version="v2"))
        self._add_service(
            connectivity_service.ConnectivityService(version="v1"))
        self._add_service(identity_service.IdentityService(version="v3"))
        self._add_service(image_service.ImageService(version="v2"))
        self._add_service(network_service.NetworkService(version="v2"))
        self._add_service(sss_service.SssService(version="v1"))
        self._add_service(
            orchestration_service.OrchestrationService(version="v1"))
        self._add_service(
            provider_connectivity_service.ProviderConnectivityService(
                version="v2"))
        self._add_service(telemetry_service.TelemetryService(version="v2"))
        self._add_service(block_store_service.BlockStoreService(version="v2"))
        self._add_service(storage_service.StorageService(version="v1"))
        self._add_service(
            security_order_service.SecurityOrderService(version="v2"))
        self._add_service(
            security_portal_service.SecurityPortalService(version="v2"))
        ## This section will be deleted if MSS v1 API is not available
        self._add_service(
            security_order_service_v1.SecurityOrderService(version="v1"))
        self._add_service(
            security_portal_service_v1.SecurityPortalService(version="v1"))
        ## end of the section
        self._add_service(rca_service.RcaService(version="v1"))
        self._add_service(baremetal_service.BaremetalService(version="v2"))
        self._add_service(
            dedicated_hypervisor_service.DedicatedHypervisorService(
                version="v1"))
        self._add_service(dns_service.DnsService(version="v2"))
        self._add_service(
            virtual_network_appliance_service.VirtualNetworkApplianceService(
                version="v1"))
        self._add_service(mvna_service.MVNAService(version="v1"))

        # NOTE: The Metric service is not added here as it currently
        # only retrieves the /capabilities API.

        if plugins:
            for plugin in plugins:
                self._load_plugin(plugin)
        self.service_keys = sorted(self._services.keys())
Exemple #3
0
class Version(resource.Resource):
    resource_key = 'version'
    resources_key = 'versions'
    base_path = '/'
    service = orchestration_service.OrchestrationService(
        version=orchestration_service.OrchestrationService.UNVERSIONED)

    # capabilities
    allow_list = True

    # Properties
    links = resource.prop('links')
    status = resource.prop('status')
Exemple #4
0
class SoftwareDeployment(resource.Resource):
    resource_key = 'software_deployment'
    resources_key = 'software_deployments'
    base_path = '/software_deployments'
    service = orchestration_service.OrchestrationService()

    # capabilities
    allow_create = True
    allow_list = True
    allow_get = True
    allow_delete = True
    allow_update = True

    # Properties
    #: The stack action that triggers this deployment resource.
    action = resource.Body('action')
    #: The UUID of the software config resource that runs when applying to the
    #: server.
    config_id = resource.Body('config_id')
    #: A map containing the names and values of all inputs to the config.
    input_values = resource.Body('input_values', type=dict)
    #: A map containing the names and values from the deployment.
    output_values = resource.Body('output_values', type=dict)
    #: The UUID of the compute server to which the configuration applies.
    server_id = resource.Body('server_id')
    #: The ID of the authentication project which can also perform operations
    #: on this deployment.
    stack_user_project_id = resource.Body('stack_user_project_id')
    #: Current status of the software deployment.
    status = resource.Body('status')
    #: Error description for the last status change.
    status_reason = resource.Body('status_reason')
    #: The date and time when the software deployment resource was created.
    created_at = resource.Body('creation_time')
    #: The date and time when the software deployment resource was created.
    updated_at = resource.Body('updated_time')

    def create(self, session):
        # This overrides the default behavior of resource creation because
        # heat doesn't accept resource_key in its request.
        return super(SoftwareDeployment, self).create(session,
                                                      prepend_key=False)

    def update(self, session):
        # This overrides the default behavior of resource creation because
        # heat doesn't accept resource_key in its request.
        return super(SoftwareDeployment, self).update(session,
                                                      prepend_key=False)
Exemple #5
0
class Resource(resource.Resource):
    name_attribute = 'resource_name'
    resource_key = 'resource'
    resources_key = 'resources'
    base_path = '/stacks/%(stack_name)s/%(stack_id)s/resources'
    service = orchestration_service.OrchestrationService()

    # capabilities
    allow_create = False
    allow_list = True
    allow_retrieve = False
    allow_delete = False
    allow_update = False

    # Properties
    #: A list of dictionaries containing links relevant to the resource.
    links = resource.Body('links')
    #: ID of the logical resource, usually the literal name of the resource
    #: as it appears in the stack template.
    logical_resource_id = resource.Body('logical_resource_id',
                                        alternate_id=True)
    #: Name of the resource.
    name = resource.Body('resource_name')
    #: ID of the physical resource (if any) that backs up the resource. For
    #: example, it contains a nova server ID if the resource is a nova
    #: server.
    physical_resource_id = resource.Body('physical_resource_id')
    #: A list of resource names that depend on this resource. This
    #: property facilitates the deduction of resource dependencies.
    #: *Type: list*
    required_by = resource.Body('required_by', type=list)
    #: A string representation of the resource type.
    resource_type = resource.Body('resource_type')
    #: A string representing the status the resource is currently in.
    status = resource.Body('resource_status')
    #: A string that explains why the resource is in its current status.
    status_reason = resource.Body('resource_status_reason')
    #: Timestamp of the last update made to the resource.
    updated_at = resource.Body('updated_time')
Exemple #6
0
class Template(resource.Resource):
    service = orchestration_service.OrchestrationService()

    # capabilities
    allow_create = False
    allow_list = False
    allow_retrieve = False
    allow_delete = False
    allow_update = False

    # Properties
    #: The description specified in the template
    description = resource.Body('Description')
    #: Key and value pairs that contain template parameters
    parameters = resource.Body('Parameters', type=dict)
    #: A list of parameter groups each contains a lsit of parameter names.
    parameter_groups = resource.Body('ParameterGroups', type=list)

    def validate(self,
                 session,
                 template,
                 environment=None,
                 template_url=None,
                 ignore_errors=None):
        url = '/validate'

        body = {'template': template}
        if environment is not None:
            body['environment'] = environment
        if template_url is not None:
            body['template_url'] = template_url
        if ignore_errors:
            qry = parse.urlencode({'ignore_errors': ignore_errors})
            url = '?'.join([url, qry])

        resp = session.post(url, endpoint_filter=self.service, json=body)
        self._translate_response(resp)
        return self
Exemple #7
0
class SoftwareConfig(resource.Resource):
    resource_key = 'software_config'
    resources_key = 'software_configs'
    base_path = '/software_configs'
    service = orchestration_service.OrchestrationService()

    # capabilities
    allow_create = True
    allow_list = True
    allow_get = True
    allow_delete = True
    allow_update = False

    # Properties
    #: Configuration script or manifest that defines which configuration is
    #: performed
    config = resource.Body('config')
    #: The date and time when the software config resource was created.
    created_at = resource.Body('creation_time')
    #: A string indicating the namespace used for grouping software configs.
    group = resource.Body('group')
    #: A list of schemas each representing an input this software config
    #: expects.
    inputs = resource.Body('inputs')
    #: Name of the software config.
    name = resource.Body('name')
    #: A string that contains options that are specific to the configuraiton
    #: management tool that this resource uses.
    options = resource.Body('options')
    #: A list of schemas each representing an output this software config
    #: produces.
    outputs = resource.Body('outputs')

    def create(self, session):
        # This overrides the default behavior of resource creation because
        # heat doesn't accept resource_key in its request.
        return super(SoftwareConfig, self).create(session, prepend_key=False)
Exemple #8
0
class Stack(resource.Resource):
    name_attribute = 'stack_name'
    resource_key = 'stack'
    resources_key = 'stacks'
    base_path = '/stacks'
    service = orchestration_service.OrchestrationService()

    # capabilities
    allow_create = True
    allow_list = True
    allow_get = True
    allow_update = True
    allow_delete = True

    # Properties
    #: Placeholder for AWS compatible template listing capabilities
    #: required by the stack.
    capabilities = resource.Body('capabilities')
    #: Timestamp of the stack creation.
    created_at = resource.Body('creation_time')
    #: A text description of the stack.
    description = resource.Body('description')
    #: Whether the stack will support a rollback operation on stack
    #: create/update failures. *Type: bool*
    is_rollback_disabled = resource.Body('disable_rollback', type=bool)
    #: A list of dictionaries containing links relevant to the stack.
    links = resource.Body('links')
    #: Name of the stack.
    name = resource.Body('stack_name')
    #: Placeholder for future extensions where stack related events
    #: can be published.
    notification_topics = resource.Body('notification_topics')
    #: A list containing output keys and values from the stack, if any.
    outputs = resource.Body('outputs')
    #: The ID of the owner stack if any.
    owner_id = resource.Body('stack_owner')
    #: A dictionary containing the parameter names and values for the stack.
    parameters = resource.Body('parameters', type=dict)
    #: The ID of the parent stack if any
    parent_id = resource.Body('parent')
    #: A string representation of the stack status, e.g. ``CREATE_COMPLETE``.
    status = resource.Body('stack_status')
    #: A text explaining how the stack transits to its current status.
    status_reason = resource.Body('stack_status_reason')
    #: A dict containing the template use for stack creation.
    template = resource.Body('template', type=dict)
    #: Stack template description text. Currently contains the same text
    #: as that of the ``description`` property.
    template_description = resource.Body('template_description')
    #: A string containing the URL where a stack template can be found.
    template_url = resource.Body('template_url')
    #: Stack operation timeout in minutes.
    timeout_mins = resource.Body('timeout_mins')
    #: Timestamp of last update on the stack.
    updated_at = resource.Body('updated_time')
    #: The ID of the user project created for this stack.
    user_project_id = resource.Body('stack_user_project_id')

    def stack_prepare_request(self,
                              session,
                              requires_id=True,
                              prepend_key=False):
        """Prepare a request with auth header"""

        body = self._body.dirty
        if prepend_key and self.resource_key is not None:
            body = {self.resource_key: body}

        headers = self._header.dirty

        headers["X-Auth-User"] = session.auth._username
        headers["X-Auth-Key"] = session.auth._password

        uri = self.base_path % self._uri.attributes
        if requires_id:
            id = self._get_id(self)
            if id is None:
                raise exceptions.InvalidRequest(
                    "Request requires an ID but none was found")

            uri = utils.urljoin(uri, id)

        return resource._Request(uri, body, headers)

    def create(self, session):
        # This overrides the default behavior of resource creation because
        # heat doesn't accept resource_key in its request.
        # & Will use self.stack_prepare_request to get proper headers.
        if not self.allow_create:
            raise exceptions.MethodNotSupported(self, "create")

        if self.put_create:
            request = self.stack_prepare_request(session,
                                                 requires_id=True,
                                                 prepend_key=False)
            response = session.put(request.uri,
                                   endpoint_filter=self.service,
                                   json=request.body,
                                   headers=request.headers)
        else:
            request = self.stack_prepare_request(session,
                                                 requires_id=False,
                                                 prepend_key=False)
            response = session.post(request.uri,
                                    endpoint_filter=self.service,
                                    json=request.body,
                                    headers=request.headers)

        self._translate_response(response)
        return self

    def update(self, session):
        # This overrides the default behavior of resource creation because
        # heat doesn't accept resource_key in its request.
        return super(Stack, self).update(session,
                                         prepend_key=False,
                                         has_body=False)

    def _action(self, session, body):
        """Perform stack actions"""
        url = utils.urljoin(self.base_path, self._get_id(self), 'actions')
        resp = session.post(url, endpoint_filter=self.service, json=body)
        return resp.json()

    def check(self, session):
        return self._action(session, {'check': ''})

    def get(self, session, requires_id=True):
        stk = super(Stack, self).get(session, requires_id=requires_id)
        if stk and stk.status in ['DELETE_COMPLETE', 'ADOPT_COMPLETE']:
            raise exceptions.NotFoundException("No stack found for %s" %
                                               stk.id)
        return stk

    def abandon(self, session):
        self.base_path = '/stacks/%s/%s/abandon' % (self.name, self.id)

        if not self.allow_delete:
            raise exceptions.MethodNotSupported(self, "delete")

        request = self._prepare_request(requires_id=False)

        response = session.delete(request.uri,
                                  endpoint_filter=self.service,
                                  headers={"Accept": ""})

        self._translate_response(response, has_body=False)
        return self