仅使用云功能的 Firebase 存储 svg 上传不起作用 其他格式可以使用 base64
Posted
技术标签:
【中文标题】仅使用云功能的 Firebase 存储 svg 上传不起作用 其他格式可以使用 base64【英文标题】:Firebase storage using cloud function only svg upload not working other format's are okay using base64 【发布时间】:2022-01-23 10:58:04 【问题描述】:因此,我和我的团队正在努力使用云功能将 SVG 上传和检索到 Firebase 存储。使用我们构建的功能,我们可以上传我们想要的任何图像,除了 SVG。由于某种原因 SVG 无法正常工作,我不知道我们是否编码错误或其他原因
这是我的函数文件
const admin = require("firebase-admin");
const nanoid = require("nanoid");
const mime = require("mime-types");
const validateCauseImageFile = require("./fileTypeUtils");
const imageStorageUrlMatch = require("./regularExpression");
module.exports.imageValidationAndUpload = async (image) =>
try
console.log("Image in base 64", image);
const bucket = admin.storage().bucket();
const mimeType = image.match(/data:([a-zA-Z0-9]+\/[a-zA-Z0-9-.+]+).*,.*/)
? image.match(/data:([a-zA-Z0-9]+\/[a-zA-Z0-9-.+]+).*,.*/)[1]
: null;
const fileExtension = mime.extension(mimeType);
console.log(fileExtension);
const fileName = nanoid() + `.$fileExtension`;
console.log("Mime type", mimeType);
const base64EncodedImageString = image.replace(
/^data:image\/\w+;base64,/,
""
);
const imageBuffer = Buffer.from(base64EncodedImageString, "base64");
const result = await validateCauseImageFile(imageBuffer.length, mimeType);
if (result.success)
const token = nanoid();
const options =
gzip: true,
metadata:
contentType: mimeType,
metadata:
firebaseStorageDownloadTokens: token,
,
,
;
const filePath = "testSvg/" + fileName;
const file = bucket.file(filePath);
await file.save(imageBuffer, options);
const response = await file.getSignedUrl(
action: "read",
expires: "03-17-2025", // this is an arbitrary date
);
return success: true, response: response[0] ;
// return response;
else if (image.match(imageStorageUrlMatch))
return success: true, url: image ;
else
const errorObject = status: 403, message: result.message ;
throw errorObject;
catch (err)
console.log("show error message : ", err.message);
return success: false, message: err.message ;
;
如果我上传 png/jpeg/jpg 图像,那么它将被上传并正常工作,但对于 SVG,它将被上传但不会渲染任何内容。在 Firebase 存储控制台存储桶上,它是这样显示的
对于 SVG 图像
对于 png 或任何其他图像
上传过程正常,但 SVG 未正确呈现或检索。这是两个文件的网址
SVG: https://firebasestorage.googleapis.com/v0/b/infaque-playground.appspot.com/o/testSvg%2FaxOmCbg7IY6Q8q8P-5c6D.svg?alt=media&token=6UXNtvtP_ONzQTkmbWypD
PNG: https://firebasestorage.googleapis.com/v0/b/infaque-playground.appspot.com/o/testSvg%2FsbbcDN_8zIpWLfuDyWEYw.png?alt=media&token=I_YsAVHXC3eMIrdGmIiPY
【问题讨论】:
你可以看看*** case。让我知道这是否有帮助! 这个答案适用于 java,我不知道那些 Bytes、Base64 库。此外,如果我使用上传文件按钮上传图像,firebase 存储那么它工作正常,并为我提供 svg 和任何其他文件的预览,但是当我使用必须将其转换为 base64 然后存储它的函数上传它时 您可以参考*** case 和documentation,其中提到了在Node.js 中将base64 解码为图像。 抱歉,一点帮助都没有。任何人都可以帮我解决这个问题 拜托,您能否在问题中发布您正在测试的实际 SVG 图像data
URL?请注意,如果您将图像定义为data:image/svg+xml;base64...
,即内容类型为image/svg+xml
- 顺便说一句,您用于获取base64 数据的正则表达式,/^data:image\/\w+;base64,/
不会由于+
符号而正常工作 - 请尝试类似/^data:image\/(\w|\+)+;base64,/
的东西。这可能是问题的原因。
【参考方案1】:
根据您的屏幕截图,SVG 图像被传输为 Content-Type image/svg+xml
。
根据你的代码,这个内容类型计算如下:
const mimeType = image.match(/data:([a-zA-Z0-9]+\/[a-zA-Z0-9-.+]+).*,.*/)
? image.match(/data:([a-zA-Z0-9]+\/[a-zA-Z0-9-.+]+).*,.*/)[1]
: null;
这意味着你的图片数据 URL 应该是这样的:
data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2ZXJzaW9uPSIxLjEiIGlkPSJMYXllcl8xIiB4PSIwcHgiIHk9IjBweCIgdmlld0JveD0iMCAwIDEwMCAxMDAiIGVuYWJsZS1iYWNrZ3JvdW5kPSJuZXcgMCAwIDEwMCAxMDAiIHhtbDpzcGFjZT0icHJlc2VydmUiIGhlaWdodD0iMTAwcHgiIHdpZHRoPSIxMDBweCI+CjxnPgoJPHBhdGggZD0iTTI4LjEsMzYuNmM0LjYsMS45LDEyLjIsMS42LDIwLjksMS4xYzguOS0wLjQsMTktMC45LDI4LjksMC45YzYuMywxLjIsMTEuOSwzLjEsMTYuOCw2Yy0xLjUtMTIuMi03LjktMjMuNy0xOC42LTMxLjMgICBjLTQuOS0wLjItOS45LDAuMy0xNC44LDEuNEM0Ny44LDE3LjksMzYuMiwyNS42LDI4LjEsMzYuNnoiLz4KCTxwYXRoIGQ9Ik03MC4zLDkuOEM1Ny41LDMuNCw0Mi44LDMuNiwzMC41LDkuNWMtMyw2LTguNCwxOS42LTUuMywyNC45YzguNi0xMS43LDIwLjktMTkuOCwzNS4yLTIzLjFDNjMuNywxMC41LDY3LDEwLDcwLjMsOS44eiIvPgoJPHBhdGggZD0iTTE2LjUsNTEuM2MwLjYtMS43LDEuMi0zLjQsMi01LjFjLTMuOC0zLjQtNy41LTctMTEtMTAuOGMtMi4xLDYuMS0yLjgsMTIuNS0yLjMsMTguN0M5LjYsNTEuMSwxMy40LDUwLjIsMTYuNSw1MS4zeiIvPgoJPHBhdGggZD0iTTksMzEuNmMzLjUsMy45LDcuMiw3LjYsMTEuMSwxMS4xYzAuOC0xLjYsMS43LTMuMSwyLjYtNC42YzAuMS0wLjIsMC4zLTAuNCwwLjQtMC42Yy0yLjktMy4zLTMuMS05LjItMC42LTE3LjYgICBjMC44LTIuNywxLjgtNS4zLDIuNy03LjRjLTUuMiwzLjQtOS44LDgtMTMuMywxMy43QzEwLjgsMjcuOSw5LjgsMjkuNyw5LDMxLjZ6Ii8+Cgk8cGF0aCBkPSJNMTUuNCw1NC43Yy0yLjYtMS02LjEsMC43LTkuNywzLjRjMS4yLDYuNiwzLjksMTMsOCwxOC41QzEzLDY5LjMsMTMuNSw2MS44LDE1LjQsNTQuN3oiLz4KCTxwYXRoIGQ9Ik0zOS44LDU3LjZDNTQuMyw2Ni43LDcwLDczLDg2LjUsNzYuNGMwLjYtMC44LDEuMS0xLjYsMS43LTIuNWM0LjgtNy43LDctMTYuMyw2LjgtMjQuOGMtMTMuOC05LjMtMzEuMy04LjQtNDUuOC03LjcgICBjLTkuNSwwLjUtMTcuOCwwLjktMjMuMi0xLjdjLTAuMSwwLjEtMC4yLDAuMy0wLjMsMC40Yy0xLDEuNy0yLDMuNC0yLjksNS4xQzI4LjIsNDkuNywzMy44LDUzLjksMzkuOCw1Ny42eiIvPgoJPHBhdGggZD0iTTI2LjIsODguMmMzLjMsMiw2LjcsMy42LDEwLjIsNC43Yy0zLjUtNi4yLTYuMy0xMi42LTguOC0xOC41Yy0zLjEtNy4yLTUuOC0xMy41LTktMTcuMmMtMS45LDgtMiwxNi40LTAuMywyNC43ICAgQzIwLjYsODQuMiwyMy4yLDg2LjMsMjYuMiw4OC4yeiIvPgoJPHBhdGggZD0iTTMwLjksNzNjMi45LDYuOCw2LjEsMTQuNCwxMC41LDIxLjJjMTUuNiwzLDMyLTIuMyw0Mi42LTE0LjZDNjcuNyw3Niw1Mi4yLDY5LjYsMzcuOSw2MC43QzMyLDU3LDI2LjUsNTMsMjEuMyw0OC42ICAgYy0wLjYsMS41LTEuMiwzLTEuNyw0LjZDMjQuMSw1Ny4xLDI3LjMsNjQuNSwzMC45LDczeiIvPgo8L2c+Cjwvc3ZnPg==
由于+
符号,您正在使用的代码不会正确处理该模式:
const base64EncodedImageString = image.replace(
/^data:image\/\w+;base64,/,
""
);
请查看结果实际上如何包含data:image/svg+xml;base64,
信息作为前缀:
为了成功处理 SVG 用例,您可以将正则表达式修改为:
const base64EncodedImageString = image.replace(
/^data:image\/(\w|\+)+;base64,/,
""
);
请注意现在如何成功提取 base64:
如果内容类型未设置为image/svg+xml
,请考虑将其更改为该值,这也会有所帮助。
【讨论】:
谢谢,伙计,从各处寻找这个答案真的很有帮助,你帮助了我 非常欢迎您@SulmanAzhar,我很高兴能提供帮助并看到答案很有帮助。以上是关于仅使用云功能的 Firebase 存储 svg 上传不起作用 其他格式可以使用 base64的主要内容,如果未能解决你的问题,请参考以下文章