다중 이미지 전송(Error 415)

pengooseDev·2023년 2월 27일
0
post-thumbnail

BE에서 설정해준 데이터 타입과 FE가 보내주는 데이터 타입에서 차이가 발생하는 경우이다.
POSTMAN 기준 json 파일이 보이는 것이 아니라, 여러 key가 보인다면 아래의 방법을 따라하면 된다.

API 명세서에 작성된 POSTMAN 기준의 key는 해당 글에서 formData에 append되는 key이다.

HTML

<form onSubmit={sendImg} encType="multipart/form-data">
	<input
          type="file"
          name="myImages"
          accept="image/png, image/gif, image/jpeg"
          multiple
          onChange={handleUpload}
        />
	<input type="file" accept="image/*" name="myName" />           
	<button>보내기</button>   
</form>

두 가지 콜백이 필요함
1. 이미지 등록할 때, state(formData)에 에셋 추가하는 handleUpload
2. onSubmit때 나머지 데이터 formData에 추가해서 axios 요청보내는 sendImg


FormData?

Map이나 Set같은 객체임.
BE로 보내기 전, 이미지와 함께 보내는 json데이터는 JSON.stringify()처리 후, Blob에 Content-type을 BE에서 받는 데이터 타입(보통 application/json)을 명시해서 FormData에 같이 담아준다.
(BE에서 Content-type을 application/json으로 받는 데이터)

  • 이미지 이외의 데이터(댓글이나 닉네임 등)를 같이 보낼 때는 JSON.stringify()하여 FormData에 append해서 FormData 내부에 모아서 한 번에 보낸다.

ref


const sendData = () => {
  const [imgData, setImgData] = useState();

  const handleUpload = (e) => {
    const {
      target: { files },
    } = e;

    const formData = new FormData();
    for (let i = 0; i <= files.length - 1; i++) formData.append('image', files[i]);
	//files 배열을 순회하며 formData 객체에 추가
    
    setImgData((prev: any) => formData); //다른 callback에서 접근할 수 있도록 저장해주기
  };

  const testSendImg = async (e: React.FormEvent) => {
    e.preventDefault();
    const myFormData = imgData;
    const myData = {
      title: 'my_title',
      description: 'my_description',
      house_type: 'my_house_type',
      city: 'my_city',
      town: 'my_town',
      street: 'my_street',
    };//더미 데이터

    const json = JSON.stringify(myData);//데이터는 json타입으로 처리하고 blob에 넣어준다.
    const blob = new Blob([json], { type: 'application/json' });
    myFormData.append('data', blob);//최종적으로 formData에 API 명세서의 key에 맞게 넣어줌.

    const cookie = new Cookies();
    const res = await axios({
      method: 'POST',
      url: `${process.env.REACT_APP_API_BASE_ROUTE}/api/product`,
      data: myFormData,
      headers: {
        'Content-Type': 'multipart/form-data',
        Authorization: `${cookie.get('ACCESS_TOKEN')}`,
      },
    });

    console.log(res);
  };

  return (
	  <form onSubmit={testSendImg} encType="multipart/form-data">
		<Div>이미지 올리기</Div>
		<input
		  type="file"
		  name="myImages"
		  accept="image/png, image/gif, image/jpeg"
		  multiple
		  onChange={handleUpload}
		/>
		<button>등록 후, 서버로 이미지 요청 보내는 버튼</button>
	  </form>
  );
};

0개의 댓글