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

Node.js函数从GCS复制文件到Drive报错:stream.push() after EOF

解决GCS到Google Drive复制时的"stream.push() after EOF"错误

我之前在做类似的GCS到Drive文件迁移时也碰到过这个一模一样的错误!这个问题本质上是因为GCS的可读流在Google Drive API完成数据读取前就提前关闭了,导致API尝试从已经标记为EOF(文件结束)的流里继续读取数据,就抛出了这个错误。

问题根源

你的代码直接把file.createReadStream()返回的可读流传给了Drive API的media.body,但有时候这个流会因为GCS的内部缓存、网络波动或者流的生命周期管理问题,在API还没读完所有数据时就触发了end事件,导致后续的读取操作失败。

两种可行的解决方案

方案1:用Node.js的pipeline管理流生命周期

Node.js核心的stream.pipeline方法专门用来处理流的传输,它会自动处理流的错误、关闭和销毁,避免出现流提前结束的问题。

首先确保导入pipeline:

const { pipeline } = require('stream');

然后修改你的代码:

const file = bucket.file(fileName);
const fileMetadata = { 'name': fileName };
const readStream = file.createReadStream();
const media = { mimeType: "image/png", body: readStream };

// 用pipeline包裹流,确保正确处理生命周期
pipeline(
  readStream,
  // 这里不需要额外的转换,pipeline会自动把流导向Drive API
  (err) => {
    if (err) {
      console.error('流传输过程出错:', err);
    }
  }
);

drive.files.create({
  resource: fileMetadata,
  media: media,
  fields: 'id'
}, function (err, file) {
  if (err) {
    console.log('Drive API调用失败:', err);
  } else {
    console.log('文件成功复制到Drive,ID:', file.data.id);
  }
});

方案2:先下载到内存缓冲区再上传

如果你的文件不大(比如几MB以内),可以先把GCS文件下载到内存缓冲区,再把缓冲区传给Drive API,这样就完全避开了流的问题:

const file = bucket.file(fileName);
const fileMetadata = { 'name': fileName };

// 先从GCS下载文件到内存
file.download((err, fileBuffer) => {
  if (err) {
    console.error('下载GCS文件失败:', err);
    return;
  }

  // 用缓冲区作为media的body
  const media = { mimeType: "image/png", body: fileBuffer };
  
  drive.files.create({
    resource: fileMetadata,
    media: media,
    fields: 'id'
  }, function (err, file) {
    if (err) {
      console.log('Drive API错误:', err);
    } else {
      console.log('文件上传成功,ID:', file.data.id);
    }
  });
});

额外注意事项

  • 确保你指定的mimeType和GCS文件的实际类型一致,如果不确定,可以从GCS文件的元数据里获取正确的MIME类型,避免因为类型不匹配导致的隐性错误。
  • 如果处理大文件,优先用方案1的pipeline,因为方案2会把整个文件加载到内存,可能导致内存溢出。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.28 06:23:52