Exemplo n.º 1
0
def add_endpoint_to_network_config(network_config, public_endpoints,
                                   private_endpoints):
    """
    Return a new network config
    :param network_config:
    :param public_endpoints: a list of int or str
    :param private_endpoints: a list of int or str
    :return:
    """
    endpoints = zip(map(str, public_endpoints), map(str, private_endpoints))
    new_network_config = ConfigurationSet()
    new_network_config.configuration_set_type = network_config.configuration_set_type
    if network_config.input_endpoints is not None:
        for input_endpoint in network_config.input_endpoints.input_endpoints:
            new_network_config.input_endpoints.input_endpoints.append(
                ConfigurationSetInputEndpoint(input_endpoint.name,
                                              input_endpoint.protocol,
                                              input_endpoint.port,
                                              input_endpoint.local_port))
    for endpoint in endpoints:
        new_network_config.input_endpoints.input_endpoints.append(
            ConfigurationSetInputEndpoint(ENDPOINT_PREFIX + endpoint[0],
                                          ENDPOINT_PROTOCOL, endpoint[0],
                                          endpoint[1]))
    return new_network_config
Exemplo n.º 2
0
def get_network_config(network_config, assigned_endpoints):
    """A helper to generate network config from azure_template_unit's network config

    decouple from azure_template_unit.get_network_config
    Public endpoint should be assigned in real time
    """

    nc = network_config

    network_config = ConfigurationSet()
    network_config.configuration_set_type = nc[
        AZURE_UNIT.NETWORK_CONFIG_CONFIGURATION_SET_TYPE]
    input_endpoints = nc[AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS]
    # avoid duplicate endpoint under same cloud service
    endpoints = map(
        lambda i: i[AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS_LOCAL_PORT],
        input_endpoints)
    unassigned_endpoints = map(
        str, find_unassigned_endpoints(endpoints, assigned_endpoints))
    map(
        lambda
        (i, u): i.update({AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS_PORT: u}),
        zip(input_endpoints, unassigned_endpoints))

    for input_endpoint in input_endpoints:
        network_config.input_endpoints.input_endpoints.append(
            ConfigurationSetInputEndpoint(
                input_endpoint[AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS_NAME],
                input_endpoint[
                    AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS_PROTOCOL],
                input_endpoint[AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS_PORT],
                input_endpoint[
                    AZURE_UNIT.NETWORK_CONFIG_INPUT_ENDPOINTS_LOCAL_PORT]))

    return network_config
Exemplo n.º 3
0
 def get_network_config(self, service, update):
     """
     Return None if image type is vm and not update
     Public endpoint should be assigned in real time
     :param service:
     :return:
     """
     if self.is_vm_image() and not update:
         return None
     cs = self.virtual_environment[self.T_CS]
     nc = self.virtual_environment[self.T_NC]
     network_config = ConfigurationSet()
     network_config.configuration_set_type = nc[self.T_NC_CST]
     input_endpoints = nc[self.T_NC_IE]
     # avoid duplicate endpoint under same cloud service
     assigned_endpoints = service.get_assigned_endpoints(cs[self.T_CS_SN])
     endpoints = map(lambda i: i[self.T_NC_IE_LP], input_endpoints)
     unassigned_endpoints = map(
         str, find_unassigned_endpoints(endpoints, assigned_endpoints))
     map(lambda (i, u): i.update({self.T_NC_IE_PO: u}),
         zip(input_endpoints, unassigned_endpoints))
     for input_endpoint in input_endpoints:
         network_config.input_endpoints.input_endpoints.append(
             ConfigurationSetInputEndpoint(input_endpoint[self.T_NC_IE_N],
                                           input_endpoint[self.T_NC_IE_PR],
                                           input_endpoint[self.T_NC_IE_PO],
                                           input_endpoint[self.T_NC_IE_LP]))
     return network_config
