NextJS文件上传到谷歌云存储成功,但总是上传0字节文件 - 使用强大的



我试图在nextJS中实现文件上传并将文件流式传输到谷歌云存储。我正在使用福米达布。强大的是给我一个文件路径,新文件名,文件大小等,但是当文件显示在谷歌存储中时,它的字节为零。这就像正在创建位置,但我的 blob 流实际上并没有将文件推送到那里。

下面是我的 api 路由中的代码。有什么想法吗?

import { Storage } from "@google-cloud/storage";
import formidable from '../../lib/formidable-serverless'
export const config = {
api: {
bodyParser: false,
},
};
export default async function handler(req, res) {
console.log('req')
const storage = new Storage({
projectId: process.env.GOOGLE_SERVICE_ID,
client_email: process.env.GOOGLE_CLIENT_EMAIL,
private_key: process.env.GOOGLE_SERVICE_KEY,
});
const data = await new Promise(function(resolve, reject) { 
const form = new formidable.IncomingForm();
form.keepExtensions = true;
form.parse(req, function(err, fields, files) {
if (err) return reject(err);
resolve({ fields, files });
});
});
const file = data.files.file
try {
const bucket = storage.bucket(process.env.GCS_BUCKET)
const blob = bucket.file(file.originalFilename);

const blobStream = blob.createWriteStream({
resumable: false,
});

blobStream.on("error", (err) => {
console.log('ERR', err.message)
res.status(500).send({ message: err.message });
});

blobStream.on("finish", async () => {
const publicURL = `https://storage.googleapis.com/${bucket.name}/${blob.name}`
;
try {
await blob.makePublic();
} catch {
return res.status(500).send({
message: `Uploaded the file successfully: ${file.newFilename}, but public access is denied!`,
url: publicURL,
});
}

res.status(200).send({
message: "Uploaded the file successfully: " + file.newFilename,
url: publicURL,
});
});
blobStream.end();
} catch (err) {
if (err.code == "LIMIT_FILE_SIZE") {
console.log('ERR', err.message)
return res.status(500).send({
message: "File size cannot be larger than 25MB!",
});
}

res.status(500).send({
message: `Could not upload the file: ${file.newFilename}. ${err}`,
});
}

这是我的 blob 流在创建后立即的样子。

Writable {
_writableState: WritableState {
objectMode: false,
highWaterMark: 16384,
finalCalled: false,
needDrain: false,
ending: false,
ended: false,
finished: false,
destroyed: false,
decodeStrings: true,
defaultEncoding: 'utf8',
length: 0,
writing: false,
corked: 0,
sync: true,
bufferProcessing: false,
onwrite: [Function: bound onwrite],
writecb: null,
writelen: 0,
afterWriteTickInfo: null,
buffered: [],
bufferedIndex: 0,
allBuffers: true,
allNoop: true,
pendingcb: 0,
prefinished: false,
errorEmitted: false,
emitClose: true,
autoDestroy: true,
errored: null,
closed: false
},

这就是解决强大承诺后文件的样子。那里还有一个可写的流。

PersistentFile {
_events: [Object: null prototype] { error: [Function (anonymous)] },
_eventsCount: 1,
_maxListeners: undefined,
lastModifiedDate: 2022-11-22T14:54:26.597Z,
filepath: '/var/folders/yb/l636l56d7ng731jp24crv6lw0000gn/T/9e8fb9b8b1e0740b2622b990b',
newFilename: '9e8fb9b8b1e0740b2622b990b',
originalFilename: '17.mp3',
mimetype: 'audio/mpeg',
hashAlgorithm: false,
size: 7020751,
_writeStream: WriteStream {
_writableState: WritableState {
objectMode: false,
highWaterMark: 16384,
finalCalled: true,
needDrain: true,
ending: true,
ended: true,
finished: true,
destroyed: true,
decodeStrings: true,
defaultEncoding: 'utf8',
length: 0,
writing: false,...
}

当我创建我的 blob 时,我是否以某种方式没有将文件传递到写入流中?

作为社区维基回答,

这可以通过实现一个读取文件路径的readStream来解决,其中 强大的在writestream开始之前临时存储文件。

import { createReadStream } from "fs";

createReadStream(file.filepath) 
.pipe(blob.createWriteStream(file.originalFilename, file.mimetype))  
console.log('blobstream', blobStream) 
.on("error", (err) => { console.log('ERR', err.message) 
res.status(500).send({ message: err.message 
});
}) 
.on("finish", async () => { // create a url to access file ... 

最新更新