Skip to main content

사용자 친화적인 쿠버네티스 API 활용 툴 개발기

Less than 1 minuteDevOpsKubernetesArticle(s)blogyozm.wishket.comkubernetesk8s

사용자 친화적인 쿠버네티스 API 활용 툴 개발기 관련

Kubernetes > Article(s)

Article(s)

사용자 친화적인 쿠버네티스 API 활용 툴 개발기 | 요즘IT
최근 우리 팀에서 누구나 간단히 쿠버네티스 리소스를 생성, 조회, 삭제할 수 있는 운영 툴을 개발하자는 의견이 나왔다. 복잡한 클라우드 인프라를 쉽고 직관적으로 관리할 수 있게 만들어 생산성을 높이자는 취지였다. 본 개발에 앞서 다양한 UI와 UX를 시도하기 위한 프로토타입 개발이 시작되었고, 나도 여기 참여하게 되었다. 쿠버네티스 API를 활용해 툴을 개발하는 과정은 매력적이면서도 도전적인 작업이었다. 이 글에서는 툴의 개발 과정을 간략히 소개하고, 그 과정에서 가진 의문과 고민을 공유하고자 한다.
미드저니 생성
미드저니 생성

쿠버네티스(Kubernetes)는 컨테이너화된 애플리케이션의 자동 디플로이, 스케일링 등을 제공하는 시스템이다. 일반적으로 쿠버네티스 리소스를 생성하거나 수정할 때에는 터미널 커맨드로 접근해야 하므로 현재 상태를 직관적으로 확인하기 어렵다. 하지만 여러 클라이언트 라이브러리open in new window를 활용하면 다양한 프로그래밍 언어와 통합해 사용하거나 직접 상태 관리 툴을 만들 수 있다.

이러한 인프라 관리는 주로 데브옵스 엔지니어가 담당한다. 그런데 최근 우리 팀에서 누구나 간단히 쿠버네티스 리소스를 생성, 조회, 삭제할 수 있는 운영 툴을 개발하자는 의견이 나왔다. 복잡한 클라우드 인프라를 쉽고 직관적으로 관리할 수 있게 만들어 생산성을 높이자는 취지였다.

본 개발에 앞서 다양한 UI와 UX를 시도하기 위한 프로토타입 개발이 시작되었고, 나도 여기 참여하게 되었다. 쿠버네티스 API를 활용해 툴을 개발하는 과정은 매력적이면서도 도전적인 작업이었다. 이 글에서는 툴의 개발 과정을 간략히 소개하고, 그 과정에서 가진 의문과 고민을 공유하고자 한다.


사용자 친화적인 툴의 조건

쿠버네티스 API는 강력한 자동화와 추상화 기능을 제공한다. 이를 활용하면 개발자는 애플리케이션의 배포, 관리 및 확장을 더욱 효과적으로 수행할 수 있다. 우리는 쿠버네티스 API가 가진 장점은 살리되, 직관성은 더 높일 필요가 있었다. 그래서 웹 사이트 형태의 사용자 친화적인 툴을 만들기로 결정했다.

프론트엔드 개발에는 Vue.js를 사용하고, 백엔드 개발에는 타입스크립트 기반 NestJS를 사용하기로 했다.Vue.js는 사용자 상호 작용이 많은 동적 웹 인터페이스를 구현하는 데 적합하며, 양방향 데이터 바인딩을 제공한다. 특히 양방향 데이터 바인딩은 작은 규모나 중간 규모의 애플리케이션에서 상태를 빠르고 효율적으로 관리하는 데 유리하다. 따라서 팀 내부에서 사용하는 툴에는 적극적으로 Vue.js를 사용해 왔다. 이번 툴 역시 규모가 크지 않고 복잡한 상태 관리가 필요하지 않아 Vue.js가 적합하다고 판단했다. 백엔드 개발에 쓴 NestJS의 경우, 그 장점인 모듈성과 일관성이 유지 보수에 도움이 된다고 판단해 선택했다.

