FaaS 환경에서 Clean Architecture로 벤더 종속 탈출하기
서버리스 아키텍처를 도입할 때 가장 큰 고민 중 하나는 벤더 종속(Vendor Lock-in) 문제다. AWS Lambda에 최적화된 코드를 작성하다 보면 어느 순간 비즈니스 로직과 AWS SDK, 이벤트 모델이 뒤엉켜버린다. 이 상태에서 Azure Functions나 GCP Cloud Run으로 이전하려면 사실상 전면 재작성에 가까운 비용이 발생한다. 4년차 이상 백엔드 개발자라면 이 문제를 단순한 "나중에 해결할 기술 부채"가 아니라, 초기 설계 단계에서 반드시 고려해야 할 아키텍처 관심사로 다뤄야 한다.
Clean Architecture + Spring Cloud Function으로 레이어 분리하기
핵심 전략은 비즈니스 로직을 인프라 레이어로부터 완전히 격리하는 것이다. Clean Architecture의 의존성 역전 원칙(DIP)을 FaaS에 적용하면, 함수 핸들러는 단순히 외부 트리거를 내부 유스케이스로 위임하는 얇은 어댑터 역할만 수행한다. Spring Cloud Function은 이 구조를 실현하는 데 매우 적합하다. Function<I, O> 인터페이스로 비즈니스 로직을 정의하면, 동일한 코드가 AWS Lambda, Azure Functions, 혹은 일반 Spring Boot 서버로 아무 수정 없이 실행된다.
// 비즈니스 로직 (infra 의존성 없음)
class OrderProcessingFunction : Function<OrderRequest, OrderResult> {
override fun apply(request: OrderRequest): OrderResult {
// 순수한 도메인 로직
return OrderResult(orderId = request.id, status = "PROCESSED")
}
}
Gradle 멀티모듈 구성을 함께 활용하면 레이어 분리를 코드 수준에서 강제할 수 있다. core 모듈에는 도메인 모델과 유스케이스만 위치시키고, aws-adapter, azure-adapter 모듈이 각각 클라우드별 핸들러와 이벤트 매핑을 담당하도록 의존 방향을 설계한다. 이렇게 하면 CI/CD 파이프라인에서 core 모듈의 테스트가 클라우드 SDK 없이도 완전히 실행 가능해진다.
Terraform CDK로 멀티클라우드 IaC 구성하기
인프라 코드 역시 동일한 언어(Kotlin/TypeScript)로 작성할 수 있다는 점이 Terraform CDK의 강점이다. 클라우드 프로바이더별로 리소스 정의 방식은 다르지만, 공통 인터페이스를 추상화해 AWS와 Azure 배포 스크립트를 하나의 코드베이스에서 관리할 수 있다.
// Terraform CDK로 AWS Lambda 정의 예시
val lambda = LambdaFunction(this, "OrderFunction",
LambdaFunctionConfig.builder()
.functionName("order-processing")
.handler("org.springframework.cloud.function.adapter.aws.FunctionInvoker")
.runtime("java21")
.build()
)
실제 운영 관점에서 멀티클라우드 전략의 이점은 단순한 이식성에 그치지 않는다. 특정 클라우드의 장애나 요금 정책 변경에 대한 협상력을 확보할 수 있고, 규제나 데이터 주권 요구사항에 따라 리전 및 프로바이더를 유연하게 선택할 수 있다. 초기 설계 비용이 다소 늘어나지만, 장기적으로 운영 유연성 확보라는 측면에서 투자 대비 효과가 크다.
정리
- 비즈니스 로직은
Function<I, O>인터페이스로 추상화하고, 클라우드 어댑터는 별도 Gradle 모듈로 격리해 인프라 의존성이 도메인 코드에 침투하지 않도록 설계한다. - Spring Cloud Function을 활용하면 동일한 비즈니스 로직 코드를 AWS Lambda, Azure Functions, 일반 HTTP 서버 등 다양한 실행 환경에 재배포할 수 있다.
- Terraform CDK로 IaC를 애플리케이션 코드와 동일한 언어로 관리하면 멀티클라우드 배포 파이프라인의 일관성을 유지하면서 벤더 종속 리스크를 실질적으로 줄일 수 있다.