如何在上传后立即接收 Cloudinary 图像 URL(React JS 和 Node Js)?
Posted
技术标签:
【中文标题】如何在上传后立即接收 Cloudinary 图像 URL(React JS 和 Node Js)?【英文标题】:How to receive Cloudinary image URL immediately upon upload (React JS and Node Js)? 【发布时间】:2021-12-09 12:42:26 【问题描述】:我可以成功上传图片到 Cloudinary。但我的问题是如何在上传后立即将成功上传图片的 Cloudinary url 发回给我?
我知道它是作为const uploadedResponse = await cloudinary.uploader.upload(fileStr, upload_preset: 'dev_setups')
的一部分发回的,但这是在后端(参见下面的代码 #2),我想在前端接收 URL(参见下面的代码 #1)所以我可以设置它到 React 状态。实现这一目标的最佳方法是什么?
如果您需要更多详细信息,请告诉我。
代码#1:下面是我上传图片到 Cloudinary 的代码(Cloudinary 的具体代码在下面注释,以供参考/* Cloudinary upload */
)
import React, useState from 'react'
import Card, Button, CardContent from '@material-ui/core';
import post, makePostAction from '../actions';
import useSelector, useDispatch from 'react-redux';
export default function MakePost()
const [title, setTitle] = useState("")
const dispatch = useDispatch();
const usernameHandle = useSelector(state => state.username)
const [fileInputState, setFileInputState] = useState('') /* new */
const [previewSource, setPreviewSource] = useState('') /* new */
const [selectedFile, setSelectedFile] = useState('') /* new */
const onInputChange = (event) =>
setTitle(event.target.value);
const handleSubmit = (evt) =>
evt.preventDefault();
if (!title) return
dispatch(makePostAction(
title,
comment: false,
comments_text: "",
handle: usernameHandle,
post_date: new Date().getTime()
))
setTitle("")
/* Cloudinary upload */
const handleFileInputChange = (e) =>
const file = e.target.files[0]
previewFile(file)
const previewFile = (file) =>
const reader = new FileReader();
reader.readAsDataURL(file);
reader.onloadend = () =>
setPreviewSource(reader.result)
const handleSubmitFile = (e) =>
e.preventDefault();
if(!previewSource) return;
uploadImage(previewSource)
const uploadImage = async (base64EncodedImage) =>
console.log(base64EncodedImage)
try
await fetch('/api/upload',
method: 'POST',
body: JSON.stringify(data: base64EncodedImage),
headers: 'Content-type': 'application/json'
)
catch (error)
console.error(error)
/* Cloudinary upload */
return (
<div>
<Card>
<CardContent>
<form onSubmit=handleSubmit>
<input type="text" value=title onChange=onInputChange />
</form>
/* new */
<form onSubmit=handleSubmitFile className="form">
<input type="file" name="image" onChange=handleFileInputChange value=fileInputState className="form-input" />
<button className="btn" type="submit">Submit</button>
</form>
/* new */
previewSource && (
<img
src=previewSource
style=height: '300px'
/>
)
</CardContent>
</Card>
</div>
)
代码 #2:这是我的 server.js
const express = require('express');
const app = express();
const cloudinary = require('./utils/cloudinary');
app.use(express.json(limit: '50mb'));
app.use(express.urlencoded(limit: '50mb', extended: true))
app.get('/api/images', async (req, res) =>
const resources = await cloudinary.search.expression('folder:dev_setups')
.sort_by('public_id', 'desc')
.max_results(1)
.execute()
const publicIds = resources.map(file => file.secure_url)
res.send(publicIds)
)
app.post('/api/upload', async (req, res) =>
try
const fileStr = req.body.data;
const uploadedResponse = await cloudinary.uploader.upload(fileStr, upload_preset: 'dev_setups')
res.json(msg: "Success")
catch (error)
console.error(error)
res.status(500).json(err: 'Something went wrong')
)
const port = process.env.PORT || 3001
app.listen(port, () =>
console.log(`listening on port $port`)
);
【问题讨论】:
【参考方案1】:Cloudinary 上传响应对象包含一个secure_url
属性,您可以将其发送回前端。查看代码 #2,您似乎正在发送“成功”消息 (res.json(msg: "Success")
)。听起来您想将该行更改为 -
res.json(url: uploadedResponse.secure_url)
在您的前端(代码 #1)中,我会考虑从 async/await
切换到 .then
机制,因为您不希望整个应用程序等待响应 -
const uploadImage = (base64EncodedImage) =>
console.log(base64EncodedImage);
fetch('/api/upload',
method: 'POST',
body: JSON.stringify(data: base64EncodedImage),
headers: 'Content-type': 'application/json'
)
.then(doWhateverYouWant)
.catch((error) => console.error(error))
const doWhateverYouWant = async (res) =>
// you can use res.url
【讨论】:
以上是关于如何在上传后立即接收 Cloudinary 图像 URL(React JS 和 Node Js)?的主要内容,如果未能解决你的问题,请参考以下文章