Use startup scripts on Linux VMs

A startup script is a file that performs tasks during the startup process of a virtual machine (VM) instance. Startup scripts can apply to all VMs in a project or to a single VM. Startup scripts specified by VM-level metadata override startup scripts specified by project-level metadata, and startup scripts only run when a network is available. This document describes how to use startup scripts on Linux VM instances. For information about how to add a project-level startup script, see gcloud compute project-info add-metadata.

For Linux startup scripts, you can use bash or non-bash file. To use a non-bash file, designate the interpreter by adding a #! to the top of the file. For example, to use a Python 3 startup script, add #! /usr/bin/python3 to the top of the file.

If you specify a startup script by using one of the procedures in this document, Compute Engine does the following:

  1. Copies the startup script to the VM

  2. Sets run permissions on the startup script

  3. Runs the startup script as the root user when the VM boots

For information about the various tasks related to startup scripts and when to perform each one, see the Overview.

Prerequisites

To run scripts stored in metadata on a VM instance, the guest environment must be installed and running.

Before you begin

Metadata keys for Linux startup scripts

A startup script is passed to a VM from a location that is specified by a metadata key. A metadata key specifies whether the startup script is stored locally, stored in Cloud Storage, or passed directly to the VM. The metadata key that you use might also depend on the size of the startup script.

The following table shows the metadata keys that you can use for Linux startup scripts, and provides information about which key to use based on the storage location and size of the startup script.

Metadata key Use for
startup-script Passing a bash or non-bash startup script that is stored locally or added directly and that is up to 256 KB in size
startup-script-url Passing a bash or non-bash startup script that is stored in Cloud Storage and that is greater than 256 KB in size. The string you enter here is used as-is to run gcloud storage. If your startup-script-url contains space characters, then don't replace the spaces with %20 or add double quotes ("") to the startup-script-url string.

Order of execution of Linux startup scripts

You can use multiple startup scripts. Startup scripts stored locally or added directly execute before startup scripts that are stored in Cloud Storage. The following table shows, based on the metadata key, the order of execution of Linux startup scripts.

Metadata key Order of execution
startup-script First during each boot after the initial boot
startup-script-url Second during each boot after the initial boot

Passing a Linux startup script directly

You can add the contents of a startup script directly to a VM when you create the VM. The following procedures show how to create a VM with a startup script that installs Apache and creates a basic web page.

Permissions required for this task

To perform this task, you must have the following permissions:

Console

Passing a Linux startup script directly to a new VM

  1. In the Google Cloud console, go to the Create an instance page.

    Go to Create an instance

  2. To use a Linux operating system, do the following:

    1. In the navigation menu, click OS and storage.

    2. Click Change.

    3. In the Boot disk pane that appears, select a Linux operating system.

  3. To directly add a Linux startup script, do the following:

    1. In the navigation menu, click Advanced.

    2. In the Automation section, enter the following in the Startup script field:

      #! /bin/bash
      apt update
      apt -y install apache2
      cat <<EOF > /var/www/html/index.html
      <html><body><p>Linux startup script added directly.</p></body></html>
      EOF
      
  4. Optional: Specify other configuration options. For more information, see Configuration options during instance creation.

  5. To create and start the instance, click Create.

Passing a Linux startup script directly to an existing VM

  1. In the Google Cloud console, go to the VM instances page.

    Go to VM instances

  2. Click the Name of the instance.

  3. Click Edit.

  4. Under Automation, add the contents of your startup script.

Verifying the startup script

After the instance starts, view the external IP in a web browser to verify that the startup script created the website. You might have to wait about 1 minute for the sample startup script to finish.

gcloud

Passing a Linux startup script directly to a new VM

Pass the contents of a startup script directly to a VM when creating it by using the following gcloud compute instances create command.

gcloud compute instances create VM_NAME \
  --image-project=debian-cloud \
  --image-family=debian-10 \
  --metadata=startup-script='#! /bin/bash
  apt update
  apt -y install apache2
  cat <<EOF > /var/www/html/index.html
  <html><body><p>Linux startup script added directly.</p></body></html>
  EOF'

Replace VM_NAME with the name of the VM.

Passing a Linux startup script directly to an existing VM

Add the startup script directly to an existing VM by using the following gcloud compute instances add-metadata command:

gcloud compute instances add-metadata VM_NAME \
    --zone=ZONE \
    --metadata=startup-script='#! /bin/bash
    apt update
    apt -y install apache2
    cat <<EOF > /var/www/html/index.html
    <html><body><p>Linux startup script added directly.</p></body></html>
    EOF'

Replace the following:

  • VM_NAME: the name of the VM

  • ZONE: the zone of the VM

Verifying the startup script

After the VM starts, view the external IP in a web browser to verify that the startup script created the web site. You might have to wait about 1 minute for the sample startup script to finish.

REST

Passing a Linux startup script directly to a new VM

Pass the contents of a startup script directly to a VM when creating it by using the following instances.insert method.

POST https://compute.googleapis.com/compute/v1/projects/PROJECT_ID/zones/ZONE/instances

{
  ...
  "networkInterfaces": [
    {
      "accessConfigs": [
        {
          "type": "ONE_TO_ONE_NAT"
        }
      ]
    }
  ],
  "metadata": {
    "items": [
      {
        "key": "startup-script",
        "value": "#! /bin/bash\napt update\napt -y install apache2\ncat <<EOF > /var/www/html/index.html\n<html><body><p>Linux startup script added directly.</p></body></html>\nEOF"
      }
    ]
  },
  ...
}

Replace the following:

  • PROJECT_ID: the ID of the project where the VM exists.

  • ZONE: the zone to create the VM in.

Passing a Linux startup script directly to an existing VM

  1. Get the metadata.fingerprint value of the VM by using the instances.get method:

    GET https://compute.googleapis.com/compute/v1/projects/PROJECT_ID/zones/ZONE/instances/VM_NAME
    

    Replace the following:

    • PROJECT_ID: the ID of the project where the VM exists.

    • ZONE: the zone of the VM.

    • VM_NAME: the name of the VM.

  2. Pass the startup script by using the fingerprint value, along with the metadata key and value for the startup script, in a call to the instances.setMetadata method:

    POST https://compute.googleapis.com/compute/v1/projects/PROJECT_ID/zones/ZONE/instances/VM_NAME/setMetadata
    
    {
      "fingerprint": FINGERPRINT,
      "items": [
        {
          "key": "startup-script",
          "value": "#! /bin/bash\napt update\napt -y install apache2\ncat <<EOF > /var/www/html/index.html\n<html><body><p>Linux startup script added directly.</p></body></html>\nEOF"
        }
      ],
      ...
    }
    

    Replace the following:

    • PROJECT_ID: the ID of the project where the VM exists.

    • ZONE: the zone of the VM.

    • VM_NAME: the name of the VM.

    • FINGERPRINT: the metadata.fingerprint value obtained by using the instances.get method.

Verifying the startup script

After the VM starts, view the external IP in a web browser to verify that the startup script created the web site. You might have to wait about 1 minute for the sample startup script to finish.

Passing a Linux startup script from a local file

You can store a startup script in a local file on your workstation and pass the local file as metadata to a VM when you create it. You cannot use files stored on VMs as startup scripts.

Before passing a Linux startup script from a local file to a VM, do the following:

  1. Create a local file to store the startup script.

  2. Note the relative path from gcloud CLI to the startup script.

  3. Add the following startup script to the file:

    #! /bin/bash
    apt update
    apt -y install apache2
    cat <<EOF > /var/www/html/index.html
    <html><body><p>Linux startup script from a local file.</p></body></html>
    EOF