후라이

@RequestBody 와 <form> 태그 본문

Spring

@RequestBody 와 <form> 태그

힐안 2025. 2. 5. 13:05

 

📌 1.  HTML <form> 태그의 기본 동작

HTML에서 <form> 태그를 사용하면 기본적으로 다음 두 가지 방식으로 데이터를 전송할 수 있다.

  1. application/x-www-form-urlencoded (기본값, POST 요청)
    • 키-값 쌍을 key1=value1&key2=value2 형태로 인코딩해서 전송
    • 브라우저에서 자동으로 데이터를 URL 인코딩해서 보냄
    • JSON이 아니라, @RequestParam이나 @ModelAttribute로 받아야 함
  2. multipart/form-data (파일 업로드 시)
    • 파일을 포함한 데이터를 보낼 때 사용
    • JSON 데이터를 포함하지 않음

🚨 application/json 방식이 아님!

<form> 태그는 기본적으로 JSON 형식(application/json)을 지원하지 않는다.
따라서, 폼 태그를 이용하면 Spring은 JSON을 받을 준비? 따위 하지 않음

 

📌 2.  실제 요청 방식 비교

❌ <form> 태그 기본 요청 (application/x-www-form-urlencoded)

<form action="/api/post/1" method="POST">
  <input type="text" name="title" value="새로운 제목">
  <textarea name="content">새로운 내용</textarea>
  <button type="submit">수정</button>
</form>

 

전송되는 데이터 (Request Body):

title=새로운+제목&content=새로운+내용

 

이렇게 전송되면, Spring이 @RequestBody가 아닌 @RequestParam이나 @ModelAttribute로만 받을 수 있다.
즉, JSON 형식이 아니라 단순한 키-값 쌍으로 넘어가는 거임.

✅ fetch()를 사용한 JSON 요청 (application/json)

fetch("/api/post/1", {
    method: "POST",
    headers: { "Content-Type": "application/json" },
    body: JSON.stringify({
        title: "새로운 제목",
        content: "새로운 내용"
    })
});

전송되는 데이터 (Request Body):

{
  "title": "새로운 제목",
  "content": "새로운 내용"
}

 

이 경우, Spring이 @RequestBody PostDto.Request postDto로 JSON을 받아서 처리할 수 있음

 

📌 3.  폼 태그로 JSON을 보낼 수 없을까?

폼 태그로 JSON을 보내려면, 기본 Content-Type을 application/json으로 변경해야 한다.
하지만 <form> 태그만으로는 이를 지정할 방법이 없음.

 

💡 해결 방법

  1. JavaScript fetch()를 사용해서 JSON으로 변환 후 전송 (내가 주구장창 하고 있는 거)
  2. <form> 태그를 쓰고 싶다면 method="dialog" 같은 커스텀 폼 처리 후 JS에서 변환
  3. Hidden Input 필드를 JSON 문자열로 만들어서 전송 후, 컨트롤러에서 파싱
    하지만 @RequestBody가 아니라 @RequestParam으로 받게 됨.
  4. <form> 태그에 onsubmit="return false;" 추가 후 fetch() 실행

 

📌 4.  그럼 <form> 태그는 무조건 쿼리스트링으로만 데이터를 보내나?

 

대부분의 경우 application/x-www-form-urlencoded (키-값 쌍) 방식으로만 동작하지만,
<form> 태그로 application/json을 보낼 수도 있긴 함. 다만, 브라우저 기본 동작을 막고 JS를 이용해야 함

-> 잘 안 쓰는 듯.

 

 

📌 결론

  1. <form> 태그는 기본적으로 JSON을 지원하지 않고, application/x-www-form-urlencoded 방식으로 보냄.
  2. @RequestBody는 JSON을 받도록 설계되어 있어서, <form> 태그를 그대로 사용하면 매칭되지 않음.