Upload files and multiple data together using FormData in React
Uploading a file in react by writing your own component is much better than understanding the nuances of a third-party library. It’s quite easy to send a file across through post in React using axios.
But, what if there is more data to send in with that post request? I have a form and a file upload (drag and drop) feature in the page and I want to send both together.
One way is to change the header’s content-type as multi-part/FormData
headers: {‘content-type’: ‘multipart/form-data’}
But that usually works when I am sending only one file across without additional data.
The best solution out there is by JavaScript itself — FormData
FormData uses append to upload files and data.
I have scoured the web for an efficient way to post data and files together using axios without creating bulk and redundant pages.
I have created a custom file upload hook using React dropzone called useDropzone():
The snippet allows multiple files to be uploaded as a Drag and Drop component or select from a file explorer.
For styling, I have chosen useMemo() hook:
The render function can display the file names I upload or the file size or anything I desire using the rootProps and inputProps.
Now, consider the main component like App.js where there is a form with multiple fields plus the file upload.
As an example, I am creating a contact us page with a form for queries. I am using hooks useEffect() and useState().
I have a topicId state that defines what your query is about, and a subject state and a description state in the form. There is an option to upload multiple files (eg: screenshots)
The parentfn() function calls the file upload component from the ReactDropzone component.
The handleChange() function calls the form inputs using switch case so you can always modify the number of inputs if need be.
The userId is to determined using access tokens. [0] determines only the id of the user as there are multiple parameters in the user data.
To upload only the file, use FormData append but to add multiple data along with files, append each data separately which is shown in the Gist above.
The interceptor is another component that checks for access token and refresh token for authentication and I don’t have to do it each time for every component, it makes the App component cleaner and less bulky.
To sum it up, I have a ReactDropzone component for file upload, an interceptor component which is for authentication of access and refresh token, and the main App component for the form data and file upload. Keeping them separate helps in the long run as it makes it highly flexible and reusable.
Please comment below if you have any questions.
:))