자유도를 제약으로 바꾸고 컴포넌트에 목적과 책임을 완벽히 내장하여 개발자와 AI 모두를 위한 완벽한 코딩 계약을 만드는 방법
채널톡의 디자인 시스템 'Bezier(베지어)' 개편을 이끈 코어 웹팀의 설계 혁신 여정을 다룹니다. 단순히 UI 디자인을 변경하는 것을 넘어, 이제는 코드를 작성하는 주체가 된 AI 에이전트와 동료 개발자가 더 명확한 코드를 작성할 수 있도록 돕는 추상화 원칙을 정립했습니다. 범용적인 컴포넌트를 세분화하고 접근성 규칙을 강제 계약으로 치환한 구체적인 React 컴포넌트 설계 공식을 공개합니다.
AI 코딩 파트너와의 협업 효율을 극대화하고 싶거나 프론트엔드 컴포넌트의 오용 가능성을 설계 수준에서 원천 봉쇄하고 싶은 디자인 시스템 빌더와 테크 리더에게 강력히 추천합니다.
AI가 제품 코드를 직접 작성하는 시대가 도래하면서, 기존 디자인 시스템의 높은 자유도가 AI에게 모호한 맥락을 전달하여 일관되지 못한 코드와 웹 접근성이 누락되는 문제를 발생시켰습니다. 또한 시각적으로만 유사하고 목적이 다른 UI 요소들을 범용ListItem 하나로 처리하면서 사용처마다 복잡한 접근성과 인터랙션 로직을 매번 수동으로 작성해야 하는 번거로움이 있었습니다.
컴포넌트가 지켜야 할 불변조건을 명확히 하기 위해 TypeScript의 Union 타입을 적극 활용하여 유효하지 않은 상태의 조합을 컴파일 단계에서 차단했습니다. 범용 ListItem을 폐기하는 대신 DropdownMenu, Section, NavigationList 등 목적에 특화된 컴포넌트로 API를 분할하고, 시각적 공통 요소는 외부 노출 없이 내부의 BaseItem으로 공통화했습니다.
컴포넌트 자체에 의미, 접근성(ARIA), 키보드 포커스 이동 등의 상호작용 로직이 내장되어 사람과 AI 모두 추가적인 설명 없이도 컴포넌트를 안전하고 일관성 있게 조립할 수 있게 되었습니다. 잘못된 상태의 코드 작성이 원천 차단되어 개발 효율성과 결과물의 품질이 크게 향상되었습니다.
Trade-off
기존에 광범위하게 사용되던 범용 ListItem을 새로운 개별 컴포넌트로 교체하는 과정에서 마이그레이션 비용과 일정이 소요되었습니다. 자유도가 줄어든 만큼 특수한 레이아웃 요구가 있을 때는 as prop과 같은 탈출구를 명시적으로 열어주어야 하며 예외 처리에 대한 책임을 개발자에게 환기하는 장치가 필요해졌습니다.
컴포넌트의 복잡한 스타일과 기능적 세부 사항을 감추고 가장 직관적이고 결함 없는 형태의 인터페이스(Prop)만을 외부에 노출하는 설계 원칙입니다.
문서나 구두 규칙으로 오용을 방지하는 대신 TypeScript의 타입 시스템을 활용해 코드 컴파일 과정에서 정의되지 않거나 충돌하는 상태의 생성을 무효화하는 방법입니다.
장애 여부에 상관없이 키보드나 스크린 리더로도 동등한 사용성을 제공하도록 사전에 정의된 웹 표준 역할(role)과 제어 메커니즘을 적용하는 작업입니다.