상세 컨텐츠

본문 제목

당신이 개발자라면 알아야 할 무기, Feature Flag

Programming/Concept

by 쌩우 2024. 3. 1. 22:08

본문

Feature Flag의 정의

Feature Flag(이하 피처 플래그)는 흔히 Feature Toggle이라고도 표현합니다.
표현 그대로 특정 기능에 대해 on/off와 같은 상태를 외부에서 제어할 수 있도록 하는 시스템입니다.

if (useFeatureIsOn('unhide-hidden-posts')) {
  // 게시글 숨김 목록 UI 노출 및 숨김 해제 기능 제공
} else {
  // 게시글 숨김 목록 UI 미노출 및 페이지 라우팅 제어
}

useFeatureIsOn 함수가 반환하는 값은 외부에서 해당 인자를 key로 갖는 설정값을 통해 결정됩니다.
피처 플래그를 조작할 권한이 있는 자가 unhide-hidden-posts 기능을 활성화하면 if문 으로 분기될 것이고,
비활성화하는 경우는 else문으로 분기되도록 설정할 수 있게 됩니다.

개념과 사용 방법 자체는 아주 간단합니다.

활용 방안

피처 플래그를 활용할 수 있는 여러 방법들이 있습니다.

1. A/B 테스팅 및 실험

https://admiral.digital/the-benefits-of-ab-testing/

피처 플래그를 사용하여 사용자 활동을 추적하거나 실험 결과를 수집하는 용도로도 활용할 수 있습니다. 이 데이터는 제품 개선 및 의사결정에 사용될 수 있습니다. 특정 사용자 그룹에 대한 기능을 활성화하거나 비활성화하여 어떤 버전이나 디자인이 더 효과적인지 비교 분석할 수 있습니다.

최근 제가 개발중인 포동 서비스 메인 화면에 Multiple A/B 테스트 를 적용해 볼 기회가 있었습니다.
기존에 제공중이던 퀘스트 기능에 대해 사용자들이 잘 인지하지 못하는 문제가 있었습니다.

포동 메인 화면

“물음표 모양의 아이콘과 퀘스트 라는 명칭의 제목이 눈에 잘 띄지 않는 것 같다”라는 점을 전제
경우를 세 가지로 나누어 테스트하게 되었습니다.
- A : 애니메이션 추가
- B : 툴팁을 통해 메뉴 강조
- C : 기존 형상 유지

Growthbook Experiments 중 각 테스트케이스별 스크린샷 첨부 상태

 

물론 각각의 경우별 노출 비율은 원하는대로 설정이 가능합니다.

id 값을 기준으로 분기 / 균등 비율 분배 (각 33% 비율) 적용

이번 실험의 경우 랜덤하게 그룹을 나눠주고, 노출 횟수 대비 퀘스트 메뉴 클릭 전환율 을 확인해보기로 했습니다.
때문에 분기 기준이 되는 id 값은 사용자를 특정짓는 owner id와 같은 값 대신 임의의 값으로 쿠키에 새롭게 세팅해주었습니다.

 

이 때, 노출 대비 클릭에 대한 전환율 산정은 amplitude의 view page event와 click event의 연계로써 집계합니다.

//page.tsx
...
useEffect(() => {
    sendViewPageEvent('HOME_MAIN', {
      quest: questFeatureType,
    });
  }, []);
...

//CircleButton.tsx
<CircleButton
    onClick={() => {
      sendButtonClickEvent(`클릭_메인홈_메뉴_${btn.ampliEventName}`, {
        click_id: 'button_001',
        quest: questFeatureType,
      });
    }}
/>

2. 긴급한 문제 대응

https://uxplanet.org/toggle-switch-5-simple-design-tips-for-better-design-b4046eff4a2f

앱에서 긴급한 문제가 발생했을 때, 특정 기능을 빠르게 비활성화하여 사용자에게 영향을 최소화하고 문제를 해결할 수 있습니다.

3. 진행 중인 작업 관리 (점진적 출시)

개발자 및 팀은 작업 중인 기능을 완료하지 않고 일부분만 구현하는 경우가 있습니다. 피처 플래그를 사용하면 완전한 기능을 릴리스하지 않고도 작업을 계속 진행할 수 있습니다. 상용 환경으로 작업 중인 코드를 반영해 놓은 후, 기능이 완전해지면 릴리스하면 됩니다. (원활한 Trunk Based Development를 실현할 수 있게 도와줍니다)

 

4. 환경별 관리

서로 다른 환경(개발, 스테이징, 프로덕션)에서 기능을 활성화 또는 비활성화하여 개발 및 테스트 단계에서의 일관성을 유지할 수 있습니다.

5. 서버 업그레이드 및 유지 보수

백엔드 서버의 업그레이드 또는 유지 보수 작업 중에도 특정 기능을 유지하거나 잠시 비활성화할 수 있으며, 이를 통해 서비스의 가용성을 보장할 수 있습니다.

6. 다른 사용자 그룹을 대상으로 커스텀화

