I have the following form that is using react hook form.
What Am I supposed to pass to the API route via fetch such that I can write the image to disk with fs, and retrieve its location and pass that to Cloudinary? In the body of the fetch I can pass the picture object which is inside of data, but how does that give me enough info to write the image to disk with fs.
I want to pass the full image path to Cloudinary so it can upload the image, I am currently only passing the name which is wrong.
<form onSubmit={handleSubmit(onSubmit)}>
<div>
<h2>Image</h2>
<input ref={register} type="file" name="picture" />
</div>
<div>
<h2>Description</h2>
<input
type="text"
placeholder="Description"
name="description"
ref={register({ required: true })}
/>
</div>
<div>
<input type="submit" />
</div>
</form>
This is the onSubmit function that is called
const onSubmit = async (data) => {
console.log(data);
console.log(data);
const res = await fetch("../api/image", {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify(data.picture[0].name),
}).then((ok) => {
console.log(ok);
});
};
and this is the API route that it is hitting
var cloudinary = require("cloudinary").v2;
import { fs } from "fs";
// first we need to disable the default body-parser
cloudinary.config({
cloud_name: process.env.CLOUDINARY_NAME,
api_key: process.env.CLOUDINARY_API_KEY,
api_secret: process.env.CLOUDINARY_API_SECRET,
});
export default async function image(req, res) {
cloudinary.uploader.upload(`${req.body}`, function (error, result) {
console.log(result, error);
});
try {
// const result = req.body;
res.status(200).send(req.body);
} catch (error) {
console.error(error);
res.status(error.requestResult.statusCode).send(error.message);
}
Here is what I have access to on the picture object in the data object
UPDATE: I have tried the suggestion from this questionto no avail, it just returns null and two empty objects after the form.parse.
How to send an image file using formdata to React/Next js api?
client
const formData = new FormData();
formData.append("image", data.picture[0]);
const res = await fetch("../api/image", {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify(formData),
}).then((ok) => {
console.log(ok);
server
var cloudinary = require("cloudinary").v2;
import { fs } from "fs";
import formidable from "formidable";
// first we need to disable the default body parser
export const config = {
api: {
bodyParser: false,
},
};
cloudinary.config({
cloud_name: process.env.CLOUDINARY_NAME,
api_key: process.env.CLOUDINARY_API_KEY,
api_secret: process.env.CLOUDINARY_API_SECRET,
});
export default async function image(req, res) {
const form = new formidable.IncomingForm();
form.uploadDir = "./";
form.keepExtensions = true;
form.parse(req, (err, fields, files) => {
console.log(err, fields, files);
});
// cloudinary.uploader.upload(`${body}`, function (error, result) {
// console.log(result, error);
// });
try {
// const result = req.body;
res.status(200).send(req.body);
} catch (error) {
console.error(error);
res.status(error.requestResult.statusCode).send(error.message);
}
}
UPDATE: So if I do the following the formData is an empty object but the console log is not, why is this, I think that is my problem.
formData.append("image", data.picture[0]);
console.log(data.picture[0]);
console.log(formData); // empty
so apparently you can't just console log formData, but it looks like you can do this, which is saying the File object is in there, so not sure why this is not working.
for (var key of formData.entries()) {
console.log(key[0] + ", " + key[1]);
}