Exemplo n.º 4
0
    def create(self, name, external_port, internal_port, protocol,
               idle_timeout):
        try:
            role = self.__get_role()
            config = self.__get_network_config_for_role(role)
            new_endpoint = ConfigurationSetInputEndpoint(
                name=name,
                protocol=protocol,
                port=external_port,
                local_port=internal_port,
                idle_timeout_in_minutes=idle_timeout,
                enable_direct_server_return=False,
            )

            # If there are no endpoints the input_endpoints
            # attribute is None. Thus create and set new instance.
            if not config.input_endpoints:
                config.input_endpoints = ConfigurationSetInputEndpoints()

            config.input_endpoints.input_endpoints.append(new_endpoint)

            result = self.service.update_role(
                self.cloud_service_name,
                self.cloud_service_name,
                role.role_name,
                os_virtual_hard_disk=role.os_virtual_hard_disk,
                network_config=config,
                availability_set_name=role.availability_set_name,
                data_virtual_hard_disks=role.data_virtual_hard_disks)
        except Exception as e:
            raise AzureEndpointCreateError('%s: %s' %
                                           (type(e).__name__, format(e)))
        return Defaults.unify_id(result.request_id)
Exemplo n.º 5
0
 def create_network_endpoint(
     self, name, public_port, local_port, protocol
 ):
     """
         create a network service endpoint
     """
     return ConfigurationSetInputEndpoint(
         name, protocol, public_port, local_port
     )
Exemplo n.º 6
0
    def _ensureBuildMachineExists(self):
        """
        Creates the VM for the build server.
        """
        service_name = self.config.getBuildServiceName()
        service_storage_name = self.config.getStorageAccountName()
        cert_thumbprint = self.config.getServiceCertificateThumbprint()
        vm_username = self.config.getVirtualMachineLogonUsername()
        vm_password = self.config.getVirtualMachineLogonPassword()
        vm_hostname = service_name

        role_instances = self._getRoleInstances(service_name)
        if vm_hostname in role_instances:
            logger.warn("Role instance %s already exists: skipping creation.", vm_hostname)
        else:
            logger.info("Role instance %s provisioning begins.", vm_hostname)
            self._assertOsImageExists(self.config.getBuildOSImageName())

            vm_diskname = '{0}.vhd'.format(vm_hostname)
            vm_disk_media_link = 'http://{0}.blob.core.windows.net/vhds/{1}'.format(service_storage_name, vm_diskname)
            os_hd = OSVirtualHardDisk(self.config.getBuildOSImageName(),
                                      vm_disk_media_link,
                                      disk_name=vm_diskname,
                                      disk_label=vm_diskname)
            linux_config = LinuxConfigurationSet(vm_hostname, vm_username, vm_password, True)
            linux_config.ssh.public_keys.public_keys.append(
                PublicKey(cert_thumbprint, u'/home/{0}/.ssh/authorized_keys'.format(vm_username))
            )
            linux_config.ssh.key_pairs.key_pairs.append(
                KeyPair(cert_thumbprint, u'/home/{0}/.ssh/id_rsa'.format(vm_username))
            )
            network_config = ConfigurationSet()
            network_config.configuration_set_type = 'NetworkConfiguration'
            ssh_endpoint = ConfigurationSetInputEndpoint(name='SSH',
                                                         protocol='TCP',
                                                         port=u'22',
                                                         local_port=u'22')
            network_config.input_endpoints.input_endpoints.append(ssh_endpoint)

            result = self.sms.create_virtual_machine_deployment(service_name=service_name,
                                                                deployment_name=service_name,
                                                                deployment_slot='Production',
                                                                label=vm_hostname,
                                                                role_name=vm_hostname,
                                                                system_config=linux_config,
                                                                os_virtual_hard_disk=os_hd,
                                                                network_config=network_config,
                                                                availability_set_name=None,
                                                                data_virtual_hard_disks=None,
                                                                role_size=self.config.getBuildInstanceRoleSize())
            self._wait_for_operation_success(result.request_id, timeout=self.config.getAzureOperationTimeout())
            self._wait_for_role_instance_status(vm_hostname, service_name, 'ReadyRole',
                                                self.config.getAzureOperationTimeout())
            logger.info("Role instance %s has been created.", vm_hostname)
