【发布时间】:2021-12-04 13:51:12
【问题描述】:
我已经复制了所有代码,包括来自 Resize Image Firebase Functions Extension 的依赖项。我在 Firebase 模拟器中运行它,需要对其进行调整以满足我的需求。但是,就目前而言,我将其设置为几乎与扩展程序的源代码完全相同。
分机网址:https://firebase.google.com/products/extensions/storage-resize-images
我的本地设置:
节点:v14.17.5
npm:7.23.0
火力基地:9.20.0
firebase 管理员:^9.11.1
firebase-functions": ^3.15.6
mkdirp: ^1.0.4
uuid:^8.3.2
扩展的依赖
firebase 管理员:^8.0.0
firebase 功能:^3.13.2
mkdirp: ^1.0.4
尖锐:0.23.4
uuidv4: ^6.1.0
这是调整图像大小的代码
请注意这一行:await remoteFile.download({ destination: originalFile }); // <- Offending line of code...,因为那是它失败的那一行。
const resizeImage = async (object): Promise<ResizedImageResult[]> => {
logs.start();
const { contentType } = object; // This is the image MIME type
const tmpFilePath = path.resolve('/', path.dirname(object.name)); // Absolute path to dirname
if (!contentType) {
logs.noContentType();
return;
}
if (!contentType.startsWith('image/')) {
logs.contentTypeInvalid(contentType);
return;
}
if (object.contentEncoding === 'gzip') {
logs.gzipContentEncoding();
return;
}
if (!supportedContentTypes.includes(contentType)) {
logs.unsupportedType(supportedContentTypes, contentType);
return;
}
if (config.includePathList && !startsWithArray(config.includePathList, tmpFilePath)) {
logs.imageOutsideOfPaths(config.includePathList, tmpFilePath);
return;
}
if (config.excludePathList && startsWithArray(config.excludePathList, tmpFilePath)) {
logs.imageInsideOfExcludedPaths(config.excludePathList, tmpFilePath);
return;
}
if (object.metadata && object.metadata.resizedImage === 'true') {
logs.imageAlreadyResized();
return;
}
const bucket = admin.storage().bucket(object.bucket);
const filePath = object.name; // File path in the bucket.
const fileDir = path.dirname(filePath);
const fileExtension = path.extname(filePath);
const fileNameWithoutExtension = extractFileNameWithoutExtension(filePath, fileExtension);
const objectMetadata = object;
let originalFile;
let remoteFile: File;
try {
originalFile = path.join(os.tmpdir(), filePath);
const tempLocalDir = path.dirname(originalFile);
// Create the temp directory where the storage file will be downloaded.
logs.tempDirectoryCreating(tempLocalDir);
await mkdirp(tempLocalDir);
logs.tempDirectoryCreated(tempLocalDir);
// Download file from bucket.
remoteFile = bucket.file(filePath);
logs.imageDownloading(filePath);
logs.imageDownloading(originalFile);
await remoteFile.download({ destination: originalFile }); // <- Offending line of code...
logs.imageDownloaded(filePath, originalFile);
// Get a unique list of image types
const imageTypes = new Set(config.imageTypes);
// Convert to a set to remove any duplicate sizes
const imageSizes = new Set(config.imageSizes);
const tasks: Promise<ResizedImageResult>[] = [];
imageTypes.forEach((format) => {
imageSizes.forEach((size) => {
tasks.push(
modifyImage({
bucket,
originalFile,
fileDir,
fileNameWithoutExtension,
fileExtension,
contentType,
size,
objectMetadata: objectMetadata,
format,
}),
);
});
});
const results = await Promise.all(tasks);
const failed = results.some((result) => result.success === false);
if (failed) {
logs.failed();
return;
} else {
if (config.deleteOriginalFile === deleteImage.onSuccess) {
if (remoteFile) {
try {
logs.remoteFileDeleting(filePath);
await remoteFile.delete();
logs.remoteFileDeleted(filePath);
} catch (err) {
logs.info('Catch 1');
logs.errorDeleting(err);
}
}
}
logs.complete();
}
} catch (err) {
logs.info('Catch 2');
logs.error(err);
} finally {
if (originalFile) {
logs.tempOriginalFileDeleting(filePath);
fs.unlinkSync(originalFile);
logs.tempOriginalFileDeleted(filePath);
}
if (config.deleteOriginalFile === deleteImage.always) {
// Delete the original file
if (remoteFile) {
try {
logs.remoteFileDeleting(filePath);
await remoteFile.delete();
logs.remoteFileDeleted(filePath);
} catch (err) {
logs.errorDeleting(err);
}
}
}
}
};
预期行为
当执行await remoteFile.download({ destination: originalFile }); 时,它应该下载原始文件。此代码与扩展代码完全相同。
实际行为
以下错误被注销:
{
"severity":"ERROR","message":"Error when resizing image TypeError: Only HTTP(S) protocols are supported
at getNodeRequestOptions (.../node_modules/teeny-request/node_modules/node-fetch/lib/index.js:1309:9)
at .../node_modules/teeny-request/node_modules/node-fetch/lib/index.js:1410:19
at new Promise (<anonymous>)
at Function.fetch [as default] (.../node_modules/teeny-request/node_modules/node-fetch/lib/index.js:1407:9)
at teenyRequest (.../node_modules/teeny-request/build/src/index.js:184:29)
at Object.request (.../node_modules/teeny-request/build/src/index.js:241:20)
at Timeout.makeRequest [as _onTimeout] (.../node_modules/retry-request/index.js:139:28)
at listOnTimeout (internal/timers.js:557:17)
at processTimers (internal/timers.js:500:7)"
}
有人遇到过这个问题吗?我无法返回到早期版本的 Firebase,因为存在重大更改。
【问题讨论】:
-
Remember 以简明扼要的摘要为您的帖子命名。
-
我创建了一个测试用例。错误是不同的,但它在同一个地方中断:github.com/vdiaz1130/fb-resize-image-locally 请务必将您的项目添加到 .firebaserc 文件中。
-
我和我的同事对此进行了测试,您在 GitHub 上发布的代码在部署时似乎运行良好。这是logs。再次检查您的设置,并确保您的依赖项与您的问题中所述的相匹配。
-
@RobertG 感谢您的测试。是的,我知道它在部署时有效。我希望让这个在模拟器中本地工作,因为我需要进行一些更改以满足我的需要。没有必要使用匹配的 dep 1. 因为它在部署时可以工作 2. 因为 Firebase v8 与 v9 发生了重大变化,而我正在使用 v9。
-
由于这是您升级后模拟器内部的问题,建议您通过Firebase Tools Issue link提交您的问题。
标签: node.js firebase google-cloud-functions google-cloud-storage