Using secrets from Secret Manager

This page explains how to include sensitive information such as passwords and API keys in Cloud Build.

Secret Manager is a Google Cloud service that securely stores API keys, passwords, and other sensitive data. To include sensitive information in your builds, you can store the information in Secret Manager and then configure your build to access the information from Secret Manager.

Before you begin

  • Enable the Cloud Build and Secret Manager APIs.

    Enable the APIs

  • To use the command-line examples in this guide, install and configure the Cloud SDK.

  • Make sure you've stored the secret in Secret Manager. For instructions, see Creating a secret.

    • Note down the secret name and secret version of your secret. You'll need this information to configure Cloud Build to access the secret.

Required IAM permissions

Grant the Secret Manager Secret Accessor (roles/secretmanager.secretAccessor) IAM role for the secret to the Cloud Build service account:

  1. Open the Secret Manager page in the Google Cloud Console:

    Go to the Secret Manager page

  2. Select the checkbox of the secret you wish to use in your build.

  3. If it is not already open, click Show info panel to open the panel.

  4. In the panel, under Permissions, click Add member.

  5. In the New members textbox, enter the email address of your Cloud Build service account of the form PROJECT_NUMBER@cloudbuild.gserviceaccount.com. PROJECT_NUMBER is the project number of the project where you are running builds. You can find the project number in your Project settings page.

  6. In the Select a role drop-down box, select Secret Manager Secret Accessor.

  7. Click Save.

Configuring builds to access the secret from Secret Manager

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

  2. In the build config file:

    • Add an availableSecrets field to specify the secret version and environment variables to use for your secret. You can specify more than one secret in a build.
    • In the build step where you want to specify the secret:
      • Add an entrypoint field pointing to bash to use the bash tool in the build step. This is required to refer to the environment variable for the secret.
      • Add a secretEnv field specifying the environment variable.
      • In the args field, add a -c flag as the first argument. Any string you pass after -c is treated as a command. For more information on running bash commands with -c, see the bash documentation.
      • When specifying the secret in the args field, specify it using the environment variable prefixed with $$.

    The following example build config file shows how to login to Docker using the Docker username and password stored in Secret Manager.

    YAML

    steps:
    - name: 'gcr.io/cloud-builders/docker'
      entrypoint: 'bash'
      args: ['-c', 'docker login --username=$$USERNAME --password=$$PASSWORD']
      secretEnv: ['USERNAME', 'PASSWORD']
    availableSecrets:
      secretManager:
      - versionName: projects/PROJECT_ID/secrets/DOCKER_PASSWORD_SECRET_NAME/versions/DOCKER_PASSWORD_SECRET_VERSION
        env: 'PASSWORD'
      - versionName: projects/PROJECT_ID/secrets/DOCKER_USERNAME_SECRET_NAME/versions/DOCKER_USERNAME_SECRET_VERSION
        env: 'USERNAME'
    

    JSON

    {
      "steps": [
      {
        "name": "gcr.io/cloud-builders/docker",
        "entrypoint": "bash",
        "args": [
          "-c",
          "docker login --username=$$USERNAME --password=$$PASSWORD"
        ],
        "secretEnv": [
          "USERNAME",
          "PASSWORD"
        ]
      }
      ],
      "availableSecrets": {
        "secretManager": [{
          "versionName": "projects/PROJECT_ID/secrets/DOCKER_PASSWORD_SECRET_NAME/versions/DOCKER_PASSWORD_SECRET_VERSION",
          "env": "PASSWORD"
      }, {
        "versionName": "projects/PROJECT_ID/secrets/DOCKER_USERNAME_SECRET_NAME/versions/DOCKER_USERNAME_SECRET_VERSION",
        "env": "USERNAME"
         }]
      }
    }
    

    Replace the placeholder values in the above commands with the following:

    • PROJECT_ID: The ID of the Cloud project where you've stored your secrets.
    • DOCKER_USERNAME_SECRET_NAME: The secret name corresponding to your Docker username. You can get the secret name from the Secret Manager page in the Cloud Console.
    • DOCKER_USERNAME_SECRET_VERSION: The secret version of your Docker username. You can get the secret version by clicking on a secret name on the Secret Manager page in the Cloud Console.
    • DOCKER_PASSWORD_SECRET_NAME: The secret name corresponding to your Docker password. You can get the secret name from the Secret Manager page in the Cloud Console.
    • DOCKER_PASSWORD_SECRET_VERSION: The secret version of your Docker password. You can get the secret version by clicking on a secret name on the Secret Manager page in the Cloud Console.
  3. Use the build config file to manually start a build or to automate builds using triggers.

Example: authenticating to Docker

In some situations, before interacting with Docker images, your build would need to authenticate to Docker. For example, Docker authentication is required for builds to pull private images and push private or public images to Docker Hub. In these cases, you can store your Docker username and password in Secret Manager and then configure Cloud Build to access the username and password from Secret Manager. For instructions on doing this see Interacting with Docker Hub images.

Example: GitHub pull request creation

Another example where you might want to configure your build to access a sensitive information from Secret Manager is for creating a GitHub pull request in response to builds. To do this:

  • Create a GitHub token.
  • Store the GitHub token in Secret Manager.
  • In your build config file:
  • Create a GitHub app trigger and use the build config file to invoke the trigger.

The following example config file shows how to create a GitHub pull request using the GitHub token:

YAML

steps:
- name: 'launcher.gcr.io/google/ubuntu1604'
  id: Create GitHub pull request
  entrypoint: bash
  args:
  - -c
  - curl -X POST -H "Authorization:Bearer $$GH_TOKEN" -H 'Accept:application/vnd.github.v3+json' https://api.github.com/repos/GITHUB_USERNAME/REPO_NAME/pulls -d '{"head":"HEAD_BRANCH","base":"BASE_BRANCH", "title":"NEW_PR"}'
  secretEnv: ['GH_TOKEN']
availableSecrets:
  secretManager:
  - versionName: projects/PROJECT_ID/secrets/GH_TOKEN_SECRET_NAME/versions/latest
    env: GH_TOKEN

JSON

{
  "steps": [
  {
    "name": "launcher.gcr.io/google/ubuntu1604",
    "id": "Create GitHub pull request",
    "entrypoint": "bash",
    "args": [
      "-c",
       "curl -X POST -H \"Authorization:Bearer $$GH_TOKEN\" -H 'Accept:application/vnd.github.v3+json' https://api.github.com/repos/GITHUB_USERNAME/REPO_NAME -d '{\"head\":\"HEAD_BRANCH\",\"base\":\"BASE_BRANCH\", \"title\":\"NEW_PR\"}'
    ],
    "secretEnv": ['GH_TOKEN']
}
],
"availableSecrets": {
  "secretManager": [
  {
    "versionName": "projects/PROJECT_ID/secrets/GH_TOKEN_SECRET_NAME/versions/latest",
    "env": "GH_TOKEN"
  }
  ]
}
}

Replace the placeholder values in the above commands with the following:

  • PROJECT_ID: The ID of the Cloud project where you've stored your secrets.
  • GITHUB_USERNAME: The GitHub username of the repository owner.
  • REPO_NAME: The name of the GitHub repository.
  • HEAD_BRANCH: The name of the branch where the changes are implemented. For cross-repository pull requests in the same network, namespace head with a user like this: username:branch.
  • BASE_BRANCH: The name of the branch you want the changes pulled into. This should be an existing branch on the current repository. You cannot submit a pull request to one repository that requests a merge to a base of another repository.
  • GH_TOKEN_SECRET_NAME: The secret name corresponding to your GitHub token.
  • NEW_PR: The new pull request you want to create.

What's next