돌려쓰던 테스트 환경을, 각자의 환경으로: 배포 병목을 없앤 이야기

Share
돌려쓰던 테스트 환경을, 각자의 환경으로: 배포 병목을 없앤 이야기

PEPE 세션 — 회원주문개발팀 정현수 님

과거 마이리얼트립의 공용 테스트 환경은 쓰려는 사람에 비해 모자랐습니다. 누가 쓰는지 알기 어려워 "지금 써도 되냐"고 서로 물어 가며 차례를 기다리는 경우가 많았고, 내가 작업 중인 사이 다른 사람이 배포하지 않도록 조율해야 했습니다. 이 병목을 환경 개수를 늘리는 방식에서 각자 자기 환경을 만들고 쓰고 없애는 구조로 옮긴 작업이 있습니다. 오픈소스의 제약에 막혔을 때는 그 코드를 직접 포크해 우리가 통제할 수 있도록 바꿔 왔고요. 그 과정을 PE 정현수 님의 시선으로 정리했습니다.

차례를 기다리고, 서로 조율해야 했던 환경

이 작업이 다룬 문제는 테스트 환경을 둘러싼 두 가지 병목이었습니다.

배경부터 짚으면 이렇습니다. 마이리얼트립에서는 다양한 직군이 프로덕트 엔지니어(PE)로 통합되면서, 테스트 환경을 직접 써야 하는 사람이 크게 늘었습니다. 문제를 정의하는 사람과 코드를 고치는 사람이 더는 나뉘어 있지 않으니, 환경 앞에 줄을 서는 사람도 그만큼 많아진 셈입니다.

그런데 공용 테스트 환경은 몇 개로 한정돼 있었고, 특정 서비스에서는 그 환경을 쓰려는 작업자가 환경 수보다 많았습니다. 그래서 첫째, 누가 그 환경을 쓰고 있는지 한눈에 알기 어려웠습니다. 작업을 시작하기 전에 "제가 지금 써도 되나요"라고 물어보고, 누군가 쓰고 있으면 끝날 때까지 기다리는 경우가 많았습니다. 둘째, 배포 타이밍을 서로 맞춰야 했습니다. 내가 환경에 무언가를 올려 두고 확인하는 동안 다른 사람이 자기 코드를 배포하면 내 작업이 영향을 받을 수 있어서, 누가 언제 배포하는지 서로 신경 써 가며 조율해야 했습니다.

쓰려는 사람은 많고 환경은 한정된 구조에서, 기다림과 조율이 매번 따라붙었습니다.

환경을 늘리는 게 답일까

가장 단순한 해법은 환경을 더 만드는 것이었습니다. 그런데 그 방향으로는 답이 나오지 않았습니다.

"환경을 늘리는 게 답일까 생각해 봤는데, 단기엔 되더라도 늘려도 또 모자라지 않을까 싶었어요. 그래서 각자 필요한 환경을 만들고, 쓰고, 없애면 되지 않을까로 방향을 바꿨습니다."

환경을 더 두면 당장은 숨통이 트입니다. 하지만 다섯 개, 열 개로 늘려도 쓰는 사람이 계속 많아지는 한 늘린 환경도 금세 다시 모자라집니다. 고정된 환경을 나눠 쓰는 한 같은 문제가 돌아온다는 뜻이었습니다.

이런 개인 환경을 만드는 흔한 방식은 서비스 메시와 헤더 기반 라우팅의 조합입니다. 요청 헤더에 표식을 담아, 그 사람의 트래픽만 그 사람의 환경으로 흘려보내는 방식이죠. 마이리얼트립도 헤더 기반 라우팅은 비슷하게 동작하지만, 개인 환경 라우팅을 위한 서비스 메시까지는 아직 갖추지 않은 단계였습니다. 절반의 재료만 갖춰진 상황이었습니다.

그래서 찾은 것이 mirrord라는 오픈소스였습니다. 로컬에서 서비스를 띄워 두면, 클러스터로 들어오는 외부 트래픽을 가로채 내 로컬로 흘려주는 도구입니다. 서비스 메시가 없어도 개인 환경에 가까운 그림을 만들 수 있는 출발점이었습니다.

로컬에서 컨테이너로, 다시 클라우드로

mirrord를 어디에서 돌릴지를 두고 세 번에 걸쳐 방식을 옮겼습니다. 매번 기준은 하나였습니다. 더 많은 사람이 어려움 없이 켜서 쓸 수 있는 쪽으로 가는 것.

