Firebase Cloud Functions callable functions Unhandled error TypeError: Cannot read properties of undefined (reading 'auth')

huangapple go评论109阅读模式
英文:

Firebase Cloud Functions callable functions Unhandled error TypeError: Cannot read properties of undefined (reading 'auth')

问题

Firebase CLI版本:12.4.0

Firebase Unity版本:11.2.0(最新版本)

Unity版本:2022.2.17

根据我的理解,Firebase可调用函数是指Firebase SDK自动将context作为参数传递,但在服务器端,在我的情况下,auth未定义并引发以下错误:

未处理的错误TypeError无法读取未定义的属性读取'auth'
    at /workspace/index.js:17:16
    at fixedLen (/workspace/node_modules/firebase-functions/lib/v2/providers/https.js:118:31)
    at /workspace/node_modules/firebase-functions/lib/common/providers/https.js:467:32
    at process.processTicksAndRejections (node:internal/process/task_queues:95:5)

index.js

const {onRequest, onCall, HttpsError} = require("firebase-functions/v2/https");
const {initializeApp} = require("firebase-admin/app");

initializeApp();

exports.onLoginAddOTPEntry = onCall((data, context) => {
  console.log(data.otp);
  console.log(data.email);
  console.log(context);

  if (!data || !data.email || !data.otp) {
    throw new HttpsError("invalid-argument",
        "onLoginAddOTPEntry应该带有电子邮件和otp");
  }

  if (!context.auth) {
    throw new HttpsError(
        "unauthorized",
        "用户未经身份验证",
    );
  }

  return "工作正常!";
});

进一步调试发现datacontext都以某种方式为undefined,而在Unity中,我调试并记录了数据按照预期传递。以下是我的Unity C#调用代码:

private FirebaseFunctions firebaseFunctions;

public void Initialize()
{
    firebaseFunctions = FirebaseFunctions.DefaultInstance;
}

public async void CallableFunction(string functionName,
    KeyValuePair<string, string>[] dataToPass,
    Action<bool, string, string> _onSuccess)
{
    var function = firebaseFunctions.GetHttpsCallable(functionName);

    // 传递数据
    if (dataToPass?.Length > 0)
    {
        var data = new Dictionary<string, object>();
        for (int i = 0, count = dataToPass.Length; i < count; ++i)
        {
            data.Add(dataToPass[i].Key, dataToPass[i].Value);
        }

        await function.CallAsync(data).ContinueWith((task) =>
        {
            Debug.Log("任务:" + task.ToJSON());
        });
        return;
    }

    await function.CallAsync().ContinueWith((task) =>
    {
         Debug.Log("任务:" + task.ToJSON());
    });
}

注意:onRequest按预期工作正常,因此变量和项目ID也已适当设置。

所以我在调用可调用的onCall函数时做错了什么?

在添加了更多的console.logs之后,发现没有传递任何数据

未定义
未定义
未定义
英文:

Firebase CLI version: 12.4.0

Firebase Unity version: 11.2.0 (latest)

Unity: 2022.2.17

According to my understanding of firebase callable functions are that Firebase SDK automatically passes the context as parameter, but on server in my case auth is undefined and giving the following error

Unhandled error TypeError: Cannot read properties of undefined (reading &#39;auth&#39;)
    at /workspace/index.js:17:16
    at fixedLen (/workspace/node_modules/firebase-functions/lib/v2/providers/https.js:118:31)
    at /workspace/node_modules/firebase-functions/lib/common/providers/https.js:467:32
    at process.processTicksAndRejections (node:internal/process/task_queues:95:5)

index.js

    const {onRequest, onCall, HttpsError} = require(&quot;firebase-functions/v2/https&quot;);
    const {initializeApp} = require(&quot;firebase-admin/app&quot;);

    initializeApp();

    exports.onLoginAddOTPEntry = onCall((data, context) =&gt; {
      console.log(data.otp);
      console.log(data.email);
      console.log(context);
    
      if (!data || !data.email || !data.otp) {
        throw new HttpsError(&quot;invalid-argument&quot;,
            &quot;onLoginAddOTPEntry should be called with email and otp&quot;);
      }
    
      if (!context.auth) {
        throw new HttpsError(
            &quot;unauthorized&quot;,
            &quot;User is not authenticated&quot;,
        );
      }

      return &quot;Worked!&quot;;
    });

Further debugging found out data and context, both are undefined somehow, while in Unity I debugged and logged the data is passed as it should be. Also, the user is logged in too. Here is my Unity C# calling code

private FirebaseFunctions firebaseFunctions;

public void Initialize()
{
    firebaseFunctions = FirebaseFunctions.DefaultInstance;
}

public async void CallableFunction(string functionName,
    KeyValuePair&lt;string, string&gt;[] dataToPass,
    Action&lt;bool, string, string&gt; _onSuccess)
{
    var function = firebaseFunctions.GetHttpsCallable(functionName);

    // pass data
    if (dataToPass?.Length &gt; 0)
    {
        var data = new Dictionary&lt;string, object&gt;();
        for (int i = 0, count = dataToPass.Length; i &lt; count; ++i)
        {
            data.Add(dataToPass[i].Key, dataToPass[i].Value);
        }

        await function.CallAsync(data).ContinueWith((task) =&gt;
        {
            Debug.Log(&quot;Task: &quot; + task.ToJSON());
        });
        return;
    }

    await function.CallAsync().ContinueWith((task) =&gt;
    {
         Debug.Log(&quot;Task: &quot; + task.ToJSON());
    });
}

NOTE: onRequest is working fine as expected, so variables and project ids are appropriately set too.

So what I'm doing wrong calling the callable onCall function?

> After adding more console.logs, found out no data is passed

Undefined
Undefined
Undefined

答案1

得分: 1

以下是您要的翻译内容:

如您在第二代可调用云函数文档中所见,传递给回调函数的参数已从

第一代: functions.https.onCall((data, context) =&gt; {...});

变为

第二代: onCall((request) =&gt; {...});

因此,您需要执行以下操作:

exports.onLoginAddOTPEntry = onCall((request) =&gt; {

  const data = request.data;

  if (!data || !data.email || !data.otp) {
        throw new HttpsError(&quot;invalid-argument&quot;,
            &quot;onLoginAddOTPEntry 应传递 email  otp&quot;);
  }
    
  if (!request.auth) {
        throw new HttpsError(
            &quot;unauthorized&quot;,
            &quot;用户未经授权&quot;,
        );
  }

  return &quot;成功&quot;;
});
英文:

As you can see in the doc for Callable Cloud Functions 2nd generation the arguments passed to the callback function have changed from

1st gen: functions.https.onCall((data, context) =&gt; {...});

to

2nd gen: onCall((request) =&gt; {...});.


So you need to do:

exports.onLoginAddOTPEntry = onCall((request) =&gt; {

  const data = request.data;

  if (!data || !data.email || !data.otp) {
        throw new HttpsError(&quot;invalid-argument&quot;,
            &quot;onLoginAddOTPEntry should be called with email and otp&quot;);
  }
    
  if (!request.auth) {
        throw new HttpsError(
            &quot;unauthorized&quot;,
            &quot;User is not authenticated&quot;,
        );
  }

  return &quot;Worked!&quot;;
});

huangapple
  • 本文由 发表于 2023年6月26日 13:50:53
  • 转载请务必保留本文链接:https://go.coder-hub.com/76553838.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定