def build(self) -> build_module.GoogleCloudBuild: """Get a GoogleCloudBuild object for the project. Returns: GoogleCloudBuild: Object that represents Google Cloud Build. """ if self._build: return self._build self._build = build_module.GoogleCloudBuild(self.project_id) return self._build
def ExportImage(self, gcs_output_folder: str, output_name: Optional[str] = None) -> None: """Export compute image to Google Cloud storage. Exported image is compressed and stored in .tar.gz format. Args: gcs_output_folder (str): Folder path of the exported image. output_name (str): Optional. Name of the output file. Name will be appended with .tar.gz. Default is [image_name].tar.gz. Raises: InvalidNameError: If exported image name is invalid. """ if output_name: if not common.REGEX_DISK_NAME.match(output_name): raise errors.InvalidNameError( 'Exported image name {0:s} does not comply with {1:s}'. format(output_name, common.REGEX_DISK_NAME.pattern), __name__) full_path = '{0:s}.tar.gz'.format( os.path.join(gcs_output_folder, output_name)) else: full_path = '{0:s}.tar.gz'.format( os.path.join(gcs_output_folder, self.name)) build_body = { 'timeout': '86400s', 'steps': [{ 'args': [ '-source_image={0:s}'.format(self.name), '-destination_uri={0:s}'.format(full_path), '-client_id=api', ], 'name': 'gcr.io/compute-image-tools/gce_vm_image_export:release', 'env': [] }], 'tags': ['gce-daisy', 'gce-daisy-image-export'] } cloud_build = build.GoogleCloudBuild(self.project_id) response = cloud_build.CreateBuild(build_body) cloud_build.BlockOperation(response) logger.info('Image {0:s} exported to {1:s}.'.format( self.name, full_path))
def ExportImage(self, gcs_output_folder: str, output_name: Optional[str] = None) -> None: """Export compute image to Google Cloud storage. Exported image is compressed and stored in .tar.gz format. Args: gcs_output_folder (str): Folder path of the exported image. output_name (str): Optional. Name of the output file, must end with .tar.gz, if not exist, the [image_name].tar.gz will be used. Raises: RuntimeError: If exported image name is invalid. """ if output_name: if not bool(re.match("^[A-Za-z0-9-]*$", output_name)): raise RuntimeError( 'Destination disk name must comply with expression ^[A-Za-z0-9-]*$' ) full_path = '{0:s}.tar.gz'.format( os.path.join(gcs_output_folder, output_name)) else: full_path = '{0:s}.tar.gz'.format( os.path.join(gcs_output_folder, self.name)) build_body = { 'timeout': '86400s', 'steps': [{ 'args': [ '-source_image={0:s}'.format(self.name), '-destination_uri={0:s}'.format(full_path), '-client_id=api', ], 'name': 'gcr.io/compute-image-tools/gce_vm_image_export:release', 'env': [] }], 'tags': ['gce-daisy', 'gce-daisy-image-export'] } cloud_build = build.GoogleCloudBuild(self.project_id) response = cloud_build.CreateBuild(build_body) cloud_build.BlockOperation(response) common.LOGGER.info('Image {0:s} exported to {1:s}.'.format( self.name, full_path))
'projects/fake-target-project/logs/OSConfigAgent' ] FAKE_LOG_ENTRIES = [{ 'logName': 'test_log', 'timestamp': '123456789', 'textPayload': 'insert.compute.create' }, { 'logName': 'test_log', 'timestamp': '123456789', 'textPayload': 'insert.compute.create' }] FAKE_NEXT_PAGE_TOKEN = 'abcdefg1234567' FAKE_GCS = gcp_storage.GoogleCloudStorage('fake-target-project') FAKE_GCB = gcp_build.GoogleCloudBuild('fake-target-project') FAKE_MONITORING = gcp_monitoring.GoogleCloudMonitoring('fake-target-project') # Mock struct to mimic GCP's API responses MOCK_INSTANCES_AGGREGATED = { # See https://cloud.google.com/compute/docs/reference/rest/v1/instances # /aggregatedList for complete structure 'items': { 0: { 'instances': [{ 'name': FAKE_INSTANCE.name, 'zone': '/' + FAKE_INSTANCE.zone }] } } }
def ImportImageFromStorage(self, storage_image_path: str, image_name: Optional[str] = None, bootable: bool = False, os_name: Optional[str] = None, guest_environment: bool = True) -> 'GoogleComputeImage': # pylint: disable=line-too-long """Import GCE image from Cloud storage. The import tool supports raw disk images and most virtual disk file formats, valid import formats are: [raw (dd), qcow2, qcow , vmdk, vdi, vhd, vhdx, qed, vpc]. Args: storage_image_path (str): Path to the source image in Cloud Storage. image_name (str): Optional. Name of the imported image, default is "imported-image-" appended with a timestamp in "%Y%m%d%H%M%S" format. bootable (bool): Optional. True if the imported image is bootable. Default is False. If True the os_name must be specified. os_name (str): Optional. Name of the operating system on the bootable image. For supported versions please see: https://cloud.google.com/sdk/gcloud/reference/compute/images/import#--os # pylint: disable=line-too-long For known limitations please see: https://googlecloudplatform.github.io/compute-image-tools/image-import.html#compatibility-and-known-limitations # pylint: disable=line-too-long guest_environment (bool): Optional. Install Google Guest Environment on a bootable image. Relevant only if image is bootable. Default True. Returns: GoogleComputeImage: A Google Compute Image object. Raises: ValueError: If bootable is True and os_name not specified. InvalidNameError: If imported image name is invalid. """ supported_os = [ 'centos-6', 'centos-7', 'centos-8', 'debian-8', 'debian-9', 'opensuse-15', 'rhel-6', 'rhel-6-byol', 'rhel-7', 'rhel-7-byol', 'rhel-8', 'rhel-8-byol', 'sles-12-byol', 'sles-15-byol', 'ubuntu-1404', 'ubuntu-1604', 'ubuntu-1804', 'windows-10-x64-byol', 'windows-10-x86-byol', 'windows-2008r2', 'windows-2008r2-byol', 'windows-2012', 'windows-2012-byol', 'windows-2012r2', 'windows-2012r2-byol', 'windows-2016', 'windows-2016-byol', 'windows-2019', 'windows-2019-byol', 'windows-7-x64-byol', 'windows-7-x86-byol', 'windows-8-x64-byol', 'windows-8-x86-byol' ] if not bootable: img_type = '-data_disk' elif not os_name: raise ValueError('For bootable images, operating system name' ' (os_name) must be specified.') elif os_name not in supported_os: logger.warning( ('Operating system of the imported image is not within the ' 'supported list:\n{0:s}\nFor the up-to-date list please refer ' 'to:\n{1:s}').format( ', '.join(supported_os), 'https://cloud.google.com/sdk/gcloud/reference/compute/images/import#--os')) # pylint: disable=line-too-long else: img_type = '-os={0:s}'.format(os_name) if image_name: if not common.REGEX_DISK_NAME.match(image_name): raise errors.InvalidNameError( 'Imported image name {0:s} does not comply with {1:s}'. format(image_name, common.REGEX_DISK_NAME.pattern), __name__) image_name = image_name[:common.COMPUTE_NAME_LIMIT] else: image_name = common.GenerateUniqueInstanceName( 'imported-image', common.COMPUTE_NAME_LIMIT) args_list = [ '-image_name={0:s}'.format(image_name), '-source_file={0:s}'.format(storage_image_path), '-timeout=86400s', '-client_id=api', img_type ] if bootable and not guest_environment: args_list.append('-no_guest_environment') build_body = { 'steps': [{ 'args': args_list, 'name': 'gcr.io/compute-image-tools/gce_vm_image_import:release', 'env': ['BUILD_ID=$BUILD_ID'] }], 'timeout': '86400s', 'tags': ['gce-daisy', 'gce-daisy-image-import'] } cloud_build = build.GoogleCloudBuild(self.project_id) response = cloud_build.CreateBuild(build_body) cloud_build.BlockOperation(response) logger.info('Image {0:s} imported as GCE image {1:s}.'.format( storage_image_path, image_name)) return GoogleComputeImage(self.project_id, '', image_name)