처음에는 로컬에서 돌렸습니다. 여기서 두 가지 벽에 부딪혔습니다. 하나는 온보딩이었습니다. macOS의 시스템 보안 기능(SIP)에 여덟 번 막혔고, mirrord를 비롯해 쿠버네티스 접근 설정과 백엔드 런타임까지 직접 갖춰야 할 도구가 여덟 가지에 이르렀습니다. macOS에서만 이 정도였으니, 다른 운영체제라면 또 다른 벽이 기다리고 있었습니다. 다른 하나는 지연이었습니다. 트래픽이 브라우저에서 클라우드를 거쳐 로컬까지 왔다가 다시 돌아가는 경로라, 응답이 늦어 타임아웃이 나거나 화면이 제대로 그려지지 않았습니다. 기본 세팅이 이 정도로 까다로우면 많은 사람이 쓰기 어렵다고 봤습니다.

다음으로 컨테이너로 옮겼습니다. 필요한 도구들을 Docker 이미지 안에 미리 담아 두니, 각자는 Docker만 설치하면 됐습니다. 온보딩 쪽 벽은 이렇게 낮아졌습니다. 다만 트래픽이 멀리 돌아오는 경로 자체는 그대로라, 느린 응답은 구조적으로 남았습니다.

마지막으로 클라우드로 옮겼습니다. 로컬이나 컨테이너에서 환경을 띄우는 대신, 브라우저 확장 기능을 통해 개인 개발 환경에 연결해 작업할 수 있도록 했습니다. 트래픽이 로컬까지 내려왔다 올라가는 경로가 사라지니 지연 문제도 함께 정리됐습니다. 이 단계에서는 코어플랫폼팀의 지원으로 기존 배포 파이프라인을 활용할 수 있었던 점이 컸습니다. 배포 흐름을 새로 만들지 않고도 개발 환경을 손쉽게 준비할 수 있었기 때문입니다.

통제할 수 없는 제약을 내 것으로

방식을 클라우드로 옮기고 나서, 정작 가장 큰 벽이 남아 있었습니다. mirrord 오픈소스는 트래픽을 가로채는 에이전트가 하나만 떠서, 한 사람이 쓰면 다른 사람은 동시에 쓸 수 없는 구조였습니다. 모두가 자기 환경을 갖게 하려던 목표와 정면으로 부딪히는 제약이었죠. 동시 사용은 유료 팀플랜에서만 열리는 기능이라, 인원이 늘수록 비용도 같이 커져 도입에 부담이 있는 선택지였습니다.

남의 제품에 발이 묶인 상황이었습니다.

"제가 제어할 수 없는 제품에 발이 묶인 상황이라, 방법은 둘 중 하나였어요. 그대로 두거나, 한번 고쳐 보거나."

그래서 오픈소스를 직접 포크하기로 했습니다. 문제는 mirrord의 코드가 Rust로 작성돼 있고 현수님은 Rust를 다뤄 본 적이 없었다는 점입니다. 처음 보는 언어로 짜인 코드에서, 여러 사람이 동시에 못 쓰게 만드는 부분이 정확히 어디인지부터 찾아야 했습니다.

여기서 Claude Code를 썼습니다. 조직이 Claude Code를 평소 적극적으로 쓰고 있던 터라, 처음 보는 코드를 읽어 내는 일에 그대로 가져왔습니다. '여러 사람이 동시에 못 쓰는 문제'를 던지자 Claude Code가 코드 구조를 분석해, 동시 사용을 막고 있는 지점이 어디인지, 어떻게 고쳐야 하는지를 짚어 줬습니다. Rust를 공부한 적도 그 코드를 본 적도 없는 상태에서 수정 지점을 빠르게 찾아낸 것이, 이 작업을 가능하게 한 핵심이었습니다. 그렇게 짚은 자리를 고치고 테스트까지 마치는 데에는 반나절 안팎의 짧은 시간이 들었습니다.

결과적으로 하나의 공용 에이전트가 요청 헤더를 보고 각 사용자의 실행 환경으로 트래픽을 갈라 보내는 구조로 바꿨습니다. 한 사람이 쓰면 나머지가 기다려야 했던 도구가, 여러 사람이 동시에 각자의 환경을 띄울 수 있는 도구로 바뀐 것입니다. 통제할 수 없던 외부 제약을 직접 손댈 수 있는 우리 코드로 옮겨 온 셈입니다.

지금은 이렇게 쓴다

이렇게 완성된 도구를 쓰는 방법은 단순합니다. 브라우저 확장 기능을 설치하고 본인 식별자를 등록하면, 그 식별자가 붙은 요청만 자기 실행 환경으로 흘러가고 나머지 일반 트래픽은 원래 환경으로 갑니다. 그러면 자기만의 테스트 환경이 완성됩니다. 누가 쓰는지 물어볼 일도, 배포 타이밍을 서로 맞출 일도 없어졌습니다.

여기에 더해, 한 서버가 다른 서버를 호출하는 경우에도 식별자가 끊기지 않도록 분산 추적 컨텍스트(baggage)에 식별자를 실어 다음 서버까지 이어 전달했습니다.

