def _Delete(self):
    """Delete a VM instance."""
    stop_cmd = util.ALI_PREFIX + [
        'ecs',
        'StopInstance',
        '--InstanceId %s' % self.id]
    stop_cmd = util.GetEncodedCmd(stop_cmd)
    vm_util.IssueRetryableCommand(stop_cmd)

    self._WaitForInstanceStatus(['Stopped'])

    delete_cmd = util.ALI_PREFIX + [
        'ecs',
        'DeleteInstance',
        '--InstanceId %s' % self.id]
    delete_cmd = util.GetEncodedCmd(delete_cmd)
    vm_util.IssueRetryableCommand(delete_cmd)

    if FLAGS.ali_use_vpc:
      self._WaitForEipStatus(['Available'])
      release_eip_cmd = util.ALI_PREFIX + [
          'ecs',
          'ReleaseEipAddress',
          '--RegionId %s' % self.region,
          '--AllocationId %s' % self.eip_id]
      release_eip_cmd = util.GetEncodedCmd(release_eip_cmd)
      vm_util.IssueRetryableCommand(release_eip_cmd)
예제 #2
0
    def _AllocatePubIp(self, region, instance_id):
        """Allocate a public ip address and associate it to the instance"""
        if FLAGS.ali_use_vpc:
            allocatip_cmd = util.ALI_PREFIX + [
                'ecs', 'AllocateEipAddress',
                '--RegionId %s' % region, '--InternetChargeType PayByTraffic'
            ]
            allocatip_cmd = util.GetEncodedCmd(allocatip_cmd)
            stdout, _ = vm_util.IssueRetryableCommand(allocatip_cmd)
            response = json.loads(stdout)
            self.ip_address = response['EipAddress']
            self.eip_id = response['AllocationId']

            self._WaitForInstanceStatus(['Stopped', 'Running'])

            associate_cmd = util.ALI_PREFIX + [
                'ecs', 'AssociateEipAddress',
                '--RegionId %s' % region,
                '--AllocationId  %s' % self.eip_id,
                '--InstanceId %s' % instance_id, '--InstanceType EcsInstance'
            ]
            associate_cmd = util.GetEncodedCmd(associate_cmd)
            vm_util.IssueRetryableCommand(associate_cmd)

        else:
            allocatip_cmd = util.ALI_PREFIX + [
                'ecs', 'AllocatePublicIpAddress',
                '--RegionId %s' % region,
                '--InstanceId %s' % instance_id
            ]
            allocatip_cmd = util.GetEncodedCmd(allocatip_cmd)
            stdout, _ = vm_util.IssueRetryableCommand(allocatip_cmd)
            response = json.loads(stdout)
            self.ip_address = response['IpAddress']
  def _Create(self):
    """Create a VM instance."""

    if self.image is None:
      # This is here and not in the __init__ method bceauese _GetDefaultImage
      # does a nontrivial amount of work (it calls the aliyuncli).
      self.image = self._GetDefaultImage(self.region)

    self.password = util.GeneratePassword()

    create_cmd = util.ALI_PREFIX + [
        'ecs',
        'CreateInstance',
        '--InstanceName perfkit-%s' % FLAGS.run_uri,
        '--RegionId %s' % self.region,
        '--ZoneId %s' % self.zone,
        '--ImageId %s' % self.image,
        '--InstanceType %s' % self.machine_type,
        '--SecurityGroupId %s' % self.network.security_group.group_id,
        '--Password %s' % self.password]

    if FLAGS.scratch_disk_type == disk.LOCAL:
      disk_cmd = [
          '--SystemDiskCategory ephemeral_ssd',
          '--DataDisk1Category ephemeral_ssd',
          '--DataDisk1Size %s' % self.scratch_disk_size,
          '--DataDisk1Device %s%s' % (util.GetDrivePathPrefix(),
                                      DRIVE_START_LETTER)]
      create_cmd.extend(disk_cmd)

    if FLAGS.ali_io_optimized is not None:
      create_cmd.extend(['--IoOptimized optimized',
                         '--SystemDiskCategory %s' % self.system_disk_type])

    if FLAGS.ali_use_vpc:
      create_cmd.extend(['--VpcId %s' % self.network.vpc.id,
                        '--VSwitchId %s' % self.network.vswitch.id])
    else:
      create_cmd.extend([
          '--InternetChargeType PayByTraffic',
          '--InternetMaxBandwidthIn %s' % self.bandwidth_in,
          '--InternetMaxBandwidthOut %s' % self.bandwidth_out])

    create_cmd = util.GetEncodedCmd(create_cmd)
    stdout, _ = vm_util.IssueRetryableCommand(create_cmd)
    response = json.loads(stdout)
    self.id = response['InstanceId']

    self._AllocatePubIp(self.region, self.id)

    start_cmd = util.ALI_PREFIX + [
        'ecs',
        'StartInstance',
        '--RegionId %s' % self.region,
        '--InstanceId %s' % self.id]
    start_cmd = util.GetEncodedCmd(start_cmd)
    vm_util.IssueRetryableCommand(start_cmd)
  def _PostCreate(self):
    """Get the instance's data and tag it."""
    describe_cmd = util.ALI_PREFIX + [
        'ecs',
        'DescribeInstances',
        '--RegionId %s' % self.region,
        '--InstanceIds \'["%s"]\'' % self.id]
    logging.info('Getting instance %s public IP. This will fail until '
                 'a public IP is available, but will be retried.', self.id)
    describe_cmd = util.GetEncodedCmd(describe_cmd)
    stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
    response = json.loads(stdout)
    instance = response['Instances']['Instance'][0]
    if self.network.use_vpc:
      pub_ip_address = instance['EipAddress']['IpAddress']
      self.internal_ip = \
          instance['VpcAttributes']['PrivateIpAddress']['IpAddress'][0]
    else:
      pub_ip_address = instance['PublicIpAddress']['IpAddress'][0]
      self.internal_ip = instance['InnerIpAddress']['IpAddress'][0]
    assert self.ip_address == pub_ip_address
    self.group_id = instance['SecurityGroupIds']['SecurityGroupId'][0]

    self._WaitForInstanceStatus(['Running'])

    self.firewall.AllowPort(self, SSH_PORT)
    tags = {}
    tags.update(self.vm_metadata)
    util.AddTags(self.id, RESOURCE_TYPE[INSTANCE], self.region, **tags)
    util.AddDefaultTags(self.id, RESOURCE_TYPE[INSTANCE], self.region)