Exemplo n.º 7
0
    def __set_endpoint_config(self, service_name, hackathon_id):
        """
        Set endpoint configuration which is need in creating Azure VM

        :param service_name: the name of cloud service
        :type service_name: str|unicode

        :param hackathon_id: the id of hackathon
        :type hackathon_id: integer

        :return: the endpoint configuration set
        :rtype: class 'azure.servicemanagement.ConfigurationSet'
        """
        used_port_set = self.__get_used_public_port_set(
            service_name, hackathon_id)
        docker_port = 4243
        ssh_port = 9000
        while docker_port in used_port_set:
            docker_port += 1
        while ssh_port in used_port_set:
            ssh_port += 1
        assert docker_port < 40000 and ssh_port < 40000
        endpoint_config = ConfigurationSet()
        endpoint_config.configuration_set_type = AzureVMEnpointConfigType.NETWORK
        endpoint1 = ConfigurationSetInputEndpoint(
            name=AzureVMEndpointName.DOCKER,
            protocol=TCPProtocol.TCP,
            port=str(docker_port),
            local_port=str(AzureVMEndpointDefaultPort.DOCKER),
            load_balanced_endpoint_set_name=None,
            enable_direct_server_return=False)
        endpoint2 = ConfigurationSetInputEndpoint(
            name=AzureVMEndpointName.SSH,
            protocol=TCPProtocol.TCP,
            port=str(ssh_port),
            local_port=str(AzureVMEndpointDefaultPort.SSH),
            load_balanced_endpoint_set_name=None,
            enable_direct_server_return=False)
        endpoint_config.input_endpoints.input_endpoints.append(endpoint1)
        endpoint_config.input_endpoints.input_endpoints.append(endpoint2)
        return endpoint_config
Exemplo n.º 8
0
 def test_get_assigned_endpoints(self):
     cs_name = 'dsfsd'
     self.service.get_hosted_service_properties = Mock()
     i = ConfigurationSetInputEndpoint('http', 'tcp', '80', '80')
     c = ConfigurationSet()
     c.input_endpoints.input_endpoints = [i]
     r = Role()
     r.configuration_sets.configuration_sets = [c]
     d = Deployment()
     d.role_list.roles = [r]
     h = HostedService()
     h.deployments.deployments = [d]
     self.service.get_hosted_service_properties.return_value = h
     self.assertEqual(len(self.service.get_assigned_endpoints(cs_name)), 1)
Exemplo n.º 9
0
def delete_endpoint_from_network_config(network_config, private_endpoints):
    """
    Return a new network config
    :param network_config:
    :param private_endpoints: a list of int or str
    :return:
    """
    private_endpoints = map(str, private_endpoints)
    new_network_config = ConfigurationSet()
    new_network_config.configuration_set_type = network_config.configuration_set_type
    if network_config.input_endpoints is not None:
        for input_endpoint in network_config.input_endpoints.input_endpoints:
            if input_endpoint.local_port not in private_endpoints:
                new_network_config.input_endpoints.input_endpoints.append(
                    ConfigurationSetInputEndpoint(input_endpoint.name,
                                                  input_endpoint.protocol,
                                                  input_endpoint.port,
                                                  input_endpoint.local_port))
    return new_network_config
Exemplo n.º 10
0
def azure_add_endpoints(name, portConfigs):
    sms = ServiceManagementService(AZURE_SUBSCRIPTION_ID, AZURE_CERTIFICATE)
    role = sms.get_role(name, name, name)

    network_config = role.configuration_sets[0]
    for i, portConfig in enumerate(portConfigs):
        network_config.input_endpoints.input_endpoints.append(
            ConfigurationSetInputEndpoint(
                name=portConfig["service"],
                protocol=portConfig["protocol"],
                port=portConfig["port"],
                local_port=portConfig["local_port"],
                load_balanced_endpoint_set_name=None,
                enable_direct_server_return=True
                if portConfig["protocol"] == "udp" else False,
                idle_timeout_in_minutes=None
                if portConfig["protocol"] == "udp" else 4))
    try:
        sms.update_role(name, name, name, network_config=network_config)
    except AzureHttpError as e:
        debug.warn("Exception opening ports for %s: %r" % (name, e))
