본문 바로가기
Spring/10. rest-api

일반적인 MVC 와 @FeignClient에서 @RequestBody / @PathVariable의 사용법

by 989898 2025. 3. 18.

@RequestBody와 @PathVariable은 일반적으로 Spring MVC에서 사용하는 방식과 Spring Cloud OpenFeign에서 사용하는 방식에 약간의 차이가 있습니다. 아래에서 두 어노테이션의 일반적인 Spring MVC 사용 FeignClient 사용을 비교하여 설명하겠습니다.

1. @RequestBody

일반적인 Spring MVC에서의 동작

  • @RequestBody는 HTTP 요청의 body를 객체로 매핑합니다.
  • 클라이언트가 보낸 JSON 데이터를 서버에서 객체로 역직렬화합니다.
  • 주로 POST, PUT 요청에서 사용되며, 클라이언트가 데이터를 body에 담아 전송합니다.

예시 코드:

@RestController
@RequestMapping("/api/v1/blogs")
public class BlogController {

    @PostMapping
    public ResponseEntity<BlogResponse> createBlog(@RequestBody BlogCreateRequest blogCreateRequest) {
        // blogCreateRequest는 JSON 데이터를 객체로 변환한 결과
        return ResponseEntity.ok(new BlogResponse());
    }
}
 

전송된 HTTP 요청:

  • Method: POST
  • Body:
{
  "blogName": "My New Blog",
  "description": "This is a description."
}

FeignClient에서의 동작

  • @RequestBody는 FeignClient를 통해 객체를 HTTP 요청의 body로 직렬화하여 전송합니다.
  • Feign은 내부적으로 Jackson 또는 Gson을 사용하여 객체를 JSON 형식으로 변환합니다.
  • 서버는 JSON 데이터를 다시 객체로 역직렬화하여 처리합니다.

예시 코드:

@FeignClient(name = "blogAdaptor", url = "http://localhost:8080", path = "/api/v1/blogs")
public interface BlogAdaptor {

    @PostMapping
    ResponseEntity<BlogResponse> postBlog(@RequestBody BlogCreateRequest blogCreateRequest);
}
 

전송된 HTTP 요청:

  • Method: POST
  • Body:
{
  "blogName": "My New Blog",
  "description": "This is a description."
}
 

2. @PathVariable

일반적인 Spring MVC에서의 동작

  • @PathVariable은 URL 경로에 포함된 값을 메서드 파라미터로 매핑합니다.
  • 클라이언트가 URL 경로에 값을 포함하여 서버에 요청을 보냅니다.
  • 주로 GET, DELETE 요청에서 리소스를 식별할 때 사용됩니다.

예시 코드:

@RestController
@RequestMapping("/api/v1/blogs")
public class BlogController {

    @GetMapping("/{id}")
    public ResponseEntity<BlogResponse> getBlog(@PathVariable("id") Long blogId) {
        // blogId는 URL 경로에서 추출된 값
        return ResponseEntity.ok(new BlogResponse());
    }
}
 

전송된 HTTP 요청:

  • URL: http://localhost:8080/api/v1/blogs/123
  • Method: GET

FeignClient에서의 동작

  • @PathVariable은 FeignClient를 통해 URL 템플릿에 값을 삽입합니다.
  • Feign은 {}로 표시된 변수 자리에 해당 값을 자동으로 매핑하여 완성된 URL을 생성합니다.
  • 서버는 URL 경로에서 값을 추출하여 처리합니다.

예시 코드:

@FeignClient(name = "blogAdaptor", url = "http://localhost:8080", path = "/api/v1/blogs")
public interface BlogAdaptor {

    @GetMapping("/{id}")
    ResponseEntity<BlogResponse> getBlog(@PathVariable("id") Long blogId);
}
 

전송된 HTTP 요청:

  • URL: http://localhost:8080/api/v1/blogs/123
  • Method: GET

비교


기능 일반적인 Spring MVC 동작 FeignClient 동작
@RequestBody 클라이언트가 보낸 JSON 데이터를 객체로 역직렬화 객체를 JSON으로 직렬화하여 HTTP 요청 body에 포함
@PathVariable URL 경로의 값을 메서드 파라미터로 매핑 파라미터 값을 URL 템플릿에 삽입하여 완성된 URL 생성
 

차이점 요약

  1. 직렬화와 역직렬화 위치:
    • Spring MVC에서는 서버가 클라이언트의 요청 데이터를 역직렬화하여 처리합니다.
    • FeignClient에서는 클라이언트 쪽에서 데이터를 직렬화하여 HTTP 요청으로 보냅니다.
  2. URL 템플릿 처리 방식:
    • Spring MVC에서는 서버가 클라이언트가 보낸 URL 경로를 분석하고 값을 추출합니다.
    • FeignClient에서는 클라이언트 쪽에서 URL 템플릿을 완성한 후 서버로 전송합니다.
  3. 사용 목적 및 위치:
    • Spring MVC는 주로 서버 쪽 컨트롤러에서 사용됩니다.
    • FeignClient는 MSA 환경에서 서비스 간 통신을 위해 클라이언트 쪽 인터페이스에서 사용됩니다.