예제 #5
0
    def AllowPort(self, vm, port):
        """Opens a port on the firewall.

    Args:
      vm: The BaseVirtualMachine object to open the port for.
      port: The local port to open.
    """
        if vm.is_static:
            return
        entry = (port, vm.group_id)
        if entry in self.firewall_set:
            return
        with self._lock:
            if entry in self.firewall_set:
                return
            for protocol in ('tcp', 'udp'):
                authorize_cmd = util.ALI_PREFIX + [
                    'ecs', 'AuthorizeSecurityGroup',
                    '--IpProtocol %s' % protocol,
                    '--PortRange %s/%s' %
                    (port, port), '--SourceCidrIp 0.0.0.0/0',
                    '--RegionId %s' % vm.region,
                    '--SecurityGroupId %s' % vm.group_id
                ]
                if FLAGS.ali_use_vpc:
                    authorize_cmd.append('--NicType intranet')
                authorize_cmd = util.GetEncodedCmd(authorize_cmd)
                vm_util.IssueRetryableCommand(authorize_cmd)
            self.firewall_set.add(entry)
예제 #6
0
 def _Delete(self):
     """Delete's the VPC."""
     delete_cmd = util.ALI_PREFIX + [
         'ecs', 'DeleteVpc',
         '--RegionId %s' % self.region,
         '--VpcId %s' % self.id
     ]
     delete_cmd = util.GetEncodedCmd(delete_cmd)
     vm_util.IssueCommand(delete_cmd)
예제 #7
0
 def _Delete(self):
     """Deletes the security group."""
     delete_cmd = util.ALI_PREFIX + [
         'ecs', 'DeleteSecurityGroup',
         '--RegionId %s' % self.region,
         '--SecurityGroupId %s' % self.group_id
     ]
     delete_cmd = util.GetEncodedCmd(delete_cmd)
     vm_util.IssueRetryableCommand(delete_cmd)