Exemplo n.º 11
0
def create_virtual_machine(module, azure):
    """
    Create new virtual machine

    module : AnsibleModule object
    azure: authenticated azure ServiceManagementService object

    Returns:
        True if a new virtual machine and/or cloud service was created, false otherwise
    """
    name = module.params.get('name')
    os_type = module.params.get('os_type')
    hostname = module.params.get('hostname') or name + ".cloudapp.net"
    endpoints = module.params.get('endpoints').split(',')
    ssh_cert_path = module.params.get('ssh_cert_path')
    user = module.params.get('user')
    password = module.params.get('password')
    location = module.params.get('location')
    role_size = module.params.get('role_size')
    storage_account = module.params.get('storage_account')
    image = module.params.get('image')
    virtual_network_name = module.params.get('virtual_network_name')
    wait = module.params.get('wait')
    wait_timeout = int(module.params.get('wait_timeout'))

    changed = False

    # Check if a deployment with the same name already exists
    cloud_service_name_available = azure.check_hosted_service_name_availability(
        name)
    if cloud_service_name_available.result:
        # cloud service does not exist; create it
        try:
            result = azure.create_hosted_service(service_name=name,
                                                 label=name,
                                                 location=location)
            _wait_for_completion(azure, result, wait_timeout,
                                 "create_hosted_service")
            changed = True
        except AzureException as e:
            module.fail_json(
                msg="failed to create the new service, error was: %s" % str(e))

    try:
        # check to see if a vm with this name exists; if so, do nothing
        azure.get_role(name, name, name)
    except AzureMissingException:
        # vm does not exist; create it

        if os_type == 'linux':
            # Create linux configuration
            disable_ssh_password_authentication = not password
            vm_config = LinuxConfigurationSet(
                hostname, user, password, disable_ssh_password_authentication)
        else:
            # Create Windows Config
            vm_config = WindowsConfigurationSet(
                hostname, password, None, module.params.get('auto_updates'),
                None, user)
            vm_config.domain_join = None
            if module.params.get('enable_winrm'):
                listener = Listener('Http')
                vm_config.win_rm.listeners.listeners.append(listener)
            else:
                vm_config.win_rm = None

        # Add ssh certificates if specified
        if ssh_cert_path:
            fingerprint, pkcs12_base64 = get_ssh_certificate_tokens(
                module, ssh_cert_path)
            # Add certificate to cloud service
            result = azure.add_service_certificate(name, pkcs12_base64, 'pfx',
                                                   '')
            _wait_for_completion(azure, result, wait_timeout,
                                 "add_service_certificate")

            # Create ssh config
            ssh_config = SSH()
            ssh_config.public_keys = PublicKeys()
            authorized_keys_path = u'/home/%s/.ssh/authorized_keys' % user
            ssh_config.public_keys.public_keys.append(
                PublicKey(path=authorized_keys_path, fingerprint=fingerprint))
            # Append ssh config to linux machine config
            vm_config.ssh = ssh_config

        # Create network configuration
        network_config = ConfigurationSetInputEndpoints()
        network_config.configuration_set_type = 'NetworkConfiguration'
        network_config.subnet_names = []
        network_config.public_ips = None
        for port in endpoints:
            network_config.input_endpoints.append(
                ConfigurationSetInputEndpoint(name='TCP-%s' % port,
                                              protocol='TCP',
                                              port=port,
                                              local_port=port))

        # First determine where to store disk
        today = datetime.date.today().strftime('%Y-%m-%d')
        disk_prefix = u'%s-%s' % (name, name)
        media_link = u'http://%s.blob.core.windows.net/vhds/%s-%s.vhd' % (
            storage_account, disk_prefix, today)
        # Create system hard disk
        os_hd = OSVirtualHardDisk(image, media_link)

        # Spin up virtual machine
        try:
            result = azure.create_virtual_machine_deployment(
                service_name=name,
                deployment_name=name,
                deployment_slot='production',
                label=name,
                role_name=name,
                system_config=vm_config,
                network_config=network_config,
                os_virtual_hard_disk=os_hd,
                role_size=role_size,
                role_type='PersistentVMRole',
                virtual_network_name=virtual_network_name)
            _wait_for_completion(azure, result, wait_timeout,
                                 "create_virtual_machine_deployment")
            changed = True
        except AzureException as e:
            module.fail_json(
                msg="failed to create the new virtual machine, error was: %s" %
                str(e))

    try:
        deployment = azure.get_deployment_by_name(service_name=name,
                                                  deployment_name=name)
        return (changed, urlparse(deployment.url).hostname, deployment)
    except AzureException as e:
        module.fail_json(
            msg=
            "failed to lookup the deployment information for %s, error was: %s"
            % (name, str(e)))
