Firebase 驗證觸發條件

Cloud Run 函式可由 Firebase 驗證事件觸發,前提是該事件與函式位於相同的Google Cloud 專案中。這些事件包括使用者建立和刪除。舉例來說,您可以向剛在應用程式中建立帳戶的使用者傳送歡迎電子郵件。

事件類型

Firebase 驗證可根據使用者的 createdelete 事件觸發函式。

事件類型 觸發條件
providers/firebase.auth/eventTypes/user.create 在建立使用者帳戶時觸發。
providers/firebase.auth/eventTypes/user.delete 在刪除使用者帳戶時觸發。

建立使用者

Firebase 帳戶會在以下情況下,觸發 Cloud Run 函式的使用者建立事件:

  • 使用者建立電子郵件帳戶與密碼。

  • 使用者使用聯合識別資訊提供者第一次登入。

  • 開發人員使用 Firebase Admin SDK 建立帳戶。

  • 使用者第一次登入新匿名驗證工作階段。

刪除使用者

您也可以設定函式,在使用者刪除時觸發。

事件結構

事件資料會以 UserRecord 物件的形式提供。

以下是以密碼為基礎的帳戶建立事件範例:

{
  "email": "me@example.com",
  "metadata": {
      "createdAt": "2018-10-19T19:29:16Z"
  },
  "uid": "XXXXX"
}

這個物件的部分屬性僅在使用特定驗證方法時定義。舉例來說,以密碼為基礎的帳戶事件會定義包含使用者電子郵件地址的 email 資源。uid 屬性 (包含專屬於專案的使用者 ID) 一律會定義。

程式碼範例

Node.js

/**
 * Background Function triggered by a change to a Firebase Auth user object.
 *
 * @param {!Object} event The Cloud Functions event.
 */
exports.helloAuth = event => {
  try {
    console.log(`Function triggered by change to user: ${event.uid}`);
    console.log(`Created at: ${event.metadata.createdAt}`);

    if (event.email) {
      console.log(`Email: ${event.email}`);
    }
  } catch (err) {
    console.error(err);
  }
};

Python

import json

def hello_auth(data, context):
    """Triggered by creation or deletion of a Firebase Auth user object.
    Args:
           data (dict): The event payload.
           context (google.cloud.functions.Context): Metadata for the event.
    """
    print("Function triggered by creation/deletion of user: %s" % data["uid"])
    print("Created at: %s" % data["metadata"]["createdAt"])

    if "email" in data:
        print("Email: %s" % data["email"])

Go


// Package firebase contains a Firestore Cloud Function.
package firebase

import (
	"context"
	"log"
	"time"
)

// AuthEvent is the payload of a Firestore Auth event.
type AuthEvent struct {
	Email    string `json:"email"`
	Metadata struct {
		CreatedAt time.Time `json:"createdAt"`
	} `json:"metadata"`
	UID string `json:"uid"`
}

// HelloAuth is triggered by Firestore Auth events.
func HelloAuth(ctx context.Context, e AuthEvent) error {
	log.Printf("Function triggered by creation or deletion of user: %q", e.UID)
	log.Printf("Created at: %v", e.Metadata.CreatedAt)
	if e.Email != "" {
		log.Printf("Email: %q", e.Email)
	}
	return nil
}

Java

import com.google.cloud.functions.Context;
import com.google.cloud.functions.RawBackgroundFunction;
import com.google.gson.Gson;
import com.google.gson.JsonObject;
import java.util.logging.Logger;

public class FirebaseAuth implements RawBackgroundFunction {
  private static final Logger logger = Logger.getLogger(FirebaseAuth.class.getName());

  // Use GSON (https://github.com/google/gson) to parse JSON content.
  private static final Gson gson = new Gson();

  @Override
  public void accept(String json, Context context) {
    JsonObject body = gson.fromJson(json, JsonObject.class);

    if (body != null && body.has("uid")) {
      logger.info("Function triggered by change to user: " + body.get("uid").getAsString());
    }

    if (body != null && body.has("metadata")) {
      JsonObject metadata = body.get("metadata").getAsJsonObject();
      logger.info("Created at: " + metadata.get("createdAt").getAsString());
    }

    if (body != null && body.has("email")) {
      logger.info("Email: " + body.get("email").getAsString());
    }
  }
}

