Building VM images using Packer

Packer is an open source tool for creating identical Virtual Machine (VM) images for multiple platforms from a single source configuration. This page explains how to use Packer and Cloud Build to create a VM image for use on Compute Engine. If you're new to Cloud Build, read the quickstarts and the build configuration overview first.

Before you begin

The instructions on this page assume that you are familiar with Packer. In addition:

  • Have your source code including the Packer template handy.
  • If you want to use the gcloud commands in this page, install the gcloud command-line tool.
  • Enable the following APIs:

    gcloud services enable sourcerepo.googleapis.com
    gcloud services enable compute.googleapis.com
    gcloud services enable servicemanagement.googleapis.com
    gcloud services enable storage-api.googleapis.com
    

Required IAM permissions

To use Packer with Cloud Build, the Cloud Build service account requires the editor role. To grant the editor role:

  1. Locate the Cloud Build service account:

    CLOUD_BUILD_ACCOUNT=$(gcloud projects get-iam-policy $PROJECT --filter="(bindings.role:roles/cloudbuild.builds.builder)"  --flatten="bindings[].members" --format="value(bindings.members[])")
    
  2. Add the editor role to the account:

    gcloud projects add-iam-policy-binding $PROJECT \
      --member $CLOUD_BUILD_ACCOUNT \
      --role roles/editor
    

Creating a Packer builder image

Cloud Build provides a Packer community builder image that you can use to invoke packer commands in Cloud Build. Before using this builder in a Cloud Build config file, you must build the image and push it to the Container Registry in your project:

  1. Clone the cloud-builders-community repository:

    git clone https://github.com/GoogleCloudPlatform/cloud-builders-community.git
    
  2. Navigate to the Packer builder image:

    cd cloud-builders-community/packer
    
  3. Submit the builder to your project:

    gcloud builds submit .
    

Using the Packer builder

  1. In your project root directory, create a build config file named cloudbuild.yaml or cloudbuild.json.

  2. In your build config file, add a build step to invoke the packer build command:

    YAML

    steps:
    - name: 'gcr.io/[PROJECT_ID]/packer'
      args:
      - build
      - -var
      - image_name=[IMAGE_NAME]
      - -var
      - project_id=[PROJECT_ID]
      - -var
      - image_family=[IMAGE_FAMILY]
      - -var
      - image_zone=[IMAGE_ZONE]
      - packer.json
    

    JSON

    {
      "steps": [
       {
          "name": "gcr.io/[PROJECT_ID]/packer",
          "args": [
            "build",
            "-var",
            "image_name=[IMAGE_NAME]",
            "-var",
            "project_id=[PROJECT_ID]",
            "-var",
            "image_family=[IMAGE_FAMILY]",
            "-var",
            "image_zone=[IMAGE_ZONE]",
            "packer.json"
           ]
        }
       ]
    }
    

    Where:

    • [PROJECT_ID] is your Cloud project ID.
    • [IMAGE_NAME] is the name of the VM image you're building.
    • [IMAGE_FAMILY] is the image family of the VM image.
    • [IMAGE_ZONE] is the image zone.
  3. Start the build using the build config file:

    gcloud builds submit [CONFIG_FILE_PATH] [SOURCE_DIRECTORY]
    

    Where:

    • [CONFIG_FILE_PATH] is the path to the build config file.
    • [SOURCE_DIRECTORY] is the path or URL to the source code.

    If you don't specify a [CONFIG_FILE_PATH] and [SOURCE_DIRECTORY] in the gcloud builds submit command, Cloud Build assumes that the config file and the source code are in the current working directory.

Once the images are built, you can view them in the Compute Engine Image page in the Cloud Console.

What's next