임동욱 임동욱 08-13
feat: backendFetch에 PUT과 form-urlencoded 전송 추가
백엔드의 일부 변경 API는 @RequestBody 없이 VO를 받아 JSON 본문을 바인딩하지
못한다(관리자 등록·수정). 그런 엔드포인트를 부를 수 있게 form 옵션을 연다.

Co-Authored-By: Claude Opus 5 
@17f4b6ee823b13871dd162adce63f18bbed87f43
lib/http/backend-fetch.ts
--- lib/http/backend-fetch.ts
+++ lib/http/backend-fetch.ts
@@ -50,8 +50,14 @@
 }
 
 type BackendRequestInit = {
-  method: 'GET' | 'POST';
+  method: 'GET' | 'POST' | 'PUT';
   body?: unknown;
+  /**
+   * form-urlencoded 본문. 백엔드의 일부 변경 API는 `@RequestBody` 없이 VO를 받아 JSON 본문을
+   * 바인딩하지 못한다(예: 관리자 등록·수정 — `@ParameterObject MngrAdminRequestVo`). 그런
+   * 엔드포인트는 이 필드를 쓴다. `body`와 함께 지정하지 않는다.
+   */
+  form?: Record<string, string>;
   /** 쿼리 스트링 파라미터. 값은 문자열로 직렬화해 붙인다. */
   query?: Record<string, string | number>;
   /**
@@ -182,12 +188,18 @@
     response = await fetch(resolveUrl(path, init.query), {
       method: init.method,
       headers: {
-        'Content-Type': 'application/json',
+        'Content-Type': init.form
+          ? 'application/x-www-form-urlencoded'
+          : 'application/json',
         ...(init.accessToken
           ? { Authorization: `Bearer ${init.accessToken}` }
           : {}),
       },
-      body: init.body !== undefined ? JSON.stringify(init.body) : undefined,
+      body: init.form
+        ? new URLSearchParams(init.form).toString()
+        : init.body !== undefined
+          ? JSON.stringify(init.body)
+          : undefined,
       signal: AbortSignal.timeout(REQUEST_TIMEOUT_MS),
       cache: init.cache,
       next: init.next,
Add a comment
List