Skip to content

Instantly share code, notes, and snippets.

@bkanhu
Created July 4, 2023 17:31
Show Gist options
  • Save bkanhu/efd7ae1fa3862c87393051168b014e0b to your computer and use it in GitHub Desktop.
Save bkanhu/efd7ae1fa3862c87393051168b014e0b to your computer and use it in GitHub Desktop.
Upload product data to MongoDB and images to Cloudinary in a MERN stack application.

To upload product data to MongoDB and images to Cloudinary in a MERN stack application, you can follow these steps:

  1. Set up your MongoDB and Cloudinary accounts: Ensure that you have created accounts and obtained the necessary credentials for both MongoDB and Cloudinary.

  2. Set up the server-side (Node.js) code:

  • Create an Express server to handle API requests.
  • Install the necessary dependencies: express, mongoose, multer, cloudinary.
  • Create a schema for your product in a Product.js file, using Mongoose:
const mongoose = require('mongoose');

const productSchema = new mongoose.Schema({
  name: String,
  description: String,
  images: [String] // Array of image URLs from Cloudinary
});

const Product = mongoose.model('Product', productSchema);

module.exports = Product;
  • Create an endpoint for uploading a product with images:
const express = require('express');
const router = express.Router();
const multer = require('multer');
const cloudinary = require('cloudinary').v2;
const Product = require('../models/Product');

// Configure multer to store uploaded files temporarily
const upload = multer({ dest: 'uploads/' });

// Configure Cloudinary
cloudinary.config({
  cloud_name: process.env.CLOUDINARY_CLOUD_NAME,
  api_key: process.env.CLOUDINARY_API_KEY,
  api_secret: process.env.CLOUDINARY_API_SECRET
});

// Endpoint for uploading a product with images
router.post('/products', upload.array('images'), async (req, res) => {
  try {
    const { name, description } = req.body;
    const files = req.files;

    // Upload images to Cloudinary
    const uploadPromises = files.map((file) =>
      cloudinary.uploader.upload(file.path)
    );
    const uploadResults = await Promise.all(uploadPromises);

    // Extract the URLs of the uploaded images
    const imageUrls = uploadResults.map((result) => result.secure_url);

    // Create a new product with the uploaded images
    const product = new Product({
      name,
      description,
      images: imageUrls
    });

    // Save the product to MongoDB
    await product.save();

    res.status(201).json({ message: 'Product uploaded successfully' });
  } catch (error) {
    console.error('Error uploading product:', error);
    res.status(500).json({ error: 'Product upload failed' });
  }
});

module.exports = router;
  1. Set up the client-side (React) code:
  • Install the necessary dependencies: axios (for making API requests), react-dropzone (for handling file uploads).
  • Create a React component to handle the product upload form:
import React, { useState } from 'react';
import axios from 'axios';
import { useDropzone } from 'react-dropzone';

const ProductUploadForm = () => {
  const [name, setName] = useState('');
  const [description, setDescription] = useState('');
  const [images, setImages] = useState([]);

  const { getRootProps, getInputProps } = useDropzone({
    accept: 'image/*',
    multiple: true,
    onDrop: (acceptedFiles) => {
      setImages(acceptedFiles);
    }
  });

  const handleSubmit = async (e) => {
    e.preventDefault();

    try {
      const formData = new FormData();
      formData.append('name', name);
      formData.append('description', description);
      images.forEach((image) => {
        formData.append('images', image);
      });

      await axios.post('/api/products', formData);

      // Reset the form after successful upload
      setName('');
      setDescription('');
      setImages([]);
    } catch (error) {
      console.error('Error uploading product:', error);
    }
  };

  return (
    <form onSubmit={handleSubmit}>
      <input
        type="text"
        value={name}
        onChange={(e) => setName(e.target.value)}
        placeholder="Product Name"
      />
      <textarea
        value={description}
        onChange={(e) => setDescription(e.target.value)}
        placeholder="Product Description"
      />
      <div {...getRootProps()}>
        <input {...getInputProps()} />
        <p>Drag 'n' drop some images here, or click to select files</p>
      </div>
      <button type="submit">Upload</button>
    </form>
  );
};

export default ProductUploadForm;
  1. Set up the routes in your Express server.
const express = require('express');
const app = express();
const productRoutes = require('./routes/productRoutes');

app.use(express.json());

// Mount the product routes
app.use('/api', productRoutes);

// Start the server
app.listen(3001, () => {
  console.log('Server listening on port 3001');
});
  1. Start your MongoDB server and run your Express server by executing node server.js.

  2. Run your React client by executing npm start or yarn start in the client directory.

Now, when you submit the product upload form, the product data will be stored in MongoDB, and the images will be uploaded to Cloudinary. The Cloudinary URLs for the images will be stored in the images array of the corresponding product in MongoDB.

Make sure to replace the placeholders with your own MongoDB and Cloudinary credentials, and adjust the code based on your project structure. Additionally, handle any additional validation or error handling as per your application's requirements.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment