# coding=utf-8
# --------------------------------------------------------------------------
# Copyright (c) Microsoft Corporation. All rights reserved.
# Licensed under the MIT License. See License.txt in the project root for
# license information.
#
# Code generated by Microsoft (R) AutoRest Code Generator.
# Changes may cause incorrect behavior and will be lost if the code is
# regenerated.
# --------------------------------------------------------------------------

import uuid
from msrest.pipeline import ClientRawResponse
from msrestazure.azure_exceptions import CloudError
from msrest.polling import LROPoller, NoPolling
from msrestazure.polling.arm_polling import ARMPolling

from .. import models

class GlobalUsersOperations(object):
    """GlobalUsersOperations operations.

    :param client: Client for service requests.
    :param config: Configuration of service client.
    :param serializer: An object model serializer.
    :param deserializer: An object model deserializer.
    :ivar api_version: Client API version. Constant value: "2018-10-15".
    """

    models = models

    def __init__(self, client, config, serializer, deserializer):

        self._client = client
        self._serialize = serializer
        self._deserialize = deserializer
        self.api_version = "2018-10-15"

        self.config = config

    def get_environment(
            self, user_name, environment_id, expand=None, custom_headers=None, raw=False, **operation_config):
        """Gets the virtual machine details.

        :param user_name: The name of the user.
        :type user_name: str
        :param environment_id: The resourceId of the environment
        :type environment_id: str
        :param expand: Specify the $expand query. Example:
         'properties($expand=environment)'
        :type expand: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: GetEnvironmentResponse or ClientRawResponse if raw=true
        :rtype: ~azure.mgmt.labservices.models.GetEnvironmentResponse or
         ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        environment_operations_payload = models.EnvironmentOperationsPayload(environment_id=environment_id)

        # Construct URL
        url = self.get_environment.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        if expand is not None:
            query_parameters['$expand'] = self._serialize.query("expand", expand, 'str')
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Accept'] = 'application/json'
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(environment_operations_payload, 'EnvironmentOperationsPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        deserialized = None

        if response.status_code == 200:
            deserialized = self._deserialize('GetEnvironmentResponse', response)

        if raw:
            client_raw_response = ClientRawResponse(deserialized, response)
            return client_raw_response

        return deserialized
    get_environment.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/getEnvironment'}

    def get_operation_batch_status(
            self, user_name, urls, custom_headers=None, raw=False, **operation_config):
        """Get batch operation status.

        :param user_name: The name of the user.
        :type user_name: str
        :param urls: The operation url of long running operation
        :type urls: list[str]
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: OperationBatchStatusResponse or ClientRawResponse if raw=true
        :rtype: ~azure.mgmt.labservices.models.OperationBatchStatusResponse or
         ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        operation_batch_status_payload = models.OperationBatchStatusPayload(urls=urls)

        # Construct URL
        url = self.get_operation_batch_status.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Accept'] = 'application/json'
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(operation_batch_status_payload, 'OperationBatchStatusPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        deserialized = None

        if response.status_code == 200:
            deserialized = self._deserialize('OperationBatchStatusResponse', response)

        if raw:
            client_raw_response = ClientRawResponse(deserialized, response)
            return client_raw_response

        return deserialized
    get_operation_batch_status.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/getOperationBatchStatus'}

    def get_operation_status(
            self, user_name, operation_url, custom_headers=None, raw=False, **operation_config):
        """Gets the status of long running operation.

        :param user_name: The name of the user.
        :type user_name: str
        :param operation_url: The operation url of long running operation
        :type operation_url: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: OperationStatusResponse or ClientRawResponse if raw=true
        :rtype: ~azure.mgmt.labservices.models.OperationStatusResponse or
         ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        operation_status_payload = models.OperationStatusPayload(operation_url=operation_url)

        # Construct URL
        url = self.get_operation_status.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Accept'] = 'application/json'
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(operation_status_payload, 'OperationStatusPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        deserialized = None

        if response.status_code == 200:
            deserialized = self._deserialize('OperationStatusResponse', response)

        if raw:
            client_raw_response = ClientRawResponse(deserialized, response)
            return client_raw_response

        return deserialized
    get_operation_status.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/getOperationStatus'}

    def get_personal_preferences(
            self, user_name, personal_preferences_operations_payload, custom_headers=None, raw=False, **operation_config):
        """Get personal preferences for a user.

        :param user_name: The name of the user.
        :type user_name: str
        :param personal_preferences_operations_payload: Represents payload for
         any Environment operations like get, start, stop, connect
        :type personal_preferences_operations_payload:
         ~azure.mgmt.labservices.models.PersonalPreferencesOperationsPayload
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: GetPersonalPreferencesResponse or ClientRawResponse if
         raw=true
        :rtype: ~azure.mgmt.labservices.models.GetPersonalPreferencesResponse
         or ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        # Construct URL
        url = self.get_personal_preferences.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Accept'] = 'application/json'
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(personal_preferences_operations_payload, 'PersonalPreferencesOperationsPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        deserialized = None

        if response.status_code == 200:
            deserialized = self._deserialize('GetPersonalPreferencesResponse', response)

        if raw:
            client_raw_response = ClientRawResponse(deserialized, response)
            return client_raw_response

        return deserialized
    get_personal_preferences.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/getPersonalPreferences'}

    def list_environments(
            self, user_name, lab_id=None, custom_headers=None, raw=False, **operation_config):
        """List Environments for the user.

        :param user_name: The name of the user.
        :type user_name: str
        :param lab_id: The resource Id of the lab
        :type lab_id: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: ListEnvironmentsResponse or ClientRawResponse if raw=true
        :rtype: ~azure.mgmt.labservices.models.ListEnvironmentsResponse or
         ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        list_environments_payload = models.ListEnvironmentsPayload(lab_id=lab_id)

        # Construct URL
        url = self.list_environments.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Accept'] = 'application/json'
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(list_environments_payload, 'ListEnvironmentsPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        deserialized = None

        if response.status_code == 200:
            deserialized = self._deserialize('ListEnvironmentsResponse', response)

        if raw:
            client_raw_response = ClientRawResponse(deserialized, response)
            return client_raw_response

        return deserialized
    list_environments.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/listEnvironments'}

    def list_labs(
            self, user_name, custom_headers=None, raw=False, **operation_config):
        """List labs for the user.

        :param user_name: The name of the user.
        :type user_name: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: ListLabsResponse or ClientRawResponse if raw=true
        :rtype: ~azure.mgmt.labservices.models.ListLabsResponse or
         ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        # Construct URL
        url = self.list_labs.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Accept'] = 'application/json'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        deserialized = None

        if response.status_code == 200:
            deserialized = self._deserialize('ListLabsResponse', response)

        if raw:
            client_raw_response = ClientRawResponse(deserialized, response)
            return client_raw_response

        return deserialized
    list_labs.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/listLabs'}

    def register(
            self, user_name, registration_code=None, custom_headers=None, raw=False, **operation_config):
        """Register a user to a managed lab.

        :param user_name: The name of the user.
        :type user_name: str
        :param registration_code: The registration code of the lab.
        :type registration_code: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: returns the direct response alongside the
         deserialized response
        :param operation_config: :ref:`Operation configuration
         overrides<msrest:optionsforoperations>`.
        :return: None or ClientRawResponse if raw=true
        :rtype: None or ~msrest.pipeline.ClientRawResponse
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        register_payload = models.RegisterPayload(registration_code=registration_code)

        # Construct URL
        url = self.register.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(register_payload, 'RegisterPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        if raw:
            client_raw_response = ClientRawResponse(None, response)
            return client_raw_response
    register.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/register'}

    def _reset_password_initial(
            self, user_name, reset_password_payload, custom_headers=None, raw=False, **operation_config):
        # Construct URL
        url = self.reset_password.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(reset_password_payload, 'ResetPasswordPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200, 202]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        if raw:
            client_raw_response = ClientRawResponse(None, response)
            return client_raw_response

    def reset_password(
            self, user_name, reset_password_payload, custom_headers=None, raw=False, polling=True, **operation_config):
        """Resets the user password on an environment This operation can take a
        while to complete.

        :param user_name: The name of the user.
        :type user_name: str
        :param reset_password_payload: Represents the payload for resetting
         passwords.
        :type reset_password_payload:
         ~azure.mgmt.labservices.models.ResetPasswordPayload
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: The poller return type is ClientRawResponse, the
         direct response alongside the deserialized response
        :param polling: True for ARMPolling, False for no polling, or a
         polling object for personal polling strategy
        :return: An instance of LROPoller that returns None or
         ClientRawResponse<None> if raw==True
        :rtype: ~msrestazure.azure_operation.AzureOperationPoller[None] or
         ~msrestazure.azure_operation.AzureOperationPoller[~msrest.pipeline.ClientRawResponse[None]]
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        raw_result = self._reset_password_initial(
            user_name=user_name,
            reset_password_payload=reset_password_payload,
            custom_headers=custom_headers,
            raw=True,
            **operation_config
        )

        def get_long_running_output(response):
            if raw:
                client_raw_response = ClientRawResponse(None, response)
                return client_raw_response

        lro_delay = operation_config.get(
            'long_running_operation_timeout',
            self.config.long_running_operation_timeout)
        if polling is True: polling_method = ARMPolling(lro_delay, **operation_config)
        elif polling is False: polling_method = NoPolling()
        else: polling_method = polling
        return LROPoller(self._client, raw_result, get_long_running_output, polling_method)
    reset_password.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/resetPassword'}

    def _start_environment_initial(
            self, user_name, environment_id, custom_headers=None, raw=False, **operation_config):
        environment_operations_payload = models.EnvironmentOperationsPayload(environment_id=environment_id)

        # Construct URL
        url = self.start_environment.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(environment_operations_payload, 'EnvironmentOperationsPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200, 202]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        if raw:
            client_raw_response = ClientRawResponse(None, response)
            return client_raw_response

    def start_environment(
            self, user_name, environment_id, custom_headers=None, raw=False, polling=True, **operation_config):
        """Starts an environment by starting all resources inside the environment.
        This operation can take a while to complete.

        :param user_name: The name of the user.
        :type user_name: str
        :param environment_id: The resourceId of the environment
        :type environment_id: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: The poller return type is ClientRawResponse, the
         direct response alongside the deserialized response
        :param polling: True for ARMPolling, False for no polling, or a
         polling object for personal polling strategy
        :return: An instance of LROPoller that returns None or
         ClientRawResponse<None> if raw==True
        :rtype: ~msrestazure.azure_operation.AzureOperationPoller[None] or
         ~msrestazure.azure_operation.AzureOperationPoller[~msrest.pipeline.ClientRawResponse[None]]
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        raw_result = self._start_environment_initial(
            user_name=user_name,
            environment_id=environment_id,
            custom_headers=custom_headers,
            raw=True,
            **operation_config
        )

        def get_long_running_output(response):
            if raw:
                client_raw_response = ClientRawResponse(None, response)
                return client_raw_response

        lro_delay = operation_config.get(
            'long_running_operation_timeout',
            self.config.long_running_operation_timeout)
        if polling is True: polling_method = ARMPolling(lro_delay, **operation_config)
        elif polling is False: polling_method = NoPolling()
        else: polling_method = polling
        return LROPoller(self._client, raw_result, get_long_running_output, polling_method)
    start_environment.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/startEnvironment'}

    def _stop_environment_initial(
            self, user_name, environment_id, custom_headers=None, raw=False, **operation_config):
        environment_operations_payload = models.EnvironmentOperationsPayload(environment_id=environment_id)

        # Construct URL
        url = self.stop_environment.metadata['url']
        path_format_arguments = {
            'userName': self._serialize.url("user_name", user_name, 'str')
        }
        url = self._client.format_url(url, **path_format_arguments)

        # Construct parameters
        query_parameters = {}
        query_parameters['api-version'] = self._serialize.query("self.api_version", self.api_version, 'str')

        # Construct headers
        header_parameters = {}
        header_parameters['Content-Type'] = 'application/json; charset=utf-8'
        if self.config.generate_client_request_id:
            header_parameters['x-ms-client-request-id'] = str(uuid.uuid1())
        if custom_headers:
            header_parameters.update(custom_headers)
        if self.config.accept_language is not None:
            header_parameters['accept-language'] = self._serialize.header("self.config.accept_language", self.config.accept_language, 'str')

        # Construct body
        body_content = self._serialize.body(environment_operations_payload, 'EnvironmentOperationsPayload')

        # Construct and send request
        request = self._client.post(url, query_parameters, header_parameters, body_content)
        response = self._client.send(request, stream=False, **operation_config)

        if response.status_code not in [200, 202]:
            exp = CloudError(response)
            exp.request_id = response.headers.get('x-ms-request-id')
            raise exp

        if raw:
            client_raw_response = ClientRawResponse(None, response)
            return client_raw_response

    def stop_environment(
            self, user_name, environment_id, custom_headers=None, raw=False, polling=True, **operation_config):
        """Stops an environment by stopping all resources inside the environment
        This operation can take a while to complete.

        :param user_name: The name of the user.
        :type user_name: str
        :param environment_id: The resourceId of the environment
        :type environment_id: str
        :param dict custom_headers: headers that will be added to the request
        :param bool raw: The poller return type is ClientRawResponse, the
         direct response alongside the deserialized response
        :param polling: True for ARMPolling, False for no polling, or a
         polling object for personal polling strategy
        :return: An instance of LROPoller that returns None or
         ClientRawResponse<None> if raw==True
        :rtype: ~msrestazure.azure_operation.AzureOperationPoller[None] or
         ~msrestazure.azure_operation.AzureOperationPoller[~msrest.pipeline.ClientRawResponse[None]]
        :raises: :class:`CloudError<msrestazure.azure_exceptions.CloudError>`
        """
        raw_result = self._stop_environment_initial(
            user_name=user_name,
            environment_id=environment_id,
            custom_headers=custom_headers,
            raw=True,
            **operation_config
        )

        def get_long_running_output(response):
            if raw:
                client_raw_response = ClientRawResponse(None, response)
                return client_raw_response

        lro_delay = operation_config.get(
            'long_running_operation_timeout',
            self.config.long_running_operation_timeout)
        if polling is True: polling_method = ARMPolling(lro_delay, **operation_config)
        elif polling is False: polling_method = NoPolling()
        else: polling_method = polling
        return LROPoller(self._client, raw_result, get_long_running_output, polling_method)
    stop_environment.metadata = {'url': '/providers/Microsoft.LabServices/users/{userName}/stopEnvironment'}


# coding=utf-8
# --------------------------------------------------------------------------
# Copyright (c) Microsoft Corporation. All rights reserved.
# Licensed under the MIT License. See License.txt in the project root for
# license information.
#
# Code generated by Microsoft (R) AutoRest Code Generator.
# Changes may cause incorrect behavior and will be lost if the code is
# regenerated.
# --------------------------------------------------------------------------

from msrest.service_client import SDKClient
from msrest import Serializer, Deserializer
from msrestazure import AzureConfiguration

from azure.profiles import KnownProfiles, ProfileDefinition
from azure.profiles.multiapiclient import MultiApiClientMixin
from .version import VERSION

class ContainerRegistryManagementClientConfiguration(AzureConfiguration):
    """Configuration for ContainerRegistryManagementClient
    Note that all parameters used to create this instance are saved as instance
    attributes.

    :param credentials: Credentials needed for the client to connect to Azure.
    :type credentials: :mod:`A msrestazure Credentials
     object<msrestazure.azure_active_directory>`
    :param subscription_id: The Microsoft Azure subscription ID.
    :type subscription_id: str
    :param str base_url: Service URL
    """

    def __init__(
            self, credentials, subscription_id, base_url=None):

        if credentials is None:
            raise ValueError("Parameter 'credentials' must not be None.")
        if subscription_id is None:
            raise ValueError("Parameter 'subscription_id' must not be None.")
        if not base_url:
            base_url = 'https://management.azure.com'

        super(ContainerRegistryManagementClientConfiguration, self).__init__(base_url)

        self.add_user_agent('containerregistrymanagementclient/{}'.format(VERSION))
        self.add_user_agent('Azure-SDK-For-Python')

        self.credentials = credentials
        self.subscription_id = subscription_id

class ContainerRegistryManagementClient(MultiApiClientMixin, SDKClient):
    """ContainerRegistryManagementClient

    :ivar config: Configuration for client.
    :vartype config: ContainerRegistryManagementClientConfiguration

    :param credentials: Credentials needed for the client to connect to Azure.
    :type credentials: :mod:`A msrestazure Credentials
     object<msrestazure.azure_active_directory>`
    :param subscription_id: The Microsoft Azure subscription ID.
    :type subscription_id: str
    :param str api_version: API version to use if no profile is provided, or if
     missing in profile.
    :param str base_url: Service URL
    :param profile: A dict using operation group name to API version.
    :type profile: dict[str, str]    """

    DEFAULT_API_VERSION = '2018-09-01'
    _PROFILE_TAG = "azure.mgmt.containerregistry.ContainerRegistryManagementClient"
    LATEST_PROFILE = ProfileDefinition({
        _PROFILE_TAG: {
            None: DEFAULT_API_VERSION
        }},
        _PROFILE_TAG + " latest"
    )

    def __init__(self, credentials, subscription_id, api_version=None, base_url=None, profile=KnownProfiles.default):
        self.config = ContainerRegistryManagementClientConfiguration(credentials, subscription_id, base_url)
        super(ContainerRegistryManagementClient, self).__init__(
            credentials,
            self.config,
            api_version=api_version,
            profile=profile
        )

############ Generated from here ############

    @classmethod
    def _models_dict(cls, api_version):
        return {k: v for k, v in cls.models(api_version).__dict__.items() if isinstance(v, type)}

    @classmethod
    def models(cls, api_version=DEFAULT_API_VERSION):
        """Module depends on the API version:

           * 2017-03-01: :mod:`v2017_03_01.models<azure.mgmt.containerregistry.v2017_03_01.models>`
           * 2017-10-01: :mod:`v2017_10_01.models<azure.mgmt.containerregistry.v2017_10_01.models>`
           * 2018-02-01-preview: :mod:`v2018_02_01_preview.models<azure.mgmt.containerregistry.v2018_02_01_preview.models>`
           * 2018-09-01: :mod:`v2018_09_01.models<azure.mgmt.containerregistry.v2018_09_01.models>`
        """
        if api_version == '2017-03-01':
            from .v2017_03_01 import models
            return models
        elif api_version == '2017-10-01':
            from .v2017_10_01 import models
            return models
        elif api_version == '2018-02-01-preview':
            from .v2018_02_01_preview import models
            return models
        elif api_version == '2018-09-01':
            from .v2018_09_01 import models
            return models
        raise NotImplementedError("APIVersion {} is not available".format(api_version))

    @property
    def build_steps(self):
        """Instance depends on the API version:

           * 2018-02-01-preview: :class:`BuildStepsOperations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.BuildStepsOperations>`
        """
        api_version = self._get_api_version('build_steps')
        if api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import BuildStepsOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def build_tasks(self):
        """Instance depends on the API version:

           * 2018-02-01-preview: :class:`BuildTasksOperations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.BuildTasksOperations>`
        """
        api_version = self._get_api_version('build_tasks')
        if api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import BuildTasksOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def builds(self):
        """Instance depends on the API version:

           * 2018-02-01-preview: :class:`BuildsOperations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.BuildsOperations>`
        """
        api_version = self._get_api_version('builds')
        if api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import BuildsOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def operations(self):
        """Instance depends on the API version:

           * 2017-03-01: :class:`Operations<azure.mgmt.containerregistry.v2017_03_01.operations.Operations>`
           * 2017-10-01: :class:`Operations<azure.mgmt.containerregistry.v2017_10_01.operations.Operations>`
           * 2018-02-01-preview: :class:`Operations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.Operations>`
           * 2018-09-01: :class:`Operations<azure.mgmt.containerregistry.v2018_09_01.operations.Operations>`
        """
        api_version = self._get_api_version('operations')
        if api_version == '2017-03-01':
            from .v2017_03_01.operations import Operations as OperationClass
        elif api_version == '2017-10-01':
            from .v2017_10_01.operations import Operations as OperationClass
        elif api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import Operations as OperationClass
        elif api_version == '2018-09-01':
            from .v2018_09_01.operations import Operations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def registries(self):
        """Instance depends on the API version:

           * 2017-03-01: :class:`RegistriesOperations<azure.mgmt.containerregistry.v2017_03_01.operations.RegistriesOperations>`
           * 2017-10-01: :class:`RegistriesOperations<azure.mgmt.containerregistry.v2017_10_01.operations.RegistriesOperations>`
           * 2018-02-01-preview: :class:`RegistriesOperations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.RegistriesOperations>`
           * 2018-09-01: :class:`RegistriesOperations<azure.mgmt.containerregistry.v2018_09_01.operations.RegistriesOperations>`
        """
        api_version = self._get_api_version('registries')
        if api_version == '2017-03-01':
            from .v2017_03_01.operations import RegistriesOperations as OperationClass
        elif api_version == '2017-10-01':
            from .v2017_10_01.operations import RegistriesOperations as OperationClass
        elif api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import RegistriesOperations as OperationClass
        elif api_version == '2018-09-01':
            from .v2018_09_01.operations import RegistriesOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def replications(self):
        """Instance depends on the API version:

           * 2017-10-01: :class:`ReplicationsOperations<azure.mgmt.containerregistry.v2017_10_01.operations.ReplicationsOperations>`
           * 2018-02-01-preview: :class:`ReplicationsOperations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.ReplicationsOperations>`
           * 2018-09-01: :class:`ReplicationsOperations<azure.mgmt.containerregistry.v2018_09_01.operations.ReplicationsOperations>`
        """
        api_version = self._get_api_version('replications')
        if api_version == '2017-10-01':
            from .v2017_10_01.operations import ReplicationsOperations as OperationClass
        elif api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import ReplicationsOperations as OperationClass
        elif api_version == '2018-09-01':
            from .v2018_09_01.operations import ReplicationsOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def runs(self):
        """Instance depends on the API version:

           * 2018-09-01: :class:`RunsOperations<azure.mgmt.containerregistry.v2018_09_01.operations.RunsOperations>`
        """
        api_version = self._get_api_version('runs')
        if api_version == '2018-09-01':
            from .v2018_09_01.operations import RunsOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def tasks(self):
        """Instance depends on the API version:

           * 2018-09-01: :class:`TasksOperations<azure.mgmt.containerregistry.v2018_09_01.operations.TasksOperations>`
        """
        api_version = self._get_api_version('tasks')
        if api_version == '2018-09-01':
            from .v2018_09_01.operations import TasksOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))

    @property
    def webhooks(self):
        """Instance depends on the API version:

           * 2017-10-01: :class:`WebhooksOperations<azure.mgmt.containerregistry.v2017_10_01.operations.WebhooksOperations>`
           * 2018-02-01-preview: :class:`WebhooksOperations<azure.mgmt.containerregistry.v2018_02_01_preview.operations.WebhooksOperations>`
           * 2018-09-01: :class:`WebhooksOperations<azure.mgmt.containerregistry.v2018_09_01.operations.WebhooksOperations>`
        """
        api_version = self._get_api_version('webhooks')
        if api_version == '2017-10-01':
            from .v2017_10_01.operations import WebhooksOperations as OperationClass
        elif api_version == '2018-02-01-preview':
            from .v2018_02_01_preview.operations import WebhooksOperations as OperationClass
        elif api_version == '2018-09-01':
            from .v2018_09_01.operations import WebhooksOperations as OperationClass
        else:
            raise NotImplementedError("APIVersion {} is not available".format(api_version))
        return OperationClass(self._client, self.config, Serializer(self._models_dict(api_version)), Deserializer(self._models_dict(api_version)))


# ------------------------------------------------------------------------
# Copyright (c) Microsoft Corporation. All rights reserved.
# Licensed under the MIT License. See License.txt in the project root for
# license information.
# -------------------------------------------------------------------------

import json
from datetime import datetime
from .models import (
    AzureServiceBusResourceNotFound,
    Queue,
    Topic,
    Subscription,
    Rule,
    EventHub,
    AuthorizationRule,
    Message)
from ._common_conversion import _lower
from ._common_serialization import (
    _XmlWriter,
    _make_etree_ns_attr_name,
    _get_etree_text,
    ETree,
    _ETreeXmlToObject)
from ._common_error import (
    _ERROR_EVENT_HUB_NOT_FOUND,
    _ERROR_QUEUE_NOT_FOUND,
    _ERROR_TOPIC_NOT_FOUND,
    _general_error_handler)

class _XmlSchemas:  # pylint: disable=too-few-public-methods
    SchemaInstance = 'http://www.w3.org/2001/XMLSchema-instance'
    SerializationArrays = 'http://schemas.microsoft.com/2003/10/Serialization/Arrays'
    ServiceBus = 'http://schemas.microsoft.com/netservices/2010/10/servicebus/connect'
    DataServices = 'http://schemas.microsoft.com/ado/2007/08/dataservices'
    DataServicesMetadata = 'http://schemas.microsoft.com/ado/2007/08/dataservices/metadata'
    Atom = 'http://www.w3.org/2005/Atom'

def _create_message(response, service_instance):
    ''' Create message from response.

    response:
        response from Service Bus cloud server.
    service_instance:
        the Service Bus client.
    '''
    respbody = response.body
    custom_properties = {}
    broker_properties = None
    message_type = None
    message_location = None

    # gets all information from respheaders.
    for name, value in response.headers:
        if name.lower() == 'brokerproperties':
            broker_properties = json.loads(value)
        elif name.lower() == 'content-type':
            message_type = value
        elif name.lower() == 'location':
            message_location = value
        # Exclude common HTTP headers to avoid noise. List
        # is not exhaustive. At worst, custom properties will contains
        # an unexpected content generated by the webserver and not the customer.
        elif name.lower() not in ['transfer-encoding',
                                  'server',
                                  'date',
                                  'strict-transport-security']:
            # Follow the spec:
            # https://docs.microsoft.com/rest/api/servicebus/message-headers-and-properties
            if '"' in value:
                value = value[1:-1].replace('\\"', '"')
                try:
                    custom_properties[name] = datetime.strptime(
                        value, '%a, %d %b %Y %H:%M:%S GMT')
                except ValueError:
                    custom_properties[name] = value
            elif value.lower() == 'true':
                custom_properties[name] = True
            elif value.lower() == 'false':
                custom_properties[name] = False
            else:  # in theory, only int or float
                try:
                    # int('3.1') doesn't work so need to get float('3.14') first
                    float_value = float(value)
                    if str(int(float_value)) == value:
                        custom_properties[name] = int(value)
                    else:
                        custom_properties[name] = float_value
                except ValueError:
                    # If we are here, this header does not respect the spec.
                    # Could be an unexpected HTTP header or an invalid
                    # header value. In both case we ignore without failing.
                    pass

    if message_type is None:
        message = Message(
            respbody, service_instance, message_location, custom_properties,
            'application/atom+xml;type=entry;charset=utf-8', broker_properties)
    else:
        message = Message(respbody, service_instance, message_location,
                          custom_properties, message_type, broker_properties)
    return message

# convert functions

_etree_sb_feed_namespaces = {
    'atom': _XmlSchemas.Atom,
    'i': _XmlSchemas.SchemaInstance,
    'sb': _XmlSchemas.ServiceBus,
    'arrays': _XmlSchemas.SerializationArrays,
}

def _convert_response_to_rule(response):
    root = ETree.fromstring(response.body)
    return _convert_etree_element_to_rule(root)

def _convert_etree_element_to_rule(entry_element):
    ''' Converts entry element to rule object.

    The format of xml for rule:
<entry xmlns='http://www.w3.org/2005/Atom'>
<content type='application/xml'>
<RuleDescription
    xmlns:i="http://www.w3.org/2001/XMLSchema-instance"
    xmlns="http://schemas.microsoft.com/netservices/2010/10/servicebus/connect">
    <Filter i:type="SqlFilterExpression">
        <SqlExpression>MyProperty='XYZ'</SqlExpression>
    </Filter>
    <Action i:type="SqlFilterAction">
        <SqlExpression>set MyProperty2 = 'ABC'</SqlExpression>
    </Action>
</RuleDescription>
</content>
</entry>
    '''
    rule = Rule()

    rule_element = entry_element.find('./atom:content/sb:RuleDescription', _etree_sb_feed_namespaces)
    if rule_element is not None:
        filter_element = rule_element.find('./sb:Filter', _etree_sb_feed_namespaces)
        if filter_element is not None:
            rule.filter_type = filter_element.attrib.get(
                _make_etree_ns_attr_name(_etree_sb_feed_namespaces['i'], 'type'), None)
            sql_exp_element = filter_element.find('./sb:SqlExpression', _etree_sb_feed_namespaces)
            if sql_exp_element is not None:
                rule.filter_expression = sql_exp_element.text

        action_element = rule_element.find('./sb:Action', _etree_sb_feed_namespaces)
        if action_element is not None:
            rule.action_type = action_element.attrib.get(
                _make_etree_ns_attr_name(_etree_sb_feed_namespaces['i'], 'type'), None)
            sql_exp_element = action_element.find('./sb:SqlExpression', _etree_sb_feed_namespaces)
            if sql_exp_element is not None:
                rule.action_expression = sql_exp_element.text

    # extract id, updated and name value from feed entry and set them of rule.
    for name, value in _ETreeXmlToObject.get_entry_properties_from_element(
            entry_element, True, '/rules').items():
        setattr(rule, name, value)

    return rule

def _convert_response_to_queue(response):
    root = ETree.fromstring(response.body)
    return _convert_etree_element_to_queue(root)

def _convert_response_to_event_hub(response):
    root = ETree.fromstring(response.body)
    return _convert_etree_element_to_event_hub(root)

def _parse_bool(value):
    if value.lower() == 'true':
        return True
    return False

def _read_etree_element(parent_element, child_element_name, target_object, target_field_name, converter):
    child_element = parent_element.find('./sb:{0}'.format(child_element_name), _etree_sb_feed_namespaces)
    if child_element is not None:
        field_value = _get_etree_text(child_element)
        if converter is not None:
            field_value = converter(field_value)
        setattr(target_object, target_field_name, field_value)
        return True
    return False

def _convert_etree_element_to_queue(entry_element):
    ''' Converts entry element to queue object.

    The format of xml response for queue:
<QueueDescription
    xmlns=\"http://schemas.microsoft.com/netservices/2010/10/servicebus/connect\">
    <MaxSizeInBytes>10000</MaxSizeInBytes>
    <DefaultMessageTimeToLive>PT5M</DefaultMessageTimeToLive>
    <LockDuration>PT2M</LockDuration>
    <RequiresGroupedReceives>False</RequiresGroupedReceives>
    <SupportsDuplicateDetection>False</SupportsDuplicateDetection>
    ...
</QueueDescription>

    '''
    queue = Queue()

    # get node for each attribute in Queue class, if nothing found then the
    # response is not valid xml for Queue.
    invalid_queue = True

    queue_element = entry_element.find('./atom:content/sb:QueueDescription', _etree_sb_feed_namespaces)
    if queue_element is not None:
        mappings = [
            ('LockDuration', 'lock_duration', None),
            ('MaxSizeInMegabytes', 'max_size_in_megabytes', int),
            ('RequiresDuplicateDetection', 'requires_duplicate_detection', _parse_bool),
            ('RequiresSession', 'requires_session', _parse_bool),
            ('DefaultMessageTimeToLive', 'default_message_time_to_live', None),
            ('DeadLetteringOnMessageExpiration', 'dead_lettering_on_message_expiration', _parse_bool),
            ('DuplicateDetectionHistoryTimeWindow', 'duplicate_detection_history_time_window', None),
            ('EnableBatchedOperations', 'enable_batched_operations', _parse_bool),
            ('MaxDeliveryCount', 'max_delivery_count', int),
            ('MessageCount', 'message_count', int),
            ('SizeInBytes', 'size_in_bytes', int),
        ]

        for mapping in mappings:
            if _read_etree_element(queue_element, mapping[0], queue, mapping[1], mapping[2]):
                invalid_queue = False

    if invalid_queue:
        raise AzureServiceBusResourceNotFound(_ERROR_QUEUE_NOT_FOUND)

    # extract id, updated and name value from feed entry and set them of queue.
    for name, value in _ETreeXmlToObject.get_entry_properties_from_element(
            entry_element, True).items():
        setattr(queue, name, value)

    return queue

def _convert_response_to_topic(response):
    root = ETree.fromstring(response.body)
    return _convert_etree_element_to_topic(root)

def _convert_etree_element_to_topic(entry_element):
    '''Converts entry element to topic

    The xml format for topic:
<entry xmlns='http://www.w3.org/2005/Atom'>
    <content type='application/xml'>
    <TopicDescription
        xmlns:i="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://schemas.microsoft.com/netservices/2010/10/servicebus/connect">
        <DefaultMessageTimeToLive>P10675199DT2H48M5.4775807S</DefaultMessageTimeToLive>
        <MaxSizeInMegabytes>1024</MaxSizeInMegabytes>
        <RequiresDuplicateDetection>false</RequiresDuplicateDetection>
        <DuplicateDetectionHistoryTimeWindow>P7D</DuplicateDetectionHistoryTimeWindow>
        <DeadLetteringOnFilterEvaluationExceptions>true</DeadLetteringOnFilterEvaluationExceptions>
    </TopicDescription>
    </content>
</entry>
    '''
    topic = Topic()

    invalid_topic = True

    topic_element = entry_element.find('./atom:content/sb:TopicDescription', _etree_sb_feed_namespaces)
    if topic_element is not None:
        mappings = [
            ('DefaultMessageTimeToLive', 'default_message_time_to_live', None),
            ('MaxSizeInMegabytes', 'max_size_in_megabytes', int),
            ('RequiresDuplicateDetection', 'requires_duplicate_detection', _parse_bool),
            ('DuplicateDetectionHistoryTimeWindow', 'duplicate_detection_history_time_window', None),
            ('EnableBatchedOperations', 'enable_batched_operations', _parse_bool),
            ('SizeInBytes', 'size_in_bytes', int),
        ]

        for mapping in mappings:
            if _read_etree_element(topic_element, mapping[0], topic, mapping[1], mapping[2]):
                invalid_topic = False

    if invalid_topic:
        raise AzureServiceBusResourceNotFound(_ERROR_TOPIC_NOT_FOUND)

    # extract id, updated and name value from feed entry and set them of topic.
    for name, value in _ETreeXmlToObject.get_entry_properties_from_element(
            entry_element, True).items():
        setattr(topic, name, value)

    return topic

def _convert_response_to_subscription(response):
    root = ETree.fromstring(response.body)
    return _convert_etree_element_to_subscription(root)

def _convert_etree_element_to_subscription(entry_element):
    '''Converts entry element to subscription

    The xml format for subscription:
<entry xmlns='http://www.w3.org/2005/Atom'>
    <content type='application/xml'>
    <SubscriptionDescription
        xmlns:i="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://schemas.microsoft.com/netservices/2010/10/servicebus/connect">
        <LockDuration>PT5M</LockDuration>
        <RequiresSession>false</RequiresSession>
        <DefaultMessageTimeToLive>P10675199DT2H48M5.4775807S</DefaultMessageTimeToLive>
        <DeadLetteringOnMessageExpiration>false</DeadLetteringOnMessageExpiration>
        <DeadLetteringOnFilterEvaluationExceptions>true</DeadLetteringOnFilterEvaluationExceptions>
    </SubscriptionDescription>
    </content>
</entry>
    '''
    subscription = Subscription()

    subscription_element = entry_element.find('./atom:content/sb:SubscriptionDescription', _etree_sb_feed_namespaces)
    if subscription_element is not None:
        mappings = [
            ('LockDuration', 'lock_duration', None),
            ('RequiresSession', 'requires_session', _parse_bool),
            ('DefaultMessageTimeToLive', 'default_message_time_to_live', None),
            ('DeadLetteringOnFilterEvaluationExceptions', 'dead_lettering_on_filter_evaluation_exceptions', _parse_bool),  # pylint: disable=line-too-long
            ('DeadLetteringOnMessageExpiration', 'dead_lettering_on_message_expiration', _parse_bool),
            ('EnableBatchedOperations', 'enable_batched_operations', _parse_bool),
            ('MaxDeliveryCount', 'max_delivery_count', int),
            ('MessageCount', 'message_count', int),
        ]

        for mapping in mappings:
            _read_etree_element(subscription_element, mapping[0], subscription, mapping[1], mapping[2])

    for name, value in _ETreeXmlToObject.get_entry_properties_from_element(
            entry_element, True, '/subscriptions').items():
        setattr(subscription, name, value)

    return subscription

def _convert_etree_element_to_event_hub(entry_element):
    hub = EventHub()

    invalid_event_hub = True
    # get node for each attribute in EventHub class, if nothing found then the
    # response is not valid xml for EventHub.

    hub_element = entry_element.find('./atom:content/sb:EventHubDescription', _etree_sb_feed_namespaces)
    if hub_element is not None:  # pylint: disable=too-many-nested-blocks
        mappings = [
            ('SizeInBytes', 'size_in_bytes', int),
            ('MessageRetentionInDays', 'message_retention_in_days', int),
            ('Status', 'status', None),
            ('UserMetadata', 'user_metadata', None),
            ('PartitionCount', 'partition_count', int),
            ('EntityAvailableStatus', 'entity_available_status', None),
        ]

        for mapping in mappings:
            if _read_etree_element(hub_element, mapping[0], hub, mapping[1], mapping[2]):
                invalid_event_hub = False

        ids = hub_element.find('./sb:PartitionIds', _etree_sb_feed_namespaces)
        if ids is not None:
            for id_node in ids.findall('./arrays:string', _etree_sb_feed_namespaces):
                value = _get_etree_text(id_node)
                if value:
                    hub.partition_ids.append(value)

        rules_nodes = hub_element.find('./sb:AuthorizationRules', _etree_sb_feed_namespaces)
        if rules_nodes is not None:
            invalid_event_hub = False
            for rule_node in rules_nodes.findall('./sb:AuthorizationRule', _etree_sb_feed_namespaces):
                rule = AuthorizationRule()

                mappings = [
                    ('ClaimType', 'claim_type', None),
                    ('ClaimValue', 'claim_value', None),
                    ('ModifiedTime', 'modified_time', None),
                    ('CreatedTime', 'created_time', None),
                    ('KeyName', 'key_name', None),
                    ('PrimaryKey', 'primary_key', None),
                    ('SecondaryKey', 'secondary_key', None),
                ]

                for mapping in mappings:
                    _read_etree_element(rule_node, mapping[0], rule, mapping[1], mapping[2])

                rights_nodes = rule_node.find('./sb:Rights', _etree_sb_feed_namespaces)
                if rights_nodes is not None:
                    for access_rights_node in rights_nodes.findall('./sb:AccessRights', _etree_sb_feed_namespaces):
                        node_value = _get_etree_text(access_rights_node)
                        if node_value:
                            rule.rights.append(node_value)

                hub.authorization_rules.append(rule)

    if invalid_event_hub:
        raise AzureServiceBusResourceNotFound(_ERROR_EVENT_HUB_NOT_FOUND)

    # extract id, updated and name value from feed entry and set them of queue.
    for name, value in _ETreeXmlToObject.get_entry_properties_from_element(
            entry_element, True).items():
        if name == 'name':
            value = value.partition('?')[0]
        setattr(hub, name, value)

    return hub

def _convert_object_to_feed_entry(obj, rootName, content_writer):
    updated_str = datetime.utcnow().isoformat()
    if datetime.utcnow().utcoffset() is None:
        updated_str += '+00:00'

    writer = _XmlWriter()
    writer.preprocessor('<?xml version="1.0" encoding="utf-8" standalone="yes"?>')
    writer.start('entry', [
        ('xmlns:d', _XmlSchemas.DataServices, None),
        ('xmlns:m', _XmlSchemas.DataServicesMetadata, None),
        ('xmlns', _XmlSchemas.Atom, None),
        ])

    writer.element('title', '')
    writer.element('updated', updated_str)
    writer.start('author')
    writer.element('name', '')
    writer.end('author')
    writer.element('id', '')
    writer.start('content', [('type', 'application/xml', None)])
    writer.start(rootName, [
        ('xmlns:i', _XmlSchemas.SchemaInstance, None),
        ('xmlns', _XmlSchemas.ServiceBus, None),
        ])

    if obj:
        content_writer(writer, obj)

    writer.end(rootName)
    writer.end('content')
    writer.end('entry')

    xml = writer.xml()
    writer.close()

    return xml

def _convert_subscription_to_xml(sub):

    def _subscription_to_xml(writer, sub):
        writer.elements([
            ('LockDuration', sub.lock_duration, None),
            ('RequiresSession', sub.requires_session, _lower),
            ('DefaultMessageTimeToLive', sub.default_message_time_to_live, None),
            ('DeadLetteringOnMessageExpiration', sub.dead_lettering_on_message_expiration, _lower),
            ('DeadLetteringOnFilterEvaluationExceptions', sub.dead_lettering_on_filter_evaluation_exceptions, _lower),
            ('EnableBatchedOperations', sub.enable_batched_operations, _lower),
            ('MaxDeliveryCount', sub.max_delivery_count, None),
            ('MessageCount', sub.message_count, None),
            ])

    return _convert_object_to_feed_entry(
        sub, 'SubscriptionDescription', _subscription_to_xml)

def _convert_rule_to_xml(rule):

    def _rule_to_xml(writer, rule):
        if rule.filter_type:
            writer.start('Filter', [('i:type', rule.filter_type, None)])
            if rule.filter_type == 'CorrelationFilter':
                writer.element('CorrelationId', rule.filter_expression)
            else:
                writer.element('SqlExpression', rule.filter_expression)
                writer.element('CompatibilityLevel', '20')
            writer.end('Filter')
        if rule.action_type:
            writer.start('Action', [('i:type', rule.action_type, None)])
            if rule.action_type == 'SqlRuleAction':
                writer.element('SqlExpression', rule.action_expression)
                writer.element('CompatibilityLevel', '20')
            writer.end('Action')

    return _convert_object_to_feed_entry(
        rule, 'RuleDescription', _rule_to_xml)

def _convert_topic_to_xml(topic):

    def _topic_to_xml(writer, topic):
        writer.elements([
            ('DefaultMessageTimeToLive', topic.default_message_time_to_live, None),
            ('MaxSizeInMegabytes', topic.max_size_in_megabytes, None),
            ('RequiresDuplicateDetection', topic.requires_duplicate_detection, _lower),
            ('DuplicateDetectionHistoryTimeWindow', topic.duplicate_detection_history_time_window, None),
            ('EnableBatchedOperations', topic.enable_batched_operations, _lower),
            ('SizeInBytes', topic.size_in_bytes, None),
            ])

    return _convert_object_to_feed_entry(
        topic, 'TopicDescription', _topic_to_xml)

def _convert_queue_to_xml(queue):

    def _queue_to_xml(writer, queue):
        writer.elements([
            ('LockDuration', queue.lock_duration, None),
            ('MaxSizeInMegabytes', queue.max_size_in_megabytes, None),
            ('RequiresDuplicateDetection', queue.requires_duplicate_detection, _lower),
            ('RequiresSession', queue.requires_session, _lower),
            ('DefaultMessageTimeToLive', queue.default_message_time_to_live, None),
            ('DeadLetteringOnMessageExpiration', queue.dead_lettering_on_message_expiration, _lower),
            ('DuplicateDetectionHistoryTimeWindow', queue.duplicate_detection_history_time_window, None),
            ('MaxDeliveryCount', queue.max_delivery_count, None),
            ('EnableBatchedOperations', queue.enable_batched_operations, _lower),
            ('SizeInBytes', queue.size_in_bytes, None),
            ('MessageCount', queue.message_count, None),
            ])

    return _convert_object_to_feed_entry(
        queue, 'QueueDescription', _queue_to_xml)

def _convert_event_hub_to_xml(hub):

    def _hub_to_xml(writer, hub):
        writer.elements(
            [('MessageRetentionInDays', hub.message_retention_in_days, None)])
        if hub.authorization_rules:
            writer.start('AuthorizationRules')
            for rule in hub.authorization_rules:
                writer.start('AuthorizationRule',
                             [('i:type', 'SharedAccessAuthorizationRule', None)])
                writer.elements(
                    [('ClaimType', rule.claim_type, None),
                     ('ClaimValue', rule.claim_value, None)])
                if rule.rights:
                    writer.start('Rights')
                    for right in rule.rights:
                        writer.element('AccessRights', right)
                    writer.end('Rights')
                writer.elements(
                    [('KeyName', rule.key_name, None),
                     ('PrimaryKey', rule.primary_key, None),
                     ('SecondaryKey', rule.secondary_key, None)])
                writer.end('AuthorizationRule')
            writer.end('AuthorizationRules')
        writer.elements(
            [('Status', hub.status, None),
             ('UserMetadata', hub.user_metadata, None),
             ('PartitionCount', hub.partition_count, None)])

    return _convert_object_to_feed_entry(
        hub, 'EventHubDescription', _hub_to_xml)

def _service_bus_error_handler(http_error):
    ''' Simple error handler for Service Bus service. '''
    return _general_error_handler(http_error)