【问题标题】:How to authenticate firebase cloud functions in Functions Emulator using the users stored in Firebase Authentication emulator?如何使用存储在 Firebase 身份验证模拟器中的用户在 Functions Emulator 中验证 Firebase 云功能?
【发布时间】:2021-05-18 04:08:02
【问题描述】:

我的 firebase 云函数包含受保护的路由,只有在请求标头中传递有效的 IdToken 时才能访问这些路由。云函数 API 是这样的

functions/index.js


const functions = require('firebase-functions');
const admin = require('firebase-admin');

admin.initializeApp({
  credential: admin.credential.applicationDefault(),
  databaseURL: "DB_URL"
});

const express = require('express');
const app = express();


const authenticate = async (req, res, next) => {
  if (!req.headers.authorization || !req.headers.authorization.startsWith('Bearer ')) {
    res.status(403).send('Unauthorized');
    return;
  }
  const idToken = req.headers.authorization.split('Bearer ')[1];
  try {
    const decodedIdToken = await admin.auth().verifyIdToken(idToken);
    req.user = decodedIdToken;
    next();
    return;
  } catch(e) {
    res.status(403).send('Unauthorized');
    return;
  }
};

app.use(authenticate);


app.get('/protected', async (req, res) => {
    return res.send('OK');
});

exports.api = functions.https.onRequest(app);

最初,我使用 Firebase 身份验证来创建新用户并获取 IdToken

Creating new user

curl 'https://identitytoolkit.googleapis.com/v1/accounts:signUp?key=[API_KEY]' \
-H 'Content-Type: application/json' \
--data-binary '{"email":"[user@example.com]","password":"[PASSWORD]","returnSecureToken":true}'

Getting IdToken 这样我就可以将它传递给 firebase 云函数以访问受保护的路由

curl 'https://identitytoolkit.googleapis.com/v1/accounts:signInWithPassword?key=[API_KEY]' \
-H 'Content-Type: application/json' \
--data-binary '{"email":"[user@example.com]","password":"[PASSWORD]","returnSecureToken":true}'

使用这种方法调用我受保护的云函数工作正常

curl --location --request GET 'http://localhost:5001/abc-production/us-central1/api/protected/' \
--header 'Authorization: Bearer SECRET_ID_TOKEN'

现在,我想使用身份验证模拟器来创建新用户并生成 IdToken,而不是使用 Firebase 身份验证。

我可以使用身份验证模拟器 UI 创建新用户,但如何生成这些用户的访问令牌?是否有任何 API 端点可以返回本地保存的用户的 IdToken,以便我可以测试受保护的 API 而无需在生产中添加用户?

另外,当我运行身份验证模拟器时,使用生产 Firebase 身份验证环境生成的 IdToken 不起作用。

"code": "auth/argument-error",
        "message": "Firebase ID token has invalid signature. See https://firebase.google.com/docs/auth/admin/verify-id-tokens for details on how to retrieve an ID token."

【问题讨论】:

    标签: firebase-authentication google-cloud-functions firebase-tools


    【解决方案1】:

    模拟器仅用于本地测试,不用于生产,您不能使用模拟器颁发的 IdToken 访问 Firebase 函数等其他服务,因为正如 documentation 所说:

    出于安全原因,身份验证模拟器发出未签名的 ID 只接受 verifyIdToken 和 createSessionCookie 的令牌 在 Cloud Functions 中运行时的 Firebase Admin SDK 模拟器。

    因此,这些令牌仅在模拟器环境中有效,如果您想将它们与 Firebase Function 一起使用,您只能通过 Functions 模拟器来执行此操作。查看this guide 了解如何在本地运行函数。

    【讨论】:

    • 我也在模拟器中运行 firebase 功能。只是我的所有功能都受到保护,只能通过在身份验证标头中传递有效令牌来访问它们。我的问题是如何为存储在 auth 模拟器中的用户生成 accessToken。我不想在生产环境中创建用户只是为了在本地环境中测试我的功能
    • 你可以尝试这里提到的解决方案 --> How to get an idToken that is valid for development from firebase without having to spin up my frontend? 在其中你只需要在你的函数中伪造一个用户的创建并为该用户发回令牌
    • 该答案建议使用firebase/app,但据我所知,它只能在前端环境中使用。不过谢谢!感谢您的帮助。
    • 你是对的,这将在客户端而不是在你的函数中创建一个用户,但这个想法仍然适用,因为你可以在你的应用程序中使用从这个示例生成的令牌用于测试目的。跨度>
    • 这是一种方法,但我不想再依赖前端来测试我的后端服务。我创建了两个不同的 firebase 项目,一个用于生产,另一个用于开发,还摆脱了模拟器
    猜你喜欢
    • 1970-01-01
    • 2019-12-02
    • 2021-10-08
    • 2018-01-11
    • 2021-04-22
    • 1970-01-01
    • 2020-10-25
    • 2017-06-07
    • 2021-07-30
    相关资源
    最近更新 更多