C#

using CloudNative.CloudEvents;
using Google.Cloud.Functions.Framework;
using Google.Events.Protobuf.Firebase.Auth.V1;
using Microsoft.Extensions.Logging;
using System.Threading;
using System.Threading.Tasks;

namespace FirebaseAuth;

public class Function : ICloudEventFunction<AuthEventData>
{
    private readonly ILogger _logger;

    public Function(ILogger<Function> logger) =>
        _logger = logger;

    public Task HandleAsync(CloudEvent cloudEvent, AuthEventData data, CancellationToken cancellationToken)
    {
        _logger.LogInformation("Function triggered by change to user: {uid}", data.Uid);
        if (data.Metadata is UserMetadata metadata)
        {
            _logger.LogInformation("User created at: {created:s}", metadata.CreateTime.ToDateTimeOffset());
        }
        if (!string.IsNullOrEmpty(data.Email))
        {
            _logger.LogInformation("Email: {email}", data.Email);
        }

        // In this example, we don't need to perform any asynchronous operations, so the
        // method doesn't need to be declared async.
        return Task.CompletedTask;
    }
}

Ruby

require "functions_framework"

# Triggered by creation or deletion of a Firebase Auth user object.
FunctionsFramework.cloud_event "hello_auth" do |event|
  # Event-triggered Ruby functions receive a CloudEvents::Event::V1 object.
  # See https://cloudevents.github.io/sdk-ruby/latest/CloudEvents/Event/V1.html
  # The Firebase event payload can be obtained from the `data` field.
  payload = event.data

  logger.info "Function triggered by creation/deletion of user: #{payload['uid']}"
  logger.info "Created at: #{payload['metadata']['createdAt']}"
  logger.info "Email: #{payload['email']}" if payload.key? "email"
end

PHP

use Google\CloudFunctions\CloudEvent;

function firebaseAuth(CloudEvent $cloudevent)
{
    $log = fopen(getenv('LOGGER_OUTPUT') ?: 'php://stderr', 'wb');
    $data = $cloudevent->getData();

    fwrite(
        $log,
        'Function triggered by change to user: ' . $data['uid'] . PHP_EOL
    );
    fwrite($log, 'Created at: ' . $data['metadata']['createTime'] . PHP_EOL);

    if (isset($data['email'])) {
        fwrite($log, 'Email: ' . $data['email'] . PHP_EOL);
    }
}

部署函式

如要部署函式,您需要指定事件類型以及您已針對其設定 Firebase 驗證的專案。在 Google Cloud 控制台中,事件類型只有一個欄位,因為系統會假設專案與包含函式的專案相同。

但是在指令列中,您必須使用特定字串指定這兩個參數。以下 gcloud 指令會部署由使用者 create 事件觸發的函式:

gcloud functions deploy FUNCTION_NAME \
  --no-gen2 \
  --entry-point ENTRY_POINT \
  --trigger-event providers/firebase.auth/eventTypes/user.create \
  --trigger-resource YOUR_PROJECT_ID \
  --runtime RUNTIME
引數 說明
FUNCTION_NAME 您要部署的 Cloud Run 函式註冊名稱。這可以是原始碼中的函式名稱,也可以是任意字串。如果 FUNCTION_NAME 是任意字串,則必須加入 --entry-point 旗標。
--entry-point ENTRY_POINT 原始碼中函式或類別的名稱。選用,除非您未使用 FUNCTION_NAME 指定要於部署期間執行的原始碼中的函式。在這種情況下,您必須使用 --entry-point 提供可執行函式的名稱。
--trigger-event NAME 觸發函式的事件類型名稱。在這種情況下,應為建立或刪除上述的其中一個選項。
--trigger-resource NAME 專案 ID (在本例中為 YOUR_PROJECT_ID),適用於含有函式和 Firebase 驗證的專案。
--runtime RUNTIME 您使用的執行階段名稱。如需完整清單,請參閱 gcloud 參考資料