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

使用Firebase 9的uploadBytesResumable上传图片时遇_throwIfRoot未定义错误

问题分析与解决方案

错误根源

你遇到的TypeError: Cannot read property '_throwIfRoot' of undefined以及上传无效小文件的问题,核心原因是错误地将本地文件路径直接转为Blob:

const blob = new Blob([image[0]]);

这里的image[0]是file://开头的本地文件路径字符串,直接用它创建Blob时,实际是把路径文本转成了二进制数据(大小仅为路径字符串的长度,也就是你看到的9字节左右),而非读取图片的真实二进制内容。这种无效的Blob传入Firebase Storage后,触发了内部方法调用错误。

修复方案

在React Native/Expo环境中,需要先通过网络请求读取本地文件的二进制内容,再转为Blob后上传。以下提供两种可行的实现方式:

方式1:使用原生fetch API(通用方案)

const uploadImage = async (image) => {
  if (!image || !image[0]) return;
  
  const imageRef = ref(storage, `images/${user.uid}/${v4()}`);
  
  try {
    // 通过fetch读取本地文件内容
    const response = await fetch(image[0]);
    const blob = await response.blob();
    
    console.log("有效Blob大小", blob.size); // 应与原图片大小一致
    await uploadBytesResumable(imageRef, blob);
    console.log("图片上传成功");
  } catch (error) {
    console.error(`上传失败:${error}`);
  }
};

方式2:使用Expo FileSystem(Expo项目推荐)

如果你的项目基于Expo,用expo-file-system处理本地文件更高效:

import * as FileSystem from 'expo-file-system';

const uploadImage = async (image) => {
  if (!image || !image[0]) return;
  
  const imageRef = ref(storage, `images/${user.uid}/${v4()}`);
  
  try {
    // 先验证原文件信息
    const fileInfo = await FileSystem.getInfoAsync(image[0], { size: true });
    console.log("原文件大小", fileInfo.size);
    
    // 通过XMLHttpRequest读取文件并转为Blob
    const blob = await new Promise((resolve, reject) => {
      const xhr = new XMLHttpRequest();
      xhr.onload = () => resolve(xhr.response);
      xhr.onerror = () => reject(new TypeError("读取文件失败"));
      xhr.responseType = "blob";
      xhr.open("GET", image[0], true);
      xhr.send(null);
    });
    
    await uploadBytesResumable(imageRef, blob);
    console.log("图片上传成功");
    blob.close(); // 释放资源
  } catch (error) {
    console.error(`上传失败:${error}`);
  }
};

额外注意事项

  • 验证Blob有效性:修复后打印blob.size,应与原图片文件大小匹配,而非几十字节。
  • 权限配置:确保已在app.json中配置了图片访问权限(iOS的NSPhotoLibraryUsageDescription、Android的READ_EXTERNAL_STORAGE等)。
  • 资源释放:上传完成后调用blob.close()避免内存泄漏。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.30 11:10:30