by Sai gowtham

How to upload files in React with NodeJS & Express

How to upload files in React with NodeJS & Express

In this tutorial, we are going to learn about file uploading in React with using Express as a backend.

Creating Express Backend server

First, we are creating a post API using NodeJS & express, which helps us to upload the files like (images, pdf, etc) to the backend server.

Setup the backend project

Let’s setup the node.js backend project by running the following commands one by one.

mkdir fileupload
cd fileupload
npm init -y

Installing packages

Now, we need to install four packages which are express, express-fileupload,cors and nodemon.

Run the below command to install packages.

npm i express express-fileupload cors nodemon

Now open the fileupload folder in your favorite code editor and create a new file called server.js.

Add the following code to the server.js file.

server.js
const express = require('express');
const fileUpload = require('express-fileupload');
const cors = require('cors')

const app = express();

// middle ware
app.use(express.static('public')); //to access the files in public folder
app.use(cors()); // it enables all cors requests
app.use(fileUpload());

// file upload api
app.post('/upload', (req, res) => {

    if (!req.files) {
        return res.status(500).send({ msg: "file is not found" })
    }
        // accessing the file
    const myFile = req.files.file;

    //  mv() method places the file inside public directory
    myFile.mv(`${__dirname}/public/${myFile.name}`, function (err) {
        if (err) {
            console.log(err)
            return res.status(500).send({ msg: "Error occured" });
        }
        // returing the response with file path and name
        return res.send({name: myFile.name, path: `/${myFile.name}`});
    });
})


app.listen(4500, () => {
    console.log('server is running at port 4500');
})

In the above code, we first imported three packages which are express, express-fileupload and cors, next we created express application by invoking express() function.

Our post API route is /upload.

We are placing files inside the public folder so that we need to create a public folder inside our backend project.

Adding scripts

To run and restarting the server we are using the nodemon, open your package.json file and add the following code to scripts object.

 "server": "nodemon server.js"

Now start the backend server by running npm start server command in your terminal.

Creating React App

Let’s create the new react app by running the following command.

npx create-react-app react-fileupload

Now change your current working directory by running the below command.

cd react-fileupload

Installing Axios library

We also need to install the axios http client library which is used to make the http requests.

npm i axios

Creating file upload component

Open the react-fileupload folder in your favorite code editor and create a new file called fileupload.js inside the src folder.

Now add the following code.

fileupload.js
import React, { useRef, useState } from 'react';
import axios from 'axios';

function FileUpload() {

    const [file, setFile] = useState(''); // storing the uploaded file    // storing the recived file from backend
    const [data, getFile] = useState({ name: "", path: "" });    const [progress, setProgess] = useState(0); // progess bar
    const el = useRef(); // accesing input element

    const handleChange = (e) => {
        setProgess(0)
        const file = e.target.files[0]; // accessing file
        console.log(file);
        setFile(file); // storing file
    }

    const uploadFile = () => {
        const formData = new FormData();        formData.append('file', file); // appending file
        axios.post('http://localhost:4500/upload', formData, {
            onUploadProgress: (ProgressEvent) => {
                let progress = Math.round(
                ProgressEvent.loaded / ProgressEvent.total * 100) + '%';
                setProgess(progress);
            }
        }).then(res => {
            console.log(res);
            getFile({ name: res.data.name,
                     path: 'http://localhost:4500' + res.data.path
                   })
        }).catch(err => console.log(err))}

    return (
        <div>
            <div className="file-upload">
                <input type="file" ref={el} onChange={handleChange} />                <div className="progessBar" style={{ width: progress }}>
                   {progress}
                </div>
                <button onClick={uploadFile} className="upbutton">                   Upload
                </button>
            <hr />
            {/* displaying received image*/}
            {data.path && <img src={data.path} alt={data.name} />}
            </div>
        </div>
    );
}

export default FileUpload;

In the above code, we have used react hooks to manage the state and we have two functions which are handleChange and uploadFile.

The handleChange function is invoked once a user selected the file.

The uploadFile() function is used to upload the file to our /upload api.

There is also a progress bar, which shows how much amount of the file is uploaded and also we are displaying the image once a response comes from the server.

Adding css styles

Add the following styles to your App.css file.

.App {
    margin: 2rem auto;
    max-width: 800px;
}

img{
  width: 500px;
  height: 500px;
  object-fit: contain;
}

.progessBar{
  height: 1rem;
  width: 0%;
  background-color: rgb(68, 212, 231);
  color: white;
  padding:2px
}

.file-upload{

  box-shadow: 2px 2px 2px 2px #ccc;
  padding: 2rem;
  display: flex;
  flex-direction: column;

  justify-content: space-between;
  font-size: 1rem;
}

input , div , button{
  margin-top: 2rem;
}

.upbutton{
   width: 5rem;
   padding: .5rem;
   background-color: #2767e9;
   color: aliceblue;
   font-size: 1rem;
   cursor: pointer;
}

Now import the FileUpload component inside the App.js file.

App.js
import React from 'react';
import FileUpload from './fileupload';
import './App.css';

function App() {
  return (
    <div className="App">
      <FileUpload />
    </div >
  );
}

export default App;

Start the react app by running npm start.

Testing react file upload component

Let’s test our FileUpload component by uploading a sample image file.

Note: Make sure that your backend server is on.

Open your browser and navigate to localhost:3000.

uploading image file demo

Code repositories

Top Udemy Courses

JavaScript - The Complete Guide 2020 (Beginner + Advanced)
JavaScript - The Complete Guide 2020 (Beginner + Advanced)
26,545 students enrolled
52 hours of video content
View Course
React - The Complete Guide (incl Hooks, React Router, Redux)
React - The Complete Guide (incl Hooks, React Router, Redux)
221,520 students enrolled
44 hours of video content
View Course
Vue JS 2 - The Complete Guide (incl. Vue Router & Vuex)
Vue JS 2 - The Complete Guide (incl. Vue Router & Vuex)
114,575 students enrolled
21 hours of video content
View Course