스프링 WebFlux 와 코루틴

백엔드&인프라 추종자·2025년 2월 19일

스프링 공부

목록 보기
3/35

WebFlux와 코루틴을 같이 사용하는 것이 항상 좋은 것은 아닙니다. 하지만 특정 상황에서는 성능과 코드 가독성을 동시에 높일 수 있습니다. 이를 이해하기 위해 WebFlux와 코루틴의 특징을 비교하고, 언제 함께 사용하는 것이 좋은지 알아보겠습니다.


📌 1. WebFlux와 코루틴 비교

특성WebFlux (Mono/Flux)코루틴 (suspend, Flow)
패러다임리액티브 스트림비동기 함수
비동기 처리subscribe() 기반suspend 함수
데이터 흐름Mono(1개), Flux(N개)suspend(1개), Flow(N개)
러닝커브어려움 (flatMap, map 등 체이닝 필요)상대적으로 쉬움 (suspend 사용)
백프레셔(Backpressure)지원 (onBackpressureXXX())일부 제한적 지원 (Flow 사용 시 지원)
  • WebFlux (Mono, Flux)
    완전히 비동기 & 논블로킹 방식. RxJava와 유사한 리액티브 프로그래밍 스타일을 사용합니다.
  • 코루틴 (suspend, Flow)
    코드를 동기적으로 작성하면서도 비동기 실행이 가능하여 가독성이 좋습니다.

📌 2. WebFlux에서 코루틴을 함께 써야 할까?

WebFlux와 코루틴을 함께 쓰면 WebFlux의 리액티브 특성을 유지하면서도 가독성을 향상할 수 있습니다. 하지만 상황에 따라 다릅니다.

코루틴을 함께 쓰는 것이 유리한 경우

  1. 비동기 처리이지만 WebFlux 연산 체이닝이 복잡할 때
    • flatMap, map 등이 얽혀 가독성이 나빠지는 경우, suspend를 활용하여 간결한 코드 작성 가능
  2. 단순한 비동기 API 호출이 많을 때
    • REST API 호출, DB 조회 등을 연달아 실행하는 경우 가독성이 좋아짐
  3. WebFlux 기반 서비스에서 기존의 블로킹 코드와 혼합해야 할 때
    • 코루틴을 이용하면 withContext(Dispatchers.IO) 등을 활용하여 쉽게 조정 가능

📌 3. WebFlux + 코루틴 예제

🚀 (1) WebFlux 순수 리액티브 방식

@RestController
class UserController(val userService: UserService) {

    @GetMapping("/users/{id}")
    fun getUser(@PathVariable id: String): Mono<User> {
        return userService.getUserById(id)
            .flatMap { user ->
                userService.getUserDetails(user)
            }
    }
}

💡 단점: flatMap, map 체이닝이 많아질 경우 가독성이 떨어짐


🚀 (2) WebFlux + 코루틴 방식

@RestController
class UserController(val userService: UserService) {

    @GetMapping("/users/{id}")
    suspend fun getUser(@PathVariable id: String): User {
        val user = userService.getUserById(id)
        return userService.getUserDetails(user)
    }
}

장점: 동기 코드처럼 작성 가능 → 가독성 증가
WebFlux 유지: suspend가 있어도 여전히 논블로킹으로 동작


📌 4. 결론: 언제 WebFlux와 코루틴을 함께 써야 할까?

사용 경우WebFlux (Mono/Flux)WebFlux + 코루틴 (suspend)
리액티브 체이닝이 많을 때복잡함 (flatMap 중첩)간결한 코드 작성 가능
단순한 API 호출Mono.fromCallable 사용suspend로 깔끔한 코드
백프레셔가 중요한 경우Flux 사용 가능Flow 사용 가능
JPA (블로킹 I/O) 사용WebFlux와 따로 실행withContext(Dispatchers.IO) 활용 가능

👉 결론:

  • 완전히 리액티브 방식이 필요하다면 WebFlux (Mono, Flux) 사용
  • 가독성을 중요시하거나 기존의 블로킹 API와 혼합해야 한다면 WebFlux + 코루틴 사용
  • 복잡한 체이닝이 많다면 suspendFlow를 활용하면 코드 유지보수가 쉬워짐

즉, WebFlux를 쓰면서도 코루틴을 적절히 활용하면 성능과 가독성을 모두 잡을 수 있습니다! 🚀

profile
AI 답변 글을 주로 올립니다.

0개의 댓글