Go to this link https://cloudinary.com/ and create your cloudinary account, verify your email and go through or skip the initial questions
After you are done you should be able to see the following in your dashboard:
- Cloud Name
- API key
- API Secret
These 3 elements are unique to you and will need them to use cloudinary. You will need to add them to your .env file.
In your .env file:
CLOUD_NAME=<your-cloudinary-name>
CLOUD_API_KEY=<your-cloudinary-key>
CLOUD_API_SECRET=<your-cloudinary-secret>
Make sure you have the correct .env syntax. You don't need to use quotes for the strings.
Install the following 3 npm packages: cloudinary, multer by running the following code in your terminal
npm i cloudinary multer
Create a file in the middlewares folder called cloudinary.config.js and add the following code:
// the following 3 packages are needed in order for cloudinary to run
const cloudinary = require("cloudinary").v2;
const multer = require("multer");
// your three cloudinary keys will be passed here from your .env file
cloudinary.config({
cloud_name: process.env.CLOUD_NAME,
api_key: process.env.CLOUD_API_KEY,
api_secret: process.env.CLOUD_API_SECRET,
});
const storage = multer.diskStorage({
filename: function (req, file, cb) {
cb(null, file.originalname);
},
});
module.exports = multer({ storage });
Make sure in your frontend you have a form with the following specifications This is the function to call on submit of form
//multiple images function
async function handleImages(e) {
//prevent the form from reloading
e.preventDefault();
//create formData (multer on the server expects form data)
const myFormData = new FormData();
// Change the images state to an array so we can call the .forEach( ) on it
//for each image, add it to the form data
Array.from(images).forEach((image) => {
myFormData.append("imageUrl", image);
});
try {
const { data } = await axios.post(
"http://localhost:5005/auth/multiple-uploads",
myFormData
);
console.log("image uploaded successfully", data);
nav("/home");
} catch (error) {
console.log(error);
}
}
This is what the form should look like, make sure to add the multiple attribute to the input
<form onSubmit={handleImages}>
<label>
Change Profile Image:
<input
type="file"
name="image"
multiple
onChange={(e) => setImages(e.target.files)}
/>
</label>
<button>Submit</button>
</form>
- the action "/multiple-uploads" can be different but needs to match your route url. See next section.
- the input name "imageUrl" can be different but needs to match the targeted name in your route. See sext section.
Go to the post route where you want to receive an image/file to store in cloudinary.
Asides from your regular require (express, routes, models) require your cloudinary.config.js by adding the following line:
This is how your route should look like:
//We will need this variable to upload each image one by one
const cloudinary = require("cloudinary").v2;
//middleware to send image to cloudinary
const uploader = require("../middlewares/cloudinary.config");
//uploader.array will accept an array of images with the key imageUrl
router.post(
"/multiple-uploads",
uploader.array("imageUrl"),
async (req, res) => {
//the images after the uploader will be in the request . files
const images = req.files;
// create an array to push the urls into after we add them to the cloud
const imageUrls = [];
//for in loop to loop over the object of images
for (const image of images) {
// await the uploader.upload from cloudinary to get the secure url
const result = await cloudinary.uploader.upload(image.path, {
resource_type: "auto",
});
//push into the array the secure url on each iteration
imageUrls.push(result.secure_url);
}
if (!imageUrls.length) {
console.log("there is no file");
res.status(403).json({ message: "there is no file" });
} else {
res.status(200).json({ message: "success!", imageUrls });
}
}
);