Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to correctly write FormData in my React app?

I have added a form in my app. When I send the form data to my local server I create an image with a title. When I attach images I should be using input type="file". Also, I should use FormData in my app.

But when I write my component I have an error 'formElem' is not defined in the two lines commented in the code. How do I fix it?

Here is my component code:

const AddImage = (props) => {
     formElem.onsubmit = async (e) => {         // ERROR THERE
       e.preventDefault();

          try {
              const response = await api(`${imageRoute}`, {
                  method:'POST',
                  body: new FormData(formElem),    // ERROR THERE
              }); 

          } catch(e) { 
              console.error(e);
          }   
    };

   return (

    <div className="formImage">

       <form id="formElem">
          <input type="text" name="name" value=""/>
          <input type="text" name="surname" value=""/>
          <input type="file" name="picture" accept="image/*"/>

        <div className="formButtonImage">
          <button type="submit">Add</button>
        </div>

       </form>
   </div>
   );
};
like image 375
tyry Avatar asked May 16 '20 13:05

tyry


2 Answers

There is quite a lot of issues in your code but this should fix most of them:

import React, { useRef } from "react";

const AddImage = (props) => {
  const formRef = useRef();

  const handleSubmit = async (event) => {
    event.preventDefault();
    const data = new FormData(formRef.current);
    // Let's assume that api and imageRoute SOMEHOW exists
    try {
      const response = await api(imageRoute, {
        method: 'POST',
        body: data,    // ERROR THERE
      }); 
    } catch(e) { 
      console.error(e);
    }  
  };

  return (
    <div className="formImage">
      <form onSubmit={handleSubmit} ref={formRef}>
        <input type="text" name="name" />
        <input type="text" name="surname" />
        <input type="file" name="picture" accept="image/*" />

        <div className="formButtonImage">
          <button type="submit">Add</button>
        </div>
      </form>
    </div>
  );
}

Make sure you remove value="" from your form elements, otherwise React will treat them as controlled and you will not be able to actually write to them.

like image 169
Láďa Durchánek Avatar answered Oct 11 '22 11:10

Láďa Durchánek


const AddImage = (props) => {
   const formEl = useRef(null)
   const onsubmit = () => {
       e.preventDefault();

      try {
          const response = await api(`${imageRoute}`, {
              method:'POST',
              body: new FormData(formEl.curent),    // ERROR THERE
          }); 

      } catch(e) { 
          console.error(e);
      }   
   }
   return (

    <div className="formImage">

       <form ref={formEl}onSubmit={onSubmit}>
          <input type="text" name="name" value=""/>
          <input type="text" name="surname" value=""/>
          <input type="file" name="picture" accept="image/*"/>

        <div className="formButtonImage">
          <button type="submit">Add</button>
        </div>

       </form>
   </div>
   );
};

But would be better to hang listener on did mount

const AddImage = (props) => {
       const formEl = useRef(null)
       useEffect(() => {
         formEl.current.addEventListener('submit', () => ...)
       }, [])

       return (

        <div className="formImage">

           <form ref={formEl}>
              <input type="text" name="name" value=""/>
              <input type="text" name="surname" value=""/>
              <input type="file" name="picture" accept="image/*"/>

            <div className="formButtonImage">
              <button type="submit">Add</button>
            </div>

           </form>
       </div>
       );
    };
like image 21
Aleksey Polonka Avatar answered Oct 11 '22 12:10

Aleksey Polonka