여기까지가 현수님이 직접 손댄 부분이고, 그 위에서 작업은 여러 갈래로 뻗어 나갔습니다. 컨셉을 잡고 구현하는 동안 코어플랫폼팀이 함께 고민하며 아이디어를 보탰고, 터미널에서 바로 배포하는 흐름과 여행자 앱까지의 확장은 PS(Product Strategy)팀 동료들이 이어받아 완성했습니다. PS팀은 각 문제에 가장 잘 맞는 PE를 배치해서 문제 정의부터 구현과 배포까지 끝까지 책임지도록 하는 조직입니다.

다음 점을 찍는 일

지금은 대시보드로 사용 현황을 보고 있는데, 다양한 사람이 각자의 환경에서 일하고 있습니다. 한정된 환경에 줄을 서던 흐름이 사라지자, 여러 사람이 서로를 기다리지 않고 동시에 작업하는 흐름으로 바뀌었습니다. 아직 더 다듬을 부분도 남아 있어, 계속 개선해 가려 합니다.

돌려쓰던 테스트 환경이 각자의 환경으로 바뀌면서, 전사의 배포와 테스트 흐름이 실제로 달라졌습니다. 사람이 직접 켜는 환경을 넘어 AI 에이전트가 직접 쓰는 환경까지가 다음 방향입니다. 그 흐름 위에서 점을 이어 찍는 일이 남아 있습니다.


마이리얼트립의 PEPE(Product Engineer Possibility Exchange)는 프로덕트 엔지니어(PE)들이 "어디까지 시도했는지, 어디서 막혔는지"를 결과보다 과정으로 나누는 사내 세션입니다.

Read more

가장 중요한 문제에, 가장 잘 맞는 사람을 붙인다

가장 중요한 문제에, 가장 잘 맞는 사람을 붙인다

마이리얼트립의 프로덕트 엔지니어(PE)는 CTO 직속 PS팀(Product Strategy)에 모여 있습니다. 전사에서 가장 중요한 문제에 가장 잘 맞는 PE를 배치하고 한 명의 PE가 문제 정의부터 구현과 배포까지 끝까지 책임지는 조직입니다. 이렇게 한 데는 이유가 있습니다. 회사에서 가장 중요한 문제는 계속 바뀌는데, 사람이 특정 버티컬에 묶여 있으면 그 경계

By 마이리얼트립
예약에서 끝나지 않는 여행: 한 명이 10여 개 레포를 가로질러 만든 항공 여정 케어

예약에서 끝나지 않는 여행: 한 명이 10여 개 레포를 가로질러 만든 항공 여정 케어

마이리얼트립이 예약한 항공편의 운항 상태를 고객이 앱을 열지 않아도 실시간으로 받아보는 서비스를 선보였습니다. 출발 3시간 전 알림부터 게이트 변경과 지연, 결항, 회항, 출발, 도착, 수하물 상태까지, 비행의 흐름 전체를 고객이 찾기 전에 먼저 안내합니다. 여행은 항공권을 예약하는 순간 끝나지 않습니다. 짐을 싸고 공항으로 향하고 비행기에 올라 목적지에 내려 짐을 찾을

By 마이리얼트립
취소를 끝이 아니라 시작점으로: 취소 화면에서 다음 여행을 제안한 이야기

취소를 끝이 아니라 시작점으로: 취소 화면에서 다음 여행을 제안한 이야기

PEPE 세션 — 회원주문개발팀 배재경 님 마이리얼트립에서 여행 예약이 취소되는 순간을, 이탈이 아니라 다음 여행이 시작되는 지점으로 바꾼 작업이 있습니다. 회원주문개발팀이 취소 후 추천 경험을 다시 설계한 프로젝트로, 취소 화면의 추천 하나로 시작한 일이 "어떤 사용자에게, 어떤 순간에, 어떤 콘텐츠를 보여줄 것인가"를 다루는 구조로까지 자랐습니다. 그 과정을 배재경

By 마이리얼트립
출처가 분명한 여행, '마이 오리진'의 탄생 이야기

출처가 분명한 여행, '마이 오리진'의 탄생 이야기

마이리얼트립이 직접 기획한 여행 브랜드 '마이 오리진(MyOrigin)'을 선보였습니다. 마이리얼트립이 직접 여행을 설계하고 검증해 내놓은 셀렉션입니다. 마이 오리진에는 이미 일본 나오시마 예술 섬 워킹 투어, 파리의 플라워 클래스와 미식 투어, 시드니 하이킹, 프라하 맥주 공장 투어까지 여러 결의 여행이 자리 잡고 있습니다. 마이리얼트립은 이런 라인업을 직접 기획하고

By 마이리얼트립