유저플로우는 단순하게 구성했다. 따로 홈페이지를 두지 않고, 사용자가 로그인에 성공하면 리소스 리스트 페이지로 이동하도록 했다. 이때 리소스는 팀 내부에서 별도로 정의해 사용하고 있는 커스텀 객체인데, 일반적인 쿠버네티스 리소스와 같다고 생각해도 무방하다. 리스트 페이지와 상세 페이지, Form 페이지는 다른 웹 사이트의 유저플로우와 유사하다. 또한 각 리소스 별로 리스트 페이지를 만들고, 사이드 메뉴로 진입할 수 있게 만들어 확장성을 확보했다. 앞으로 파드나 볼륨, 서비스, 네임스페이스 등 여러 리소스를 이 툴에서 관리하는 경우도 대비한 작업이었다. 상세 페이지와 생성 페이지는 쿼리 파라미터로 개별 라우트를 부여해 사용 편의성을 높였다.

우리 목표는 모두에게 친숙하면서도 쿠버네티스 API의 기능을 전부 활용할 수 있는 툴을 만드는 거였다. 마치 반대 방향으로 뛰어가는 두 마리 토끼를 한 번에 잡는 일 같았다. 사용자의 간단한 입력만으로 리소스를 만드는 일과 쿠버네티스 API가 제공하는 모든 옵션을 열어주는 일은 서로 충돌할 수밖에 없었다. 특히 Form 페이지에서 인풋 필드를 어떻게 배치할 것인지, 어디까지 생략할 것인지에 대한 의견이 분분했다.

결론적으로 논의 끝에 우리는 이런 절충안을 만들었다.

  • Form 입력단에서 단계를 나누고, 각 단계는 간결하게 배치할 것
  • 모든 옵션을 열어주되, 대부분 필드에 기본값을 채워둘 것

이로써 사용자는 꼭 필요한 인풋 필드 몇 개만 입력해 간단히 리소스를 만들 수 있게 되었다. 또한 필요할 때는 모든 필드를 직접 작성하여 쿠버네티스 API의 기능을 다양하게 활용할 수도 있을 것이다.


BFF 서버를 만들어야 할까?

사용자에 얼마나 많은 옵션을 제공할지 생각하다 보니 자연스레 BFF(Backend For Frontend)에 대한 고민으로 이어졌다. BFF란 프론트엔드의 요구에 맞추어 개별적으로 최적화된 백엔드를 제공하는 방식을 의미한다.

쿠버네티스 API는 특정 서비스를 대상으로 하지 않는 범용 API로 많은 옵션을 포함하고 있다. 다만 다양한 리소스를 일관된 형태의 API로 제공하다 보니 인터페이스가 복잡해졌다. 쿠버네티스 리소스는 파드, 서비스, 볼륨, 네임스페이스, 레플리카셋, 디플로이먼트 등 종류가 매우 다양한데, 이들 모두 비슷한 구조의 YAML 파일을 사용하여 생성된다. 리소스를 생성하려면 YAML 파일을 쿠버네티스 API에 payload로 전달해야 한다. 이때, YAML 파일은 주로 네 가지 핵심 필드를 포함한다.

  • kind: 리소스의 종류를 나타내며 생성하려는 리소스 유형(예: Pod, Service 등)을 지정할 수 있다.
  • apiVersion: 사용할 API의 버전을 명시한다. 이는 쿠버네티스의 해당 리소스를 정의하는 API 스펙의 버전을 나타낸다.
  • metadata: 리소스에 대한 메타데이터를 제공하며 이름, 네임스페이스, 레이블 등 정보를 포함할 수 있다.
  • spec: 리소스의 원하는 상태(specifications)를 정의하며 다양한 구성 옵션을 포함할 수 있다.
<출처: <FontIcon icon="fas fa-globe"/>ARMO 공식 홈페이지>
<출처: ARMO 공식 홈페이지open in new window>

kind 필드로 리소스 종류를 구분하고, metadata와 spec 필드에서 세부 옵션 값을 입력하면 새로운 리소스가 만들어진다. apiVersion은 말 그대로 API의 버전으로, 해당 리소스가 어떤 API 버전을 사용할 것인지를 알린다. API는 개발 과정에서 필요에 따라 새로운 기능을 추가하거나 기존 기능을 개선함에 따라 버전을 업데이트한다. 이전 버전의 API는 점진적으로 폐기될 수 있다. 만약 새로운 버전의 API 체계를 사용하려면 이 apiVersion을 업데이트해야 한다.

우리 백엔드 서버는 프론트엔드와 쿠버네티스 리소스 사이를 중개해 주는 브릿지 역할을 한다. 이 서버를 BFF로 만들거나, 아니면 범용 서버를 사용하되 추가로 BFF 서버를 만들면 어떨지 고민했다. 백엔드 서버가 프론트엔드에 쿠버네티스 API 형태를 그대로 제공하는 것과 간결하게 추상화하여 제공하는 것은 큰 차이가 있다.