Exemplo n.º 12
0
    def _ensureVirtualMachinesExist(self):
        """
        Creates the VMs for the web site.
        """
        service_name = self.config.getServiceName()
        cert_thumbprint = self.config.getServiceCertificateThumbprint()
        vm_username = self.config.getVirtualMachineLogonUsername()
        vm_password = self.config.getVirtualMachineLogonPassword()
        vm_role_size = self.config.getServiceInstanceRoleSize()
        vm_numbers = self.config.getServiceInstanceCount()
        if vm_numbers < 1:
            raise Exception(
                "Detected an invalid number of instances: {0}.".format(
                    vm_numbers))

        self._assertOsImageExists(self.config.getServiceOSImageName())

        role_instances = self._getRoleInstances(service_name)
        for vm_number in range(1, vm_numbers + 1):
            vm_hostname = '{0}-{1}'.format(service_name, vm_number)
            if vm_hostname in role_instances:
                logger.warn(
                    "Role instance %s already exists: skipping creation.",
                    vm_hostname)
                continue

            logger.info("Role instance %s provisioning begins.", vm_hostname)
            vm_diskname = '{0}.vhd'.format(vm_hostname)
            vm_disk_media_link = 'http://{0}.blob.core.windows.net/vhds/{1}'.format(
                self.config.getServiceStorageAccountName(), vm_diskname)
            ssh_port = str(self.config.getServiceInstanceSshPort() + vm_number)

            os_hd = OSVirtualHardDisk(self.config.getServiceOSImageName(),
                                      vm_disk_media_link,
                                      disk_name=vm_diskname,
                                      disk_label=vm_diskname)
            linux_config = LinuxConfigurationSet(vm_hostname, vm_username,
                                                 vm_password, True)
            linux_config.ssh.public_keys.public_keys.append(
                PublicKey(
                    cert_thumbprint,
                    u'/home/{0}/.ssh/authorized_keys'.format(vm_username)))
            linux_config.ssh.key_pairs.key_pairs.append(
                KeyPair(cert_thumbprint,
                        u'/home/{0}/.ssh/id_rsa'.format(vm_username)))
            network_config = ConfigurationSet()
            network_config.configuration_set_type = 'NetworkConfiguration'
            ssh_endpoint = ConfigurationSetInputEndpoint(name='SSH',
                                                         protocol='TCP',
                                                         port=ssh_port,
                                                         local_port=u'22')
            network_config.input_endpoints.input_endpoints.append(ssh_endpoint)
            http_endpoint = ConfigurationSetInputEndpoint(
                name='HTTP',
                protocol='TCP',
                port=u'80',
                local_port=u'80',
                load_balanced_endpoint_set_name=service_name)
            http_endpoint.load_balancer_probe.port = '80'
            http_endpoint.load_balancer_probe.protocol = 'TCP'
            network_config.input_endpoints.input_endpoints.append(
                http_endpoint)

            if vm_number == 1:
                result = self.sms.create_virtual_machine_deployment(
                    service_name=service_name,
                    deployment_name=service_name,
                    deployment_slot='Production',
                    label=vm_hostname,
                    role_name=vm_hostname,
                    system_config=linux_config,
                    os_virtual_hard_disk=os_hd,
                    network_config=network_config,
                    availability_set_name=service_name,
                    data_virtual_hard_disks=None,
                    role_size=vm_role_size)
                self._wait_for_operation_success(
                    result.request_id,
                    timeout=self.config.getAzureOperationTimeout())
                self._wait_for_role_instance_status(
                    vm_hostname, service_name, 'ReadyRole',
                    self.config.getAzureOperationTimeout())
            else:
                result = self.sms.add_role(service_name=service_name,
                                           deployment_name=service_name,
                                           role_name=vm_hostname,
                                           system_config=linux_config,
                                           os_virtual_hard_disk=os_hd,
                                           network_config=network_config,
                                           availability_set_name=service_name,
                                           role_size=vm_role_size)
                self._wait_for_operation_success(
                    result.request_id,
                    timeout=self.config.getAzureOperationTimeout())
                self._wait_for_role_instance_status(
                    vm_hostname, service_name, 'ReadyRole',
                    self.config.getAzureOperationTimeout())

            logger.info("Role instance %s has been created.", vm_hostname)