결론적으로, 두 어노테이션의 기본 동작은 동일하지만, FeignClient에서는 클라이언트 쪽에서 직렬화와 URL 템플릿 처리가 이루어진다는 점이 주요 차이입니다.


프런트엔드에서 JSON 데이터를 백엔드로 전달하는 방법

1. 프런트엔드에서 HTML Form을 통해 데이터 입력

 

프런트엔드에서 사용자가 데이터를 입력할 수 있도록 HTML Form을 생성합니다.

 

사용자가 데이터를 제출하면, 이를 BlogController가 처리합니다.

 

HTML Form 예시:

<form action="/blogs/create" method="post">
    <label for="blogName">Blog Name:</label>
    <input type="text" id="blogName" name="blogName" required>
    
    <label for="description">Description:</label>
    <textarea id="description" name="description"></textarea>
    
    <button type="submit">Create Blog</button>
</form>
 

2. BlogController에서 Form 데이터를 받아 처리

BlogController는 사용자가 입력한 데이터를 받아서 BlogService를 통해 백엔드로 전달합니다.

 

이 과정에서 JSON 데이터를 생성하여 BlogAdaptor를 호출합니다.

 

BlogController 수정 예시:

@Controller
@RequestMapping("/blogs")
public class BlogController {

    private final BlogService blogService;

    public BlogController(BlogService blogService) {
        this.blogService = blogService;
    }

    @PostMapping("/create")
    public String createBlog(@ModelAttribute BlogCreateRequest blogCreateRequest) {
        blogService.createBlog(blogCreateRequest);
        return "redirect:/blogs"; // 성공 후 블로그 목록 페이지로 리다이렉트
    }
}
 

3. BlogService에서 JSON 데이터 생성 및 전달

BlogService는 프런트엔드에서 받은 데이터를 BlogAdaptor를 통해 백엔드로 전달합니다.

 

BlogService 수정 예시:

@Service
public class BlogServiceImpl implements BlogService {

    private final BlogAdaptor blogAdaptor;

    public BlogServiceImpl(BlogAdaptor blogAdaptor) {
        this.blogAdaptor = blogAdaptor;
    }

    @Override
    public void createBlog(BlogCreateRequest blogCreateRequest) {
        ResponseEntity<BlogResponse> response = blogAdaptor.postBlog(blogCreateRequest);

        if (!response.getStatusCode().is2xxSuccessful()) {
            throw new ResponseStatusException(response.getStatusCode(), "Failed to create blog");
        }
    }
}
 

4. BlogAdaptor를 통해 백엔드에 JSON 데이터 전달

BlogAdaptor는 OpenFeign을 사용하여 HTTP 요청을 보냅니다.

 

여기서 @RequestBody를 사용하여 JSON 데이터를 백엔드로 전달합니다.

 

FeignClient 설정 예시:

@FeignClient(name = "blogAdaptor", url = "http://localhost:8080", path = "/api/v1/blogs")
public interface BlogAdaptor {
    @PostMapping
    ResponseEntity<BlogResponse> postBlog(@Validated @RequestBody BlogCreateRequest blogCreateRequest);
}
 

전체 데이터 흐름

  1. 사용자 입력: 프런트엔드 HTML Form에서 사용자 입력을 받음.
  2. Form 데이터 처리: @ModelAttribute를 통해 데이터를 컨트롤러로 전달.
  3. 서비스 호출: 컨트롤러가 서비스 계층을 호출하여 비즈니스 로직 수행.
  4. JSON 데이터 생성 및 전송: 서비스 계층이 OpenFeign 클라이언트를 통해 JSON 데이터를 백엔드로 전송.
  5. 백엔드 처리: 백엔드는 @RestController로 JSON 데이터를 받고 처리 후 응답 반환.

추가 고려사항

  • CSRF 보호: POST 요청 시 CSRF 토큰을 사용하는 것이 중요합니다.
  • Validation: @Validated와 같은 어노테이션으로 입력값 검증을 수행해야 합니다.
  • 에러 처리: 백엔드 응답이 실패했을 경우 사용자에게 적절한 메시지를 보여주는 로직 추가.

이 방식으로 프런트엔드에서 JSON 데이터를 생성하고 백엔드로 전달할 수 있습니다. OpenFeign과 같은 HTTP 클라이언트를 사용하면 MSA 환경에서도 서비스 간 통신이 간편해집니다!