개발 과정에서 고려한 장단점은 다음과 같다.

쿠버네티스 API 형태를 그대로 제공하는 경우

  • 장점: 초기 비용 및 유지 관리 측면에서 경제적이다. 개발 구조가 단순해지며, 직접적인 API 호출로 성능 이슈를 최소화할 수 있다.
  • 단점: 클라이언트에서 처리해야 할 비즈니스 로직이 증가한다. 이는 애플리케이션의 복잡도를 높이며 추후 유지 보수 비용을 증가시킬 수 있다.

서버에서 추상화한 API를 제공하는 경우

  • 장점: 툴의 클라이언트에서 복잡한 로직을 처리할 필요가 없이, 간결하고 추상화된 인터페이스로 쿠버네티스 리소스를 쉽게 관리할 수 있다. 또한, 중요한 로직이나 데이터를 클라이언트와 분리하여 보호할 수 있다.
  • 단점: 추가 서버 구축 및 관리가 필요하다. 이는 운영 비용 증가로 이어진다.

우리 팀은 결국 쿠버네티스 API 형태 그대로 제공하는 쪽을 선택했다. 필요성이 커진다면 그때 BFF 서버를 만들 수도 있을 것이다. 하지만 당장은 프로토타입을 개발하는 과정이고 적은 리소스로 빠른 결과물을 만들어야 한다는 데 모두 동의했다. 이로써 프론트엔드에서는 사실상 쿠버네티스 API를 직접 호출하는 것과 마찬가지가 되었다. 따라서 사용자에 더 많은 옵션을 제공하고 yaml 에디터로 직접 payload를 작성하는 기능까지 넣기로 했다.

여기까지 손쉬운 쿠버네티스 리소스 관리를 위한 툴의 모양이 잡혔다. 물론 사용자 테스트를 거쳐야 알겠지만, 약간의 적응 기간을 거쳐 익숙해지고 나면 모두에게 굉장히 유용한 툴이 될 것이라 예상해 본다.


마치며: 누가 복잡성을 감당해야 할까

쿠버네티스 API는 클라우드 기반 애플리케이션 관리의 핵심 요소로 자리 잡고 있다. 이 API는 강력한 자동화 기능으로 애플리케이션의 배포, 관리 및 확장을 간편하게 해준다. 여러 기업들 역시 이를 적용해 더 효율적으로 인프라를 관리할 수 있게 되었다. 최근에는 노코드(No Code), 로우 코드(Low Code) 툴이 여럿 생겨나며, 개발자의 영역 중 다수가 비개발자에게로 넘어가고 있다. 인프라 관리 역시 점차 더 쉽고 직관적으로 할 수 있게 진화하는 것은 자연스러운 흐름으로 보인다.

인프라 관리의 여러 부분이 자동화되었지만, 그 자동화 기능을 쓰기 위해 인프라 관리자가 선택해야 하는 옵션의 수는 그대로이거나 오히려 늘어났다. 자유도가 높다는 건 그만큼 사용하기 어렵다는 걸 의미한다. 결국, 누군가는 이러한 복잡함을 감당해야 한다. 사용자에 모든 선택지를 노출할 것인지, 아니면 프론트엔드 또는 백엔드 단에서 이를 감당할 지는 상당히 까다로운 문제다. 툴을 만들며 부딪힌 사용자 UI, BFF 서버 도입 여부 등은 이 문제의 연장선이었다.

어쩌면 당연한 말이지만, 이는 간결성 원칙과 비용-효율성의 균형을 잘 고려하여 팀의 상황에 맞게 결정해야 한다. 각 팀의 상황과 요구 사항에 따라 최적의 선택이 달라질 수 있으므로, 팀원들과 충분한 논의를 거쳐 합리적으로 결정하는 것이 중요하다. 다만 이 과정에서 중요한 건 팀원, 즉 사용자의 더 나은 경험이다. 너무 오래 고민하기보다 빠르게 프로토타입을 만들어 직접 장단점을 파악하는 게 좋을 때가 많다. 훌륭한 툴은 한번에 만들어지지 않는다.


이찬희 (MarkiiimarK)
Never Stop Learning.