如何使用带有替换的 Google Cloud Build 部署 Google Cloud Function

How to deploy a Google Cloud Function using Google Cloud Build with substitutions

我正在尝试使用 Google Cloud Build(包括替换)部署 Google Cloud Function。

但是,我在构建时收到错误消息:

ERROR: (gcloud.functions.deploy) OperationError: code=3, message=Function failed on loading user code. Error message: Provided module can't be loaded.
Detailed stack trace: Error: Incoming webhook URL is required

我的 cloudbuild.yaml 文件包含:

steps:

# This step builds the container image.
- name: 'gcr.io/cloud-builders/gcloud'
  id: Deploy
  args: ['functions', 'deploy', 'subscribeSlack', '--trigger-topic', 'cloud-builds', '--runtime', 'nodejs10', '--set-env-vars', '"SLACK_WEBHOOK_URL=${_SLACK_WEBHOOK_URL}"', '--region', '${_REGION}']
  env: 
    - 'SLACK_WEBHOOK_URL=${_SLACK_WEBHOOK_URL}'

而且,我已经通过 Google Cloud Console 在触发器中添加了替换: screenshot of build trigger with substitutions filled in.

该函数本身基于 Google 文档中的 the example

const { IncomingWebhook } = require('@slack/webhook');
const url = process.env.SLACK_WEBHOOK_URL;

const webhook = new IncomingWebhook(url);

// subscribeSlack is the main function called by Cloud Functions.
module.exports.subscribeSlack = (pubSubEvent, context) => {
  const build = eventToBuild(pubSubEvent.data);

  // Skip if the current status is not in the status list.
  // Add additional statuses to list if you'd like:
  // QUEUED, WORKING, SUCCESS, FAILURE,
  // INTERNAL_ERROR, TIMEOUT, CANCELLED
  const status = ['SUCCESS', 'FAILURE', 'INTERNAL_ERROR', 'TIMEOUT'];
  if (status.indexOf(build.status) === -1) {
    return;
  }

  // Send message to Slack.
  const message = createSlackMessage(build);
  webhook.send(message);
};

// eventToBuild transforms pubsub event message to a build object.
const eventToBuild = (data) => {
  return JSON.parse(Buffer.from(data, 'base64').toString());
}

// createSlackMessage creates a message from a build object.
const createSlackMessage = (build) => {
  console.log(JSON.stringify(build));
  const message = {
    text: `Build \`${build.status}\``,
    mrkdwn: true,
    attachments: [
      {
        title: 'Build logs',
        title_link: build.logUrl,
        fields: [{
          title: 'Status',
          value: build.status
        }]
      }
    ]
  };

  if(build.source.repoSource.repoName !== undefined)
    message.attachments[0].fields.push({ title: "Repo", value: build.source.repoSource.repoName });

  if(build.finishTime !== undefined)
    message.attachments[0].fields.push({ title: "Finished", value: (new Date(build.finishTime)).toLocaleString('en-GB', {timeZone: "Australia/Brisbane"}) });

  return message;
}

该函数可以从 gcloud cli 正常部署,但仅在使用 Cloud Build 时失败。

我检查了 cloudbuild.yaml,我发现在 SLACK_WEBHOOK_URL=${_SLACK_WEBHOOK_URL} 周围有双引号和单引号会生成这个问题,去掉双引号似乎可以解决。

我附上修改后的cloudbuild.yaml

steps:
# This step builds the container image.
- name: 'gcr.io/cloud-builders/gcloud'
  id: Deploy
  args: ['functions', 'deploy', 'subscribeSlack', '--trigger-topic', 'cloud-builds', '--runtime', 'nodejs10', '--set-env-vars', 'SLACK_WEBHOOK_URL=${_SLACK_WEBHOOK_URL}', '--region', '${_REGION}']
  env:
    - 'SLACK_WEBHOOK_URL=${_SLACK_WEBHOOK_URL}'