You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何从TypeScript编写的Firebase可调用云函数向Unity发送自定义对象?

解决Firebase可调用函数返回数据在Unity中反序列化卡住的问题

先做核心排查:确认实际返回的JSON结构

不管用哪种序列化方式,先搞清楚Firebase云函数到底返回了什么内容,这是定位问题的关键:

  • 在TypeScript云函数中打印返回的JSON:

    export const CreateNewCharacter = functions.https.onCall(async (data, context) => {
      const resp = new CharactersResponse();
      resp.Code = CharactersCode.InvalidName;
      // 按需设置CharacterID,不需要就留空
      console.log("返回的JSON数据:", JSON.stringify(resp));
      return resp;
    });
    

    去Firebase控制台的函数日志里查看输出的JSON字符串,确认字段名、值类型是否符合预期。

  • 在Unity中打印收到的原始数据:
    不要直接反序列化,先把task.Result.Data转成字符串看真实内容:

    // 调用云函数后的回调逻辑
    if (task.IsCompletedSuccessfully)
    {
        string rawJson = JsonConvert.SerializeObject(task.Result.Data);
        Debug.Log("Firebase返回的原始JSON: " + rawJson);
        // 再尝试反序列化
        // var resp = JsonConvert.DeserializeObject<CharactersResponse>(rawJson);
    }
    

针对性解决反序列化问题

1. 修正C#类的序列化配置,匹配TS结构

TS里的CharacterID是可选字段(未赋值时不会出现在JSON中),Unity的C#类要对应处理,同时明确字段映射规则:

using Newtonsoft.Json;

public class CharactersResponse : CustomResponse
{
    [JsonProperty("Code")]
    public CharactersCode Code;

    // 标记为可选,JSON中无此字段时自动设为null
    [JsonProperty("CharacterID", NullValueHandling = NullValueHandling.Ignore)]
    public string CharacterID;
}

// 确保父类字段兼容无JSON值的情况
public class CustomResponse
{
    [JsonProperty(Required = Required.Default)]
    public string UnknownErrorMessage = string.Empty;
}

2. 放弃JsonConvert,直接解析Firebase返回的字典

Firebase可调用函数返回的Data本质是Dictionary<string, object>,直接解析更可靠,避免序列化冲突:

if (task.IsCompletedSuccessfully)
{
    var dataDict = task.Result.Data as Dictionary<string, object>;
    if (dataDict == null)
    {
        Debug.LogError("返回数据格式错误");
        return;
    }

    var resp = new CharactersResponse();
    // Firebase返回的数字是long类型,需强制转换为枚举
    resp.Code = (CharactersCode)(long)dataDict["Code"];

    // 处理可选的CharacterID字段
    if (dataDict.ContainsKey("CharacterID"))
    {
        resp.CharacterID = dataDict["CharacterID"] as string;
    }

    // 后续业务逻辑
    Debug.Log("解析成功,Code: " + resp.Code);
}

3. 规范TS类的实例化方式

TS里用类创建对象时,确保必填字段Code一定被赋值,避免返回不完整的JSON:

export class CharactersResponse {
    Code: CharactersCode;
    CharacterID?: string;

    // 用构造函数强制初始化Code字段
    constructor(code: CharactersCode, characterID?: string) {
        this.Code = code;
        this.CharacterID = characterID;
    }
}

// 使用示例
const resp = new CharactersResponse(CharactersCode.InvalidName);

额外注意点

  • 枚举值匹配:确认TS和C#的枚举数字值完全一致(你的代码目前是一致的,没问题);如果TS返回的是枚举字符串(比如"InvalidName"),C#枚举要加[JsonConverter(typeof(StringEnumConverter))]特性。
  • 简化云函数返回:也可以直接返回普通对象替代类实例,比如return { Code: CharactersCode.InvalidName, CharacterID: null };,避免TS类序列化的潜在问题。

内容的提问来源于stack exchange,提问作者Hellcat8

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.05 22:55:37