예제 #8
0
 def _Delete(self):
     """Deletes the VSwitch."""
     delete_cmd = util.ALI_PREFIX + [
         'ecs', 'DeleteVSwitch',
         '--RegionId %s' % self.region,
         '--VSwitchId %s' % self.id
     ]
     delete_cmd = util.GetEncodedCmd(delete_cmd)
     vm_util.IssueCommand(delete_cmd, raise_on_failure=False)
 def _Exists(self):
     """Returns true if the security group exists."""
     show_cmd = util.ALI_PREFIX + [
         'ecs', 'DescribeSecurityGroupAttribute',
         '--RegionId %s' % self.region,
         '--SecurityGroupId %s' % self.group_id
     ]
     show_cmd = util.GetEncodedCmd(show_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(show_cmd)
     return 'SecurityGroupId' in json.loads(stdout)
예제 #10
0
 def _Delete(self):
     """Deletes the disk."""
     delete_cmd = util.ALI_PREFIX + [
         'ecs', 'DeleteDisk', '--DiskId %s' % self.id
     ]
     logging.info(
         'Deleting AliCloud disk %s. This may fail if the disk is not '
         'yet detached, but will be retried.', self.id)
     delete_cmd = util.GetEncodedCmd(delete_cmd)
     vm_util.IssueRetryableCommand(delete_cmd)
예제 #11
0
 def _Create(self):
     """Creates the VPC."""
     create_cmd = util.ALI_PREFIX + [
         'ecs', 'CreateVpc',
         '--VpcName %s' % self.name,
         '--RegionId %s' % self.region, '--CidrBlock 10.0.0.0/16'
     ]
     create_cmd = util.GetEncodedCmd(create_cmd)
     stdout, _, _ = vm_util.IssueCommand(create_cmd)
     response = json.loads(stdout)
     self.id = response['VpcId']
예제 #12
0
 def _Create(self):
     """Creates the security group."""
     create_cmd = util.ALI_PREFIX + [
         'ecs', 'CreateSecurityGroup',
         '--SecurityGroupName %s' % self.name,
         '--RegionId %s' % self.region
     ]
     if self.use_vpc:
         create_cmd.append('--VpcId %s' % self.vpc_id)
     create_cmd = util.GetEncodedCmd(create_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(create_cmd)
     self.group_id = json.loads(stdout)['SecurityGroupId']
 def _Create(self):
     """Creates the disk."""
     create_cmd = util.ALI_PREFIX + [
         'ecs', 'CreateDisk',
         '--RegionId %s' % self.region,
         '--ZoneId %s' % self.zone,
         '--Size %s' % self.disk_size,
         '--DiskCategory %s' % DISK_TYPE[self.disk_type]
     ]
     create_cmd = util.GetEncodedCmd(create_cmd)
     stdout, _, _ = vm_util.IssueCommand(create_cmd)
     response = json.loads(stdout)
     self.id = response['DiskId']
예제 #14
0
 def _Exists(self):
     """Returns true if the VPC exists."""
     describe_cmd = util.ALI_PREFIX + [
         'ecs', 'DescribeVpcs',
         '--RegionId %s' % self.region,
         '--VpcId %s' % self.id
     ]
     describe_cmd = util.GetEncodedCmd(describe_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
     response = json.loads(stdout)
     vpcs = response['Vpcs']['Vpc']
     assert len(vpcs) < 2, 'Too many VPCs.'
     return len(vpcs) > 0
예제 #15
0
 def _Exists(self):
     """Returns true if the VSwitch exists."""
     describe_cmd = util.ALI_PREFIX + [
         'ecs', 'DescribeVSwitches',
         '--RegionId %s' % self.region,
         '--VpcId %s' % self.vpc_id,
         '--ZoneId %s' % self.zone
     ]
     describe_cmd = util.GetEncodedCmd(describe_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
     response = json.loads(stdout)
     vswitches = response['VSwitches']['VSwitch']
     assert len(vswitches) < 2, 'Too many VSwitches.'
     return len(vswitches) > 0
 def _Create(self):
     """Creates the VSwitch."""
     create_cmd = util.ALI_PREFIX + [
         'ecs',
         'CreateVSwitch',
         '--VSwitchName %s' % self.name,
         '--ZoneId %s' % self.zone,
         '--CidrBlock 10.0.0.0/24',
         '--VpcId %s' % self.vpc_id,
     ]
     create_cmd = util.GetEncodedCmd(create_cmd)
     stdout, _, _ = vm_util.IssueCommand(create_cmd)
     response = json.loads(stdout)
     self.id = response['VSwitchId']
예제 #17
0
 def _Exists(self):
     """Returns true if the security group exists."""
     show_cmd = util.ALI_PREFIX + [
         'ecs', 'DescribeSecurityGroups',
         '--RegionId %s' % self.region,
         '--SecurityGroupId %s' % self.group_id
     ]
     show_cmd = util.GetEncodedCmd(show_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(show_cmd)
     response = json.loads(stdout)
     securityGroups = response['SecurityGroups']['SecurityGroup']
     assert len(securityGroups) < 2, 'Too many securityGroups.'
     if not securityGroups:
         return False
     return True
예제 #18
0
    def Detach(self):
        """Detaches the disk from a VM."""
        detach_cmd = util.ALI_PREFIX + [
            'ecs', 'DetachDisk',
            '--InstanceId %s' % self.attached_vm_id,
            '--DiskId %s' % self.id
        ]
        detach_cmd = util.GetEncodedCmd(detach_cmd)
        vm_util.IssueRetryableCommand(detach_cmd)

        with self._lock:
            assert self.attached_vm_id in AliDisk.vm_devices
            AliDisk.vm_devices[self.attached_vm_id].add(self.device_letter)
            self.attached_vm_id = None
            self.device_letter = None
 def _WaitForEipStatus(self, status_list):
   """Waits until the instance's status is in status_list"""
   logging.info('Waits until the eip\'s status is one of statuses: %s',
                status_list)
   describe_cmd = util.ALI_PREFIX + [
       'ecs',
       'DescribeEipAddresses',
       '--RegionId %s' % self.region,
       '--AllocationId %s' % self.eip_id]
   describe_cmd = util.GetEncodedCmd(describe_cmd)
   stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
   response = json.loads(stdout)
   EipAddresses = response['EipAddresses']['EipAddress']
   assert len(EipAddresses) == 1
   status = EipAddresses[0]['Status']
   assert status in status_list
 def _WaitForInstanceStatus(self, status_list):
   """Waits until the instance's status is in status_list"""
   logging.info('Waits until the instance\'s status is one of statuses: %s',
                status_list)
   describe_cmd = util.ALI_PREFIX + [
       'ecs',
       'DescribeInstances',
       '--RegionId %s' % self.region,
       '--InstanceIds \'["%s"]\'' % self.id]
   describe_cmd = util.GetEncodedCmd(describe_cmd)
   stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
   response = json.loads(stdout)
   instances = response['Instances']['Instance']
   assert len(instances) == 1
   status = instances[0]['Status']
   assert status in status_list
예제 #21
0
 def _WaitForVpcStatus(self, status_list):
     """Waits until VPC's status is in status_list"""
     logging.info('Waits until the status of VPC is in status_list: %s',
                  status_list)
     describe_cmd = util.ALI_PREFIX + [
         'ecs', 'DescribeVpcs',
         '--RegionId %s' % self.region,
         '--VpcId %s' % self.id
     ]
     describe_cmd = util.GetEncodedCmd(describe_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
     response = json.loads(stdout)
     vpcs = response['Vpcs']['Vpc']
     assert len(vpcs) == 1
     vpc_status = response['Vpcs']['Vpc'][0]['Status']
     assert vpc_status in status_list
예제 #22
0
 def WaitForDiskStatus(self, status_list):
     """Waits until disk is attach to the instance"""
     logging.info('Waits until the disk\'s status is one of statuses: %s',
                  status_list)
     describe_cmd = util.ALI_PREFIX + [
         'ecs', 'DescribeDisks',
         '--RegionId %s' % self.region,
         '--ZoneId %s' % self.zone,
         '--DiskIds \'["%s"]\'' % self.id
     ]
     attach_cmd = util.GetEncodedCmd(describe_cmd)
     stdout, _ = vm_util.IssueRetryableCommand(attach_cmd)
     response = json.loads(stdout)
     disk = response['Disks']['Disk']
     assert len(disk) == 1
     status = disk[0]['Status']
     assert status in status_list
 def _Exists(self):
   """Returns true if the VM exists."""
   describe_cmd = util.ALI_PREFIX + [
       'ecs',
       'DescribeInstances',
       '--RegionId %s' % self.region,
       '--InstanceIds \'["%s"]\'' % str(self.id)]
   describe_cmd = util.GetEncodedCmd(describe_cmd)
   stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)
   response = json.loads(stdout)
   instances = response['Instances']['Instance']
   assert len(instances) < 2, 'Too many instances.'
   if not instances:
     return False
   assert len(instances) == 1, 'Wrong number of instances.'
   status = instances[0]['Status']
   assert status in INSTANCE_KNOWN_STATUSES, status
   return status in INSTANCE_EXISTS_STATUSES
예제 #24
0
    def AllowIcmp(self, vm):
        """Opens the ICMP protocol on the firewall.

    Args:
      vm: The BaseVirtualMachine object to open the ICMP protocol for.
    """
        if vm.is_static:
            return
        with self._lock:
            authorize_cmd = util.ALI_PREFIX + [
                'ecs', 'AuthorizeSecurityGroup', '--IpProtocol ICMP',
                '--PortRange -1/-1', '--SourceCidrIp 0.0.0.0/0',
                '--RegionId %s' % vm.region,
                '--SecurityGroupId %s' % vm.group_id
            ]
            if FLAGS.ali_use_vpc:
                authorize_cmd.append('--NicType intranet')
            authorize_cmd = util.GetEncodedCmd(authorize_cmd)
            vm_util.IssueRetryableCommand(authorize_cmd)
예제 #25
0
    def Attach(self, vm):
        """Attaches the disk to a VM.

    Args:
      vm: The AliVirtualMachine instance to which the disk will be attached.
    """
        with self._lock:
            self.attached_vm_id = vm.id
            if self.attached_vm_id not in AliDisk.vm_devices:
                AliDisk.vm_devices[self.attached_vm_id] = set(
                    string.ascii_lowercase[1:])
            self.device_letter = min(AliDisk.vm_devices[self.attached_vm_id])
            AliDisk.vm_devices[self.attached_vm_id].remove(self.device_letter)

        attach_cmd = util.ALI_PREFIX + [
            'ecs', 'AttachDisk',
            '--InstanceId %s' % self.attached_vm_id,
            '--DiskId %s' % self.id,
            '--Device %s' % self.GetVirtualDevicePath()
        ]
        attach_cmd = util.GetEncodedCmd(attach_cmd)
        vm_util.IssueRetryableCommand(attach_cmd)
  def _GetDefaultImage(cls, region):
    """Returns the default image given the machine type and region.

    If no default is configured, this will return None.
    """
    if cls.IMAGE_NAME_FILTER is None:
      return None

    describe_cmd = util.ALI_PREFIX + [
        'ecs',
        'DescribeImages',
        '--RegionId %s' % region,
        '--ImageName \'%s\'' % cls.IMAGE_NAME_FILTER]
    describe_cmd = util.GetEncodedCmd(describe_cmd)
    stdout, _ = vm_util.IssueRetryableCommand(describe_cmd)

    if not stdout:
      return None

    images = json.loads(stdout)['Images']['Image']
    # We want to return the latest version of the image, and since the wildcard
    # portion of the image name is the image's creation date, we can just take
    # the image with the 'largest' name.
    return max(images, key=lambda image: image['ImageName'])['ImageId']
  def _Create(self):
    """Create a VM instance."""

    if self.image is None:
      # This is here and not in the __init__ method bceauese _GetDefaultImage
      # does a nontrivial amount of work (it calls the aliyuncli).
      self.image = self._GetDefaultImage(self.region)

    create_cmd = util.ALI_PREFIX + [
        'ecs',
        'CreateInstance',
        '--InstanceName perfkit-%s' % FLAGS.run_uri,
        '--RegionId %s' % self.region,
        '--ZoneId %s' % self.zone,
        '--ImageId %s' % self.image,
        '--InstanceType %s' % self.machine_type,
        '--SecurityGroupId %s' % self.network.security_group.group_id,
        '--KeyPairName %s' % self.key_pair_name,
        '--SystemDisk.Category %s' % self.system_disk_type,
        '--SystemDisk.Size %s' % self.system_disk_size]

    if FLAGS.scratch_disk_type == disk.LOCAL:
      disk_cmd = [
          '--DataDisk1Category ephemeral_ssd',
          '--DataDisk1Size %s' % self.scratch_disk_size,
          '--DataDisk1Device %s%s' % (util.GetDrivePathPrefix(),
                                      DRIVE_START_LETTER)]
      create_cmd.extend(disk_cmd)

    if FLAGS.ali_io_optimized is not None:
      create_cmd.extend(['--IoOptimized optimized'])

    if FLAGS.ali_use_vpc:
      create_cmd.extend(['--VSwitchId %s' % self.network.vswitch.id])
    else:
      create_cmd.extend([
          '--InternetChargeType PayByTraffic',
          '--InternetMaxBandwidthIn %s' % self.bandwidth_in,
          '--InternetMaxBandwidthOut %s' % self.bandwidth_out])

    # Create user and add SSH key
    public_key = AliCloudKeyFileManager.GetPublicKey()
    user_data = util.ADD_USER_TEMPLATE.format(user_name=self.user_name,
                                              public_key=public_key)
    logging.debug('encoding startup script: %s', user_data)
    create_cmd.extend(['--UserData', six.ensure_str(
        base64.b64encode(user_data.encode('utf-8')))])

    create_cmd = util.GetEncodedCmd(create_cmd)
    stdout, _ = vm_util.IssueRetryableCommand(create_cmd)
    response = json.loads(stdout)
    self.id = response['InstanceId']

    self._AllocatePubIp(self.region, self.id)

    start_cmd = util.ALI_PREFIX + [
        'ecs',
        'StartInstance',
        '--InstanceId %s' % self.id]
    start_cmd = util.GetEncodedCmd(start_cmd)
    vm_util.IssueRetryableCommand(start_cmd)