특정 사용자 그룹에 대상으로 한 사용자 지정 기능을 활성화하여 고객 또는 파트너에게 특별한 기능을 제공할 수 있습니다. 특정 지역에 있는 사용자에 대해서만 새로운 UI를 노출한다거나 하는 방식으로도 동작할 수 있겠습니다.

심화 과정 - Server Driven UI

다같이 한 번 상상해보겠습니다.

오늘은 네이티브 앱 심사를 모두 마치고 힘겹게 배포를 마치고 얼마 지나지 않은 어느 날.
지금은 스프린트를 마무리하며 메인 화면의 변경 대응을 포함해 배포를 마치고 얼마 지나지 않은 시점.

이 때 누군가 말을 걸어옵니다.

디자이너 : “개발자님, 이 영역은 막상 배포해놓고 보니 위치를 아래쪽으로 옮겨야 보기 좋을 것 같아요.”

기획자: “개발자님, 이 영역 제목이 잘못된 것 같은데 바꿔주시겠어요?”


프론트엔드 개발자라면 누구나 한 번은 겪어봤을 상황입니다.

우리는 모든 상황이 완벽히 통제된 채로 흘러가길 바라지만 현실은 그렇지 못합니다.

여러분이라면 어떻게 대응을 하시겠습니까?

이전 버전 앱의 사용자라면 코드푸시로 밀어버리거나, 강제로라도 업데이트를 하도록 유도하시겠습니까?

웹 앱이라면 그나마 상황이 낫습니다.

(좀 귀찮지만) 하라는 대로 코드를 수정하고 다시 빌드하고 다시 배포하면 됩니다.

하지만 근본적으로 이런 문제가 발생했을 때 유연하게 대처하지 못하는 UI를 탓하기도 해야합니다.

UI가 유연해지려면 빌드와 배포에서 해방되어야 합니다.

서버가 결정하는 UI

서버는 클라이언트에 비해 변경, 배포가 자유롭습니다.

API를 통해 동적인 UI 구성을 상상해보도록 하겠습니다.

서버는 UI와 관련된 정보를 응답으로 반환하고, 클라이언트는 이 응답에 따라 렌더링을 하게 됩니다.

응답값을 변경하기만 했을 뿐인데 사용자가 보는 화면이 크게 영향을 받게 되는 것입니다.

예를 들어 사용자에게 어떤 책에 대한 정보를 제공하는 화면이 있다고 가정해봅니다.

서버는 현재 화면을 구성하는 UI 요소를 JSON 포맷으로 응답합니다.

클라이언트는 응답의 data 값을 사용해 각 name에 해당하는 UI 컴포넌트를 렌더링합니다.

서버

Book, Author, Reviews의 순서로 화면을 보여주도록 하는 서버 코드

JSON 응답값
 

클라이언트

서버 응답값을 통해 renderComponent 순차적 실행

클라이언트 디렉토리 구조

위 JSON 응답값을 이용해 렌더링한 화면은 아래와 같습니다.

서버에서 내려준 책, 저자, 리뷰 정보의 순서 그대로 클라이언트의 컴포넌트가 나열된 것을 확인할 수 있습니다.
현재 구성이 마음에 들지 않는다고 하면, 응답값을 조작하여 특정 영역을 제외시키거나 순서 또는 컴포넌트를 변경하여 보여줄 수 있게 됩니다.

사용자 편의 기능으로 활용한다면, 개인화의 영역으로 확장이 가능합니다.
특정 요구사항에 일치하는 인터페이스의 제공으로 이어질 수 있습니다.

서버에서 컨트롤 가능한 영역을 얼마나, 어떻게 가져갈 지는 설계 단계에서부터 긴밀히 논의가 되어야 합니다.
화면 전체에 대해 허용하거나, 헤더와 푸터 영역을 제외한 컨텐츠 영역만 허용할 것이냐, 레이아웃도 조작할 수 있게 만들 것이냐 등등 다양한 형태로 구성이 가능할 것입니다.

피처 플래그는 JSON 값으로도 설정이 가능한 경우가 대부분이다보니 server driven UI 정보의 일부를 담을 수 있습니다.

A/B 테스트 + Server Driven UI 적용을 통한 레이아웃 다양화 같은 예시 가능

장점

  • 앱 업데이트 없이 새로운 화면을 보여줄 수 있음
  • 개인화 지원

단점

  • 하위 호환성과 버전에 대한 관리 복잡도
  • 로딩 : 콘텐츠 데이터와 함께 인터페이스 형태 정보까지 한번에 가져와야 함
  • 오프라인 모드 : 오프라인일 땐 서버로부터 UI 정보를 응답받지 못함. 기본 설정으로만 구동.

Feature Flag 서비스

참고

'Programming > Concept' 카테고리의 다른 글

Sass (2) - 불러오기, 상속, 믹스인  (0) 2019.11.04
Sass (1) - 정의, 변수, 연산자, 내장함수, 중첩  (0) 2019.11.04
정규표현식  (0) 2019.07.17
마크다운 markdown  (1) 2019.07.16
Bootstrap 부트스트랩  (0) 2019.07.11

관련글 더보기

댓글 영역