Skip to content
This repository was archived by the owner on Dec 31, 2023. It is now read-only.

Commit 34092b5

Browse files
authored
docs(samples): Adding samples for instance from template creation (#159)
* docs(samples): Adding samples for instance from template creation
1 parent 4010cb4 commit 34092b5

File tree

2 files changed

+233
-0
lines changed

2 files changed

+233
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
# Copyright 2021 Google LLC
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
# [START compute_instances_create_from_template]
16+
# [START compute_instances_create_from_template_with_overrides]
17+
from google.cloud import compute_v1
18+
# [END compute_instances_create_from_template_with_overrides]
19+
20+
21+
def create_instance_from_template(
22+
project_id: str, zone: str, instance_name: str, instance_template_url: str
23+
) -> compute_v1.Instance:
24+
"""
25+
Creates a Compute Engine VM instance from an instance template.
26+
27+
Args:
28+
project_id: ID or number of the project you want to use.
29+
zone: Name of the zone you want to check, for example: us-west3-b
30+
instance_name: Name of the new instance.
31+
instance_template_url: URL of the instance template used for creating the new instance.
32+
It can be a full or partial URL.
33+
Examples:
34+
- https://www.googleapis.com/compute/v1/projects/project/global/instanceTemplates/example-instance-template
35+
- projects/project/global/instanceTemplates/example-instance-template
36+
- global/instanceTemplates/example-instance-template
37+
38+
Returns:
39+
Instance object.
40+
"""
41+
operation_client = compute_v1.ZoneOperationsClient()
42+
instance_client = compute_v1.InstancesClient()
43+
44+
instance_insert_request = compute_v1.InsertInstanceRequest()
45+
instance_insert_request.project = project_id
46+
instance_insert_request.zone = zone
47+
instance_insert_request.source_instance_template = instance_template_url
48+
instance_insert_request.instance_resource.name = instance_name
49+
50+
op = instance_client.insert(instance_insert_request)
51+
operation_client.wait(project=project_id, zone=zone, operation=op.name)
52+
53+
return instance_client.get(project=project_id, zone=zone, instance=instance_name)
54+
55+
56+
# [END compute_instances_create_from_template]
57+
58+
59+
# [START compute_instances_create_from_template_with_overrides]
60+
def create_instance_from_template_with_overrides(
61+
project_id: str,
62+
zone: str,
63+
instance_name: str,
64+
instance_template_name: str,
65+
machine_type: str,
66+
new_disk_source_image: str,
67+
) -> compute_v1.Instance:
68+
"""
69+
Creates a Compute Engine VM instance from an instance template, changing the machine type and
70+
adding a new disk created from a source image.
71+
72+
Args:
73+
project_id: ID or number of the project you want to use.
74+
zone: Name of the zone you want to check, for example: us-west3-b
75+
instance_name: Name of the new instance.
76+
instance_template_name: Name of the instance template used for creating the new instance.
77+
machine_type: Machine type you want to set in following format:
78+
"zones/{zone}/machineTypes/{type_name}". For example:
79+
- "zones/europe-west3-c/machineTypes/f1-micro"
80+
- You can find the list of available machine types using:
81+
https://cloud.google.com/sdk/gcloud/reference/compute/machine-types/list
82+
newDiskSourceImage: Path the the disk image you want to use for your new
83+
disk. This can be one of the public images
84+
(like "projects/debian-cloud/global/images/family/debian-10")
85+
or a private image you have access to.
86+
For a list of available public images, see the documentation:
87+
http://cloud.google.com/compute/docs/images
88+
89+
Returns:
90+
Instance object.
91+
"""
92+
operation_client = compute_v1.ZoneOperationsClient()
93+
instance_client = compute_v1.InstancesClient()
94+
instance_template_client = compute_v1.InstanceTemplatesClient()
95+
96+
# Retrieve an instance template by name.
97+
instance_template = instance_template_client.get(
98+
project=project_id, instance_template=instance_template_name
99+
)
100+
101+
# Adjust diskType field of the instance template to use the URL formatting required by instances.insert.diskType
102+
# For instance template, there is only a name, not URL.
103+
for disk in instance_template.properties.disks:
104+
if disk.initialize_params.disk_type:
105+
disk.initialize_params.disk_type = (
106+
f"zones/{zone}/diskTypes/{disk.initialize_params.disk_type}"
107+
)
108+
109+
instance = compute_v1.Instance()
110+
instance.name = instance_name
111+
instance.machine_type = machine_type
112+
instance.disks = instance_template.properties.disks
113+
114+
new_disk = compute_v1.AttachedDisk()
115+
new_disk.initialize_params.disk_size_gb = 50
116+
new_disk.initialize_params.source_image = new_disk_source_image
117+
new_disk.auto_delete = True
118+
new_disk.boot = False
119+
new_disk.type_ = compute_v1.AttachedDisk.Type.PERSISTENT
120+
121+
instance.disks.append(new_disk)
122+
123+
instance_insert_request = compute_v1.InsertInstanceRequest()
124+
instance_insert_request.project = project_id
125+
instance_insert_request.zone = zone
126+
instance_insert_request.instance_resource = instance
127+
instance_insert_request.source_instance_template = instance_template.self_link
128+
129+
op = instance_client.insert(instance_insert_request)
130+
operation_client.wait(project=project_id, zone=zone, operation=op.name)
131+
132+
return instance_client.get(project=project_id, zone=zone, instance=instance_name)
133+
134+
135+
# [END compute_instances_create_from_template_with_overrides]
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
# Copyright 2021 Google LLC
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
import uuid
15+
16+
import google.auth
17+
from google.cloud import compute_v1
18+
import pytest
19+
20+
from quickstart import delete_instance
21+
from sample_instance_from_template import (
22+
create_instance_from_template,
23+
create_instance_from_template_with_overrides,
24+
)
25+
26+
27+
PROJECT = google.auth.default()[1]
28+
INSTANCE_ZONE = "us-central1-b"
29+
30+
31+
@pytest.fixture
32+
def instance_template():
33+
disk = compute_v1.AttachedDisk()
34+
initialize_params = compute_v1.AttachedDiskInitializeParams()
35+
initialize_params.source_image = (
36+
"projects/debian-cloud/global/images/family/debian-11"
37+
)
38+
initialize_params.disk_size_gb = 25
39+
disk.initialize_params = initialize_params
40+
disk.auto_delete = True
41+
disk.boot = True
42+
43+
network_interface = compute_v1.NetworkInterface()
44+
network_interface.name = "global/networks/default"
45+
46+
template = compute_v1.InstanceTemplate()
47+
template.name = "test-template-" + uuid.uuid4().hex[:10]
48+
template.properties.disks = [disk]
49+
template.properties.machine_type = "e2-standard-4"
50+
template.properties.network_interfaces = [network_interface]
51+
52+
template_client = compute_v1.InstanceTemplatesClient()
53+
operation_client = compute_v1.GlobalOperationsClient()
54+
op = template_client.insert(project=PROJECT, instance_template_resource=template)
55+
operation_client.wait(project=PROJECT, operation=op.name)
56+
57+
template = template_client.get(project=PROJECT, instance_template=template.name)
58+
59+
yield template
60+
61+
op = template_client.delete(project=PROJECT, instance_template=template.name)
62+
operation_client.wait(project=PROJECT, operation=op.name)
63+
64+
65+
@pytest.fixture()
66+
def autodelete_instance_name():
67+
instance_name = "test-instance-" + uuid.uuid4().hex[:10]
68+
yield instance_name
69+
delete_instance(PROJECT, INSTANCE_ZONE, instance_name)
70+
71+
72+
def test_create_instance_from_template(instance_template, autodelete_instance_name):
73+
instance = create_instance_from_template(
74+
PROJECT, INSTANCE_ZONE, autodelete_instance_name, instance_template.self_link
75+
)
76+
77+
assert instance.name == autodelete_instance_name
78+
assert instance.zone.endswith(INSTANCE_ZONE)
79+
80+
81+
def test_create_instance_from_template_override(
82+
instance_template, autodelete_instance_name
83+
):
84+
image_client = compute_v1.ImagesClient()
85+
86+
image = image_client.get_from_family(project="centos-cloud", family="centos-8")
87+
instance = create_instance_from_template_with_overrides(
88+
PROJECT,
89+
INSTANCE_ZONE,
90+
autodelete_instance_name,
91+
instance_template.name,
92+
f"zones/{INSTANCE_ZONE}/machineTypes/n2-standard-2",
93+
image.self_link,
94+
)
95+
96+
assert instance.name == autodelete_instance_name
97+
assert instance.machine_type.endswith("n2-standard-2")
98+
assert len(instance.disks) == 2

0 commit comments

Comments
 (0)