Exemplo n.º 13
0
            ssh_config.public_keys = PublicKeys()
            authorized_keys_path = u'/home/%s/.ssh/authorized_keys' % user
            ssh_config.public_keys.public_keys.append(
                PublicKey(path=authorized_keys_path, fingerprint=fingerprint))
            # Append ssh config to linux machine config
            linux_config.ssh = ssh_config

        # Create network configuration
        network_config = ConfigurationSetInputEndpoints()
        network_config.configuration_set_type = 'NetworkConfiguration'
        network_config.subnet_names = []
        network_config.public_ips = None
        for port in endpoints:
            network_config.input_endpoints.append(
                ConfigurationSetInputEndpoint(name='TCP-%s' % port,
                                              protocol='TCP',
                                              port=port,
                                              local_port=port))

        # First determine where to store disk
        today = datetime.date.today().strftime('%Y-%m-%d')
        disk_prefix = u'%s-%s' % (name, name)
        media_link = u'http://%s.blob.core.windows.net/vhds/%s-%s.vhd' % (
            storage_account, disk_prefix, today)
        # Create system hard disk
        os_hd = OSVirtualHardDisk(image, media_link)

        # Spin up virtual machine
        try:
            result = azure.create_virtual_machine_deployment(
                service_name=name,
                deployment_name=name,
Exemplo n.º 14
0
            # Create ssh config
            ssh_config = SSH()
            ssh_config.public_keys = PublicKeys()
            authorized_keys_path = u'/home/%s/.ssh/authorized_keys' % user
            ssh_config.public_keys.public_keys.append(PublicKey(path=authorized_keys_path, fingerprint=fingerprint))
            # Append ssh config to linux machine config
            vm_config.ssh = ssh_config

        # Create network configuration
        network_config = ConfigurationSetInputEndpoints()
        network_config.configuration_set_type = 'NetworkConfiguration'
        network_config.subnet_names = []
        network_config.public_ips = None
        for port in endpoints:
            network_config.input_endpoints.append(ConfigurationSetInputEndpoint(name='TCP-%s' % port,
                                                                                protocol='TCP',
                                                                                port=port,
                                                                                local_port=port))

        # First determine where to store disk
        today = datetime.date.today().strftime('%Y-%m-%d')
        disk_prefix = u'%s-%s' % (name, name)
        media_link = u'http://%s.blob.core.windows.net/vhds/%s-%s.vhd' % (storage_account, disk_prefix, today)
        # Create system hard disk
        os_hd = OSVirtualHardDisk(image, media_link)

        # Spin up virtual machine
        try:
            result = azure.create_virtual_machine_deployment(service_name=name,
                                                             deployment_name=name,
                                                             deployment_slot='production',
                                                             label=name,
Exemplo n.º 15
0
pk = PublicKey(SERVICE_CERT_THUMBPRINT, vm_public_key_path)

pair = KeyPair(SERVICE_CERT_THUMBPRINT, vm_public_key_path)

linux_config.ssh = SSH()

linux_config.ssh.key_pairs.key_pairs.append(pair)
linux_config.ssh.public_keys.public_keys.append(pk)

endpoint_config = ConfigurationSet()
endpoint_config.configuration_set_type = 'NetworkConfiguration'

ssh_endpoint = ConfigurationSetInputEndpoint(
    name='ssh',
    protocol='tcp',
    port='22',
    local_port='22',
    load_balanced_endpoint_set_name=None,
    enable_direct_server_return=False)
http_endpoint = ConfigurationSetInputEndpoint(
    name='http',
    protocol='tcp',
    port='80',
    local_port='80',
    load_balanced_endpoint_set_name=None,
    enable_direct_server_return=False)
endpoint_config.input_endpoints.input_endpoints.append(ssh_endpoint)
endpoint_config.input_endpoints.input_endpoints.append(http_endpoint)

result = sms.create_virtual_machine_deployment(
    service_name=hosted_service_name,
Exemplo n.º 16
0
def create_virtual_machine(module, azure):
    """
    Create new virtual machine

    module : AnsibleModule object
    azure: authenticated azure ServiceManagementService object

    Returns:
        True if a new virtual machine was created, false otherwise
    """
    name = module.params.get('name')
    hostname = module.params.get('hostname') or name + ".cloudapp.net"
    endpoints = module.params.get('endpoints').split(',')
    ssh_cert_path = module.params.get('ssh_cert_path')
    user = module.params.get('user')
    password = module.params.get('password')
    location = module.params.get('location')
    role_size = module.params.get('role_size')
    storage_account = module.params.get('storage_account')
    image = module.params.get('image')
    vm_image = module.params.get('vm_image')
    virtual_network_name = module.params.get('virtual_network_name')
    wait = module.params.get('wait')
    wait_timeout = int(module.params.get('wait_timeout'))

    use_vm_image = vm_image is not None and image is None

    # Check if a deployment with the same name already exists
    cloud_service_name_available = azure.check_hosted_service_name_availability(
        name)
    if not cloud_service_name_available.result:
        changed = False
    else:
        changed = True
        # Create cloud service if necessary
        try:
            result = azure.create_hosted_service(service_name=name,
                                                 label=name,
                                                 location=location)
            _wait_for_completion(azure, result, wait_timeout,
                                 "create_hosted_service")
        except WindowsAzureError as e:
            module.fail_json(
                msg=
                "failed to create the new service name, it already exists: %s"
                % str(e))

        # Create linux configuration
        if not use_vm_image:
            disable_ssh_password_authentication = not password
            linux_config = LinuxConfigurationSet(
                hostname, user, password, disable_ssh_password_authentication)

            # Add ssh certificates if specified
            if ssh_cert_path:
                fingerprint, pkcs12_base64 = get_ssh_certificate_tokens(
                    module, ssh_cert_path)
                # Add certificate to cloud service
                result = azure.add_service_certificate(name, pkcs12_base64,
                                                       'pfx', '')
                _wait_for_completion(azure, result, wait_timeout,
                                     "add_service_certificate")

                # Create ssh config
                ssh_config = SSH()
                ssh_config.public_keys = PublicKeys()
                authorized_keys_path = u'/home/%s/.ssh/authorized_keys' % user
                ssh_config.public_keys.public_keys.append(
                    PublicKey(path=authorized_keys_path,
                              fingerprint=fingerprint))
                # Append ssh config to linux machine config
                linux_config.ssh = ssh_config
        else:
            # When using vm_image, you can't specify an OS configuration set (burned into the image)
            linux_config = None

        # Create network configuration
        network_config = ConfigurationSetInputEndpoints()
        network_config.configuration_set_type = 'NetworkConfiguration'
        network_config.subnet_names = []
        network_config.public_ips = None
        for port in endpoints:
            network_config.input_endpoints.append(
                ConfigurationSetInputEndpoint(name='TCP-%s' % port,
                                              protocol='TCP',
                                              port=port,
                                              local_port=port))

        # First determine where to store disk
        today = datetime.date.today().strftime('%Y-%m-%d')
        disk_prefix = u'%s-%s' % (name, name)
        media_link = u'http://%s.blob.core.windows.net/vhds/%s-%s.vhd' % (
            storage_account, disk_prefix, today)
        # Create system hard disk
        if image:
            os_hd = OSVirtualHardDisk(image, media_link)
        else:
            # When using vm_image_name, you can't specify an OS Virtual Hard Disk,
            # since the image already contains the VHD configuration
            os_hd = None

        # Spin up virtual machine
        try:
            result = azure.create_virtual_machine_deployment(
                service_name=name,
                deployment_name=name,
                deployment_slot='production',
                label=name,
                role_name=name,
                system_config=linux_config,
                network_config=network_config,
                os_virtual_hard_disk=os_hd,
                vm_image_name=vm_image,
                role_size=role_size,
                role_type='PersistentVMRole',
                virtual_network_name=virtual_network_name)
            _wait_for_completion(azure, result, wait_timeout,
                                 "create_virtual_machine_deployment")
        except WindowsAzureError as e:
            module.fail_json(
                msg="failed to create the new virtual machine, error was: %s" %
                str(e))

    try:
        deployment = azure.get_deployment_by_name(service_name=name,
                                                  deployment_name=name)
        return (changed, urlparse(deployment.url).hostname, deployment)
    except WindowsAzureError as e:
        module.fail_json(
            msg=
            "failed to lookup the deployment information for %s, error was: %s"
            % (name, str(e)))