【问题标题】:Firebase HTTP Cloud Function error 'Cannot GET /'Firebase HTTP 云函数错误“无法获取 /”
【发布时间】:2019-11-21 09:31:16
【问题描述】:

我正在尝试从 firebase 获取用户数据,但我不断收到“CANNOT GET /”错误。

//firebase init
const functions = require('firebase-functions');
const admin = require("firebase-admin");
admin.initializeApp();

//express and cors init
const express = require('express');
const cors = require('cors');

//middleware init
const app = express();
app.use(cors());

const database = admin.database();

app.get("/users", function (request, response) {
    return database.ref('/users').on("value", snapshot => {
        return response.status(200).send(snapshot.val());
    }, error => { 
        console.error(database);
        return response.status(500).send(err);
    })
});

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

我还尝试使用我所指的另一个网站的另一个函数来获取至少用户名,但它返回错误。

exports.users = functions.https.onRequest((req, res) => {
     database().ref('/merchants').once('value').then(function(snapshot) {
       var username = snapshot.val().username;
       res.status(200).send(username);
     });
});

【问题讨论】:

    标签: node.js firebase express google-cloud-functions


    【解决方案1】:

    问题一:导出快递应用

    当您通过 Cloud Function 导出 express 应用程序时,路径将相对于导出的函数名称。您将您的应用导出为exports.users,这会将您的函数的根路径设置为/users,要调用它,您将访问https://us-central1-<project-id>.cloudfunctions.net/users

    但是,由于您也为/users 定义了一个路由处理程序(使用app.get("/users", ...)),因此您改为为https://us-central1-<project-id>.cloudfunctions.net/users/users 添加了一个处理程序。

    抛出错误 Cannot GET / 是因为当您在 https://us-central1-<project-id>.cloudfunctions.net/users 调用函数时,相对 URL 设置为 "/",而您尚未为其配置处理程序(使用 app.get("/", ...))。

    所以要修复上面的代码,请更改

    app.get("/users", function (request, response) {
    

    app.get("/", function (request, response) {
    

    问题 2:用户名查询

    问题可能很简单,只需调用database() 而不是admin.database()

    但是,此查询的目的尚不清楚,因此我假设您有一个商家 ID,并且您正在尝试获取该特定商家所有者的用户名。

    这意味着数据结构类似于:

    {
      "users": {
        "somePerson": { ... },
        "otherPerson: { ... }
      },
      "merchants": {
        "reallyGreatGuyInc": {
          "username": "somePerson",
          ...
        },
        "realShadyPeopleInc": {
          "username": "otherPerson",
          ...
        }
      }
    }
    

    如果您导出了一个名为 getMerchantUsername 的函数,您通过 GET 参数传入商家 ID 并在 URL https://us-central1-<project-id>.cloudfunctions.net/getMerchantUsername?id=reallyGreatGuyInc 上调用它,您将使用以下代码定义它:

    const functions = require('firebase-functions');
    const admin = require('firebase-admin');
    admin.initializeApp();
    
    exports.getMerchantUsername = functions.https.onRequest((req, res) => {
        if (!req.query.id) {
          // '?id=' is required
          return res.status(400).send("Missing 'id' parameter");
        } else if (/[\u0000-\u001F\u007F\.\$#/\[\]\\]/.test(req.query.id)) {
          // check id for invalid characters
          return res.status(400).send("Invalid 'id' parameter");
        }
    
        // run query
        admin.database().ref(`/merchants/${req.query.id}/username`).once('value')
          .then((snapshot) => {
              var username = snapshot.val();
              res.status(200).send(username);
          })
          .catch((error) => {
              console.error(error);
              res.status(500).send('Request failed.');
          });
    });
    

    注意事项:

    • 无效字符的测试基于RTDB: Structure data 文档中的列表。这在某种程度上阻止了查看其他数据库值。
    • 如果您只需要用户名的值,而不是请求整个商家对象并对其进行解析,请仅请求用户名,如上例中我使用`/merchants/${req.query.id}/username`

    【讨论】:

    • 感谢您的回答,感谢您的解释,我能够更好地理解这个问题。但是为什么问题 1 中的代码只会返回 1 条用户记录,因为 firebase 数据库中有 6 条用户记录。我尝试使用快照的 foreach 来解决它,但它返回错误。
    • 该代码应该返回/users下面的所有数据就好了。确保您正在查看的数据实际上位于 /users 下,而不是类似于 /user 的数据。
    猜你喜欢
    • 1970-01-01
    • 2019-06-24
    • 2017-08-22
    • 2018-03-30
    • 2019-04-13
    • 2022-08-14
    • 2022-08-23
    • 2018-08-01
    • 2020-08-01
    相关资源
    最近更新 更多