c++

12 개의 포스트

discord

Discord Social SDK 버전 1.10에서 모바일 플랫폼 지원 정식 출시 (새 탭에서 열림)

Discord Social SDK 1.10은 iOS와 Android 모바일 지원을 정식 출시해, 게임 개발자가 모바일에서도 Discord의 소셜 기능을 활용할 수 있게 했다. 주요 개선 사항은 Android Rich Presence, 딥링크 기반 계정 연결, 모바일 Discord Social Commerce이며, 이를 통해 플레이어 유지율·참여도·신규 유입을 높이는 것이 목표다. Tencent, Scopely, Ninja Kiwi 등의 사례는 친구 관리, 파티 구성, 커뮤니티 참여를 게임 경험과 자연스럽게 연결할 수 있음을 보여준다. ## 모바일 플랫폼 지원 정식 출시 - Discord Social SDK는 C++, Unreal Engine, Unity 프로젝트에서 사용할 수 있다. - 지원 플랫폼과 최소 버전은 다음과 같다. - Android 7.0 이상 - iOS 15.1 이상 - 모바일 환경에 맞춰 작은 화면과 이동 중 플레이를 고려한 기능 개선이 이루어졌다. - 계정 연결과 소셜 기능을 통해 게임의 도달 범위, 플레이 시간, 참여도를 높이는 것을 목표로 한다. ## Android Rich Presence 개선 - Android 게임에서 실시간 게임 상태를 공유하는 방법이 여러 가지로 확대됐다. - 계정 연결뿐 아니라 RPC(Remote Procedure Call)를 통해서도 Rich Presence를 제공할 수 있다. - 플레이어의 현재 게임 상태를 Discord 친구들에게 노출해 게임 발견과 소셜 공유를 촉진한다. - 향후 Rich Presence 초대 기능과 결합해 친구의 게임 참여를 유도할 수 있다. ## 딥링크 기반 모바일 계정 연결 - 모바일 계정 연결 과정에 딥링크가 추가됐다. - 브라우저 리디렉션이나 수동 로그인 절차를 줄여 앱 안에서 더 빠르게 Discord 계정을 연결할 수 있다. - Tencent의 Delta Force 사례에서는 단일 탭 방식의 계정 연결로 모바일 온보딩과 캠페인 활성화 과정의 마찰을 낮췄다. - 계정 연결은 게임 내 친구 목록, 초대, 커뮤니티 기능을 사용하기 위한 기반으로 활용된다. ## 모바일 Discord Social Commerce - Discord Social Commerce가 모바일로 확장돼, Discord를 통해 게임 아이템을 판매할 수 있게 된다. - 기존 플레이어뿐 아니라 친구와 잠재적인 신규 유저에게도 상품을 노출할 수 있다. - Marvel Rivals 파일럿 결과: - 구매의 41%가 선물 구매였다. - 선물 구매자의 25%는 휴면 유저 또는 신규 유저였다. - Discord의 소셜 관계가 수익화뿐 아니라 플레이어 재활성화와 신규 유입에도 기여할 수 있음을 보여준다. ## Tencent의 Arena Breakout 사례 - 크로스플랫폼에서 분산된 친구 목록과 파티 구성의 불편함을 해결하기 위해 SDK를 도입했다. - 주요 기능: - **Unified Friends List**: 여러 플랫폼의 친구 목록을 하나로 통합 - **Game Invites**: 분대 구성과 게임 초대 절차를 간소화 - 개선된 모바일 Account Linking - 도입 효과: - 분대 구성 시간 단축 - 세션 간 크로스플랫폼 메시지 증가 - 공식 Discord 서버 활동 증가 - 향후 기간 한정 게임 이벤트와 Discord 소셜 기능을 결합할 계획이다. ## Scopely의 Marvel Strike Force 사례 - Discord를 게임 내 커뮤니케이션과 동맹 관리 플랫폼으로 활용했다. - 플레이어 간 소셜 상호작용뿐 아니라 고객 지원과 커뮤니티 운영을 위한 전용 채널도 제공했다. - 도입 이후 나타난 결과: - 신규 플레이어의 계정 연결 증가 - 동맹별 Discord 채널 생성 가속 - 전반적으로 긍정적인 커뮤니티 반응 - 게임 커뮤니티 관리와 플레이어 지원을 Discord 안에서 함께 운영할 수 있다는 점을 보여준다. ## Tencent의 Delta Force 사례 - 공식 Discord 커뮤니티를 단순한 공지 채널이 아니라 플레이어가 함께 만들어가는 커뮤니티 공간으로 발전시켰다. - Account Linking과 Unified Friends List를 먼저 도입해 게임과 커뮤니티 사이의 경계를 줄였다. - 브라우저 이동과 수동 로그인 대신 모바일 단일 탭 계정 연결을 적용했다. - 주요 효과: - 온보딩 과정 개선 - 캠페인 참여 활성화 - 분대 구성 편의성 향상 - 커뮤니티 제작 콘텐츠와 게임 활동의 연결 - 향후 Discord 내 게임 검색 노출과 Rich Presence 초대 기능도 확대할 예정이다. ## Ninja Kiwi의 Bloons TD 6 사례 - Bloons TD 6는 Account Linking과 Unified Friends List를 도입해 Discord 기반 소셜 경험을 구축하기 시작했다. - 제공된 글의 내용은 이 사례의 초기 도입 기능을 소개하는 부분에서 끝나며, 구체적인 성과 수치는 제시되지 않았다. 모바일 게임에 Discord Social SDK를 도입하려면 먼저 계정 연결과 통합 친구 목록으로 진입 장벽을 낮추고, 이후 Rich Presence·게임 초대·커뮤니티 채널을 결합하는 방식이 효과적이다. 특히 모바일에서는 브라우저 전환과 수동 로그인 단계를 최소화하는 것이 온보딩과 유지율 개선에 중요하다.

cloudflare

프로젝트 글래스윙: Mythos가 우리에게 보여준 것 (새 탭에서 열림)

Mythos Preview는 단순히 취약점을 찾아내는 수준을 넘어, 여러 취약점을 연결해 실제 공격 경로를 구성하고 실행 가능한 증명 코드까지 생성하는 새로운 단계의 보안 도구로 평가된다. 그러나 모델의 자발적 거부는 일관되지 않으며, 탐색적 모델의 높은 오탐률 때문에 대규모 운영에는 별도의 안전장치와 검증·분류 체계가 필요하다. Project Glasswing의 핵심 교훈은 강력한 모델 자체뿐 아니라 이를 통제하고 결과를 검증하는 아키텍처가 함께 발전해야 한다는 점이다. ## Mythos Preview가 달라진 점 - Cloudflare는 Project Glasswing의 일환으로 Mythos Preview를 50개가 넘는 자체 저장소에 적용했다. - 이전 범용 프런티어 모델과의 단순한 성능 비교보다, Mythos가 실제로 수행하는 작업의 성격을 이해하는 것이 중요하다고 설명한다. - 기존 모델도 개별 버그를 발견하거나 영향도를 분석할 수 있었지만, 여러 조각을 하나의 공격으로 연결하는 단계에서 자주 멈췄다. ## 여러 취약점을 연결하는 공격 체인 - 실제 공격은 하나의 버그가 아니라 여러 취약점과 공격 원시 기능을 조합해 완성되는 경우가 많다. - 예를 들어: - use-after-free를 임의 메모리 읽기·쓰기 기능으로 전환 - 제어 흐름 탈취 - ROP(Return-Oriented Programming) 체인 구성 - 최종적으로 시스템 제어권 획득 - Mythos Preview는 낮은 심각도로 분류될 만한 개별 버그들을 결합해 더 심각한 실제 공격 경로를 추론할 수 있었다. - 이러한 추론 과정이 자동화된 스캐너보다는 숙련된 보안 연구자의 작업에 가깝게 나타났다는 점이 두드러졌다. ## 반복 실행을 통한 익스플로잇 증명 - Mythos Preview는 의심되는 취약점을 설명하는 데 그치지 않고, 이를 재현하는 코드를 직접 작성한다. - 생성한 코드를 격리된 scratch 환경에서 컴파일하고 실행해 예상한 동작이 발생하는지 확인한다. - 실패하면 오류 결과를 분석하고 가설을 수정한 뒤 다시 시도한다. - 이 반복 루프를 통해 단순한 “취약할 가능성”과 실제 악용 가능한 취약점을 구분한다. - 따라서 취약점 탐지와 익스플로잇 가능성 입증 사이의 간극을 모델 스스로 줄일 수 있다. ## 정당한 보안 연구에서의 모델 거부 - Project Glasswing에서 제공된 Mythos Preview에는 일반 공개 모델에 적용되는 추가 안전장치가 없었지만, 모델 자체적으로 일부 요청을 거부하는 경향이 나타났다. - 그러나 거부 기준은 일관되지 않았다. - 동일한 코드라도 실행 환경의 사소한 변화에 따라 연구를 허용하거나 거부했다. - 심각한 메모리 버그를 확인한 뒤에도 시연용 익스플로잇 작성은 거부할 수 있었다. - 요청 표현을 바꾸거나 실행 시점을 달리하면 반대 결과가 나오기도 했다. - 이러한 자발적 안전장치는 실제로 존재하지만, 확률적이고 상황 의존적이므로 단독 안전 경계로 사용할 수 없다. - 향후 공개되는 강력한 사이버 보안 모델에는 통제된 연구 환경 밖에서도 사용할 수 있도록 별도의 안전장치가 필요하다. ## 신호 대 잡음 문제와 오탐 - 보안 취약점 분석에서 가장 어려운 일 중 하나는 발견된 문제가 실제인지, 악용 가능한지, 즉시 수정해야 하는지를 판별하는 것이다. - AI 스캐너와 AI가 생성한 코드의 확산은 이 문제를 더욱 악화시켰으며, Cloudflare는 여러 후속 검증 단계를 구축해 대응하고 있다. ### 프로그래밍 언어의 영향 - C와 C++는 메모리를 직접 제어할 수 있어 다음과 같은 취약점이 발생하기 쉽다. - 버퍼 오버플로 - 경계 밖 읽기·쓰기 - 메모리 수명 관리 오류 - Rust와 같은 메모리 안전 언어는 이러한 버그 유형의 상당수를 컴파일 시점에 제거한다. - 실험에서는 메모리 비안전 언어로 작성된 프로젝트에서 오탐이 일관되게 더 많이 발생했다. ### 모델의 탐색 편향 - 숙련된 사람은 발견 내용과 함께 확신 수준을 명확히 제시하지만, 모델은 코드에 문제가 없어도 문제를 찾으려는 경향이 있다. - 결과에는 “가능성이 있다”, “잠재적으로”, “이론상 가능하다”와 같은 추측성 표현이 많이 포함된다. - 탐색 단계에서는 이런 보수적·과잉 탐지 성향이 유용할 수 있다. - 하지만 실제 트리아지 큐에서는 각각의 추측성 결과를 사람이 검증하고 기각해야 하므로, 수천 건으로 확장될 경우 인력과 모델 토큰 비용이 크게 누적된다. ## 실용적인 결론 Mythos Preview 같은 모델은 취약점 후보 발굴을 넘어 공격 체인 구성과 재현 증명까지 수행할 수 있어 보안 연구의 생산성을 크게 높일 수 있다. 다만 결과를 그대로 신뢰해서는 안 되며, 격리된 실행 환경, 다단계 검증, 신뢰도 기반 우선순위화, 일관된 안전 정책을 함께 구축해야 대규모 운영에 적합하다.

meta

포크에서 벗어나기: Meta가 50개 이상의 유스케이스에서 WebRTC를 현대화한 방법 (새 탭에서 열림)

메타는 대규모 오픈소스 프로젝트인 WebRTC를 커스터마이징하여 사용하며 겪었던 '포크 트랩(Forking Trap)'을 해결하기 위해, 최신 업스트림 버전과 내부 최적화 버전을 동시에 실행할 수 있는 듀얼 스택 아키텍처를 구축했습니다. 이를 통해 50개 이상의 유즈케이스에서 안전하게 A/B 테스트를 수행하며 성공적인 마이그레이션을 마쳤고, 결과적으로 성능 향상과 바이너리 크기 최적화 및 보안 강화를 달성했습니다. 현재 메타는 이 구조를 바탕으로 모노레포 환경에서도 업스트림의 최신 업데이트를 지속적으로 반영하며 기술적 부채 없이 서비스를 운영하고 있습니다. **포크 트랩과 모노레포 환경의 도전 과제** * 오픈소스 프로젝트를 내부적으로 포크하여 오래 사용하면 업스트림과의 격차가 벌어져 최신 기능을 반영하기 어려워지는 '포크 트랩'이 발생합니다. * 빌리언 단위의 사용자를 보유한 서비스에서 대규모 라이브러리를 한 번에 교체하는 것은 리스크가 크기 때문에, 구버전과 신버전을 동시에 실행하며 검증할 수 있는 A/B 테스트 역량이 필수적이었습니다. * 하지만 메타의 모노레포 환경과 정적 링크(Static Linking) 방식에서는 동일한 라이브러리의 두 버전을 동시에 포함할 때 '단일 정의 원칙(ODR)' 위반으로 인한 수천 개의 심볼 충돌 문제가 발생했습니다. **심(Shim) 레이어와 듀얼 스택 아키텍처** * 애플리케이션과 WebRTC 구현체 사이에 프록시 역할을 하는 '심(Shim) 레이어'를 구축하여 통합된 API를 제공했습니다. * 애플리케이션은 버전과 무관한 심 API를 호출하고, 심 레이어는 런타임 설정(Flavor)에 따라 레거시 또는 최신 구현체로 호출을 전달합니다. * 모든 라이브러리를 복제하는 대신 최하위 레이어에서 심을 구현함으로써, 바이너리 크기 증가폭을 예상치(38MB) 대비 약 87% 감소한 5MB 수준으로 억제했습니다. **심볼 충돌 해결과 하위 호환성 유지** * 자동화된 네임스페이스 재명명(Renamespacing) 스크립트를 통해 `webrtc::` 네임스페이스를 각 버전에 맞게 `webrtc_legacy::`, `webrtc_latest::` 등으로 분리했습니다. * 네임스페이스 외부에 존재하는 글로벌 C 함수와 변수들은 버전별 식별자를 추가하여 충돌을 방지했습니다. * 기존 코드의 수정을 최소화하기 위해 C++의 `using` 선언을 활용하여, 외부 호출부에서는 여전히 기존 네임스페이스를 사용하는 것처럼 보이게 하면서 내부적으로는 올바른 버전에 연결되도록 설계했습니다. **런타임 버전 디스패치 및 관리** * 템플릿 기반의 헬퍼 라이브러리를 사용하여 중복 로직을 줄이고 버전별 특화 동작을 정의했습니다. * 앱 시작 시점에 결정되는 글로벌 플래그(Enum)를 통해 어떤 WebRTC 버전을 사용할지 동적으로 결정합니다. * 패치 관리의 복잡성을 해결하기 위해 모노레포 내에서 업스트림 버전을 주기적으로 가져오고 내부 패치를 반복적으로 적용하는 워크플로우를 정립했습니다. 대규모 오픈소스 프로젝트를 운영할 때 직접적인 포크보다는 이와 같은 모듈식 아키텍처와 자동화된 네임스페이스 관리를 도입하는 것이 기술적 고립을 막는 효과적인 전략이 될 수 있습니다. 이는 특히 안전한 배포와 지속적인 업스트림 동기화가 중요한 대규모 시스템에서 실무적인 해법을 제시합니다.

toss

소프트웨어 3.0 시대를 맞이하며 (새 탭에서 열림)

소프트웨어 개발은 명시적 코딩(1.0)과 데이터 기반 학습(2.0)을 거쳐, 자연어 프롬프트가 프로그램이 되는 '소프트웨어 3.0' 시대로 진입하고 있습니다. 하지만 강력한 LLM 모델이라도 실질적인 업무를 수행하기 위해서는 모델의 능력을 제어하고 연결하는 '하네스(Harness)'라는 도구적 환경이 필수적이며, 이를 설계하는 데 있어 기존 소프트웨어 1.0의 계층형 아키텍처 원칙은 여전히 유효한 가이드가 됩니다. 결국 미래의 개발은 전통적인 설계 원칙을 유지하면서도, 에이전트가 인간과 소통하며 의사결정을 내리는 'Human-in-the-Loop(HITL)' 모델을 결합하는 방향으로 진화할 것입니다. **소프트웨어 3.0과 하네스의 필요성** - 안드레 카파시는 소프트웨어 3.0을 자연어로 된 프롬프트가 코드를 대신하는 시대로 정의하며, 이것이 이전 세대의 패러다임을 흡수할 것이라고 예측했습니다. - 하지만 LLM 단독으로는 코드베이스를 읽거나 데이터베이스에 접근하는 등의 실질적인 작업을 수행할 수 없다는 한계가 있습니다. - 이를 해결하기 위해 등장한 것이 '하네스(Harness)' 개념으로, 앤스로픽의 'Claude Code'처럼 모델이 도구(Skills)를 사용하고 외부와 통신하며 에이전트로 동작하게 만드는 실행 환경을 의미합니다. **계층형 아키텍처로 매핑한 에이전트 구조** - **슬래시 커맨드(Slash Command) = 컨트롤러(Controller):** `/review`, `/refactor`와 같은 명령어는 사용자 요청을 받아 적절한 워크플로우를 실행하는 서비스의 진입점 역할을 합니다. - **서브 에이전트(Sub-agent) = 서비스 계층(Service Layer):** 여러 기술(Skills)을 조합해 특정 비즈니스 로직을 완수하며, 독립적인 컨텍스트를 유지하는 단위입니다. - **기술(Skills) = 도메인 컴포넌트:** 단일 책임 원칙(SRP)에 따라 코드 리뷰, 테스트 생성 등 명확한 한 가지 기능만 수행하는 가장 작은 단위의 기능 모듈입니다. - **MCP(Model Context Protocol) = 인프라/어댑터:** 외부 API나 DB와의 연결을 추상화하여 내부 로직이 외부 시스템의 구현 상세를 몰라도 동작하게 돕습니다. - **CLAUDE.md = 프로젝트 헌장:** 기술 스택, 코딩 컨벤션 등 프로젝트의 변하지 않는 근간 원칙을 정의하며 시스템의 안정성을 보장합니다. **에이전트 설계에서 경계해야 할 안티패턴** - **God Sub-agent:** 하나의 서브 에이전트가 너무 많은 역할과 권한을 가지게 되면 관리 효율이 떨어지므로 적절한 분리가 필요합니다. - **기능 편애(Feature Envy):** 특정 기술이 자신의 역할 범위를 벗어나 다른 기술의 데이터나 프롬프트에 과도하게 의존하는 경우입니다. - **프롬프트 중복:** 동일한 프롬프트 내용이 여러 기술에 중복되어 포함될 경우 유지보수가 어려워지므로 공통화가 필요합니다. **에이전트만의 핵심 차별점: 질문하는 능력(HITL)** - 전통적인 소프트웨어는 예외 상황에서 미리 정의된 에러를 던지지만, 3.0 시대의 에이전트는 `UserAskQuestion` 기술을 통해 모호한 상황에서 사용자에게 직접 질문을 던질 수 있습니다. - 에이전트는 삭제나 배포처럼 되돌리기 어려운 작업, 혹은 여러 대안 중 선택이 필요한 고위험 상황에서 인간의 판단을 구하는 'Human-in-the-Loop' 구조를 가집니다. - 반면, 관습적으로 처리 가능한 일이나 안전한 반복 작업은 질문 없이 자율적으로 수행함으로써 효율성과 안정성 사이의 균형을 맞춥니다. 소프트웨어 3.0 시대에 적응하기 위해서는 모든 로직을 명시적으로 작성하려는 강박에서 벗어나야 합니다. 대신 계층 분리, 추상화, 단일 책임 원칙과 같은 전통적인 소프트웨어 공학의 정수를 에이전트 설계에 투영하여, LLM을 단순한 자동완성 도구가 아닌 신뢰할 수 있는 협력자로 구축하는 능력이 핵심 경쟁력이 될 것입니다.

figma

피그마 AI 검색의 (새 탭에서 열림)

Figma의 AI 검색은 텍스트·이미지·레이어 선택을 동일한 임베딩 공간에서 비교해 디자인과 컴포넌트를 의미적으로 찾도록 구축됐다. 핵심 기반은 CLIP 멀티모달 임베딩 모델과 벡터 검색 인덱스이며, 수십억 개의 임베딩을 생성·관리하면서도 비용과 처리량을 고려한 인프라 설계가 필요했다. 특히 파일 내부의 검색 가능한 프레임을 식별하고 썸네일과 임베딩을 비동기적으로 생성하는 과정이 주요 기술 과제였다. ## AI 검색이 해결하는 문제 - **디자인 검색** - 조직이나 팀 전체의 Figma 파일에 포함된 프레임을 검색한다. - 파일명이나 레이어 이름이 없어도 프레임의 시각적 내용으로 찾을 수 있다. - 텍스트 설명, 스크린샷, 선택한 Figma 레이어를 검색 입력으로 사용할 수 있다. - 선택 영역은 새 스크린샷으로 렌더링한 뒤 이미지 검색과 같은 경로로 처리한다. - **컴포넌트 검색** - 기존 Assets 검색의 엄격한 텍스트 일치 방식을 의미 기반 검색으로 확장했다. - 예를 들어 이름이 😀인 컴포넌트를 “smiley”, “happy”, “face”, “grin” 같은 표현으로도 찾을 수 있다. - 컴포넌트 이름과 설명에 검색 키워드를 일일이 추가하는 SEO 작업이 필요 없다. - 컴포넌트 역시 스크린샷이나 레이어 선택을 이용해 시각적으로 검색할 수 있다. ## CLIP 기반 멀티모달 임베딩 - 임베딩 모델은 텍스트나 이미지를 의미를 보존한 숫자 배열로 변환한다. - Figma는 현재 오픈소스 **CLIP** 모델을 사용한다. - CLIP은 이미지와 텍스트를 같은 벡터 공간에 표현한다. - 고양이 이미지의 임베딩과 `"cat"`이라는 텍스트의 임베딩이 서로 가까운 위치에 놓인다. - 따라서 이미지와 텍스트를 서로 다른 입력 방식으로 검색해도 의미적으로 비교할 수 있다. - 모델은 고객의 비공개 Figma 파일이나 고객 데이터를 학습에 사용하지 않았다. - 공개된 무료 Community 파일의 UI 이미지로 미세 조정했다. - 초기에는 선택 영역을 JSON 같은 텍스트 표현으로 변환해 임베딩하는 방식도 검토했다. - 그러나 이미지로 임베딩을 생성하는 방식이 더 나은 검색 결과를 제공했다. - 스크린샷 검색과 동일한 처리 경로를 사용할 수 있다는 장점도 있었다. ## 벡터 검색 처리 방식 - 검색 대상 콘텐츠마다 임베딩을 생성해 벡터 검색 인덱스에 저장한다. - 예: 디자인 시스템의 모든 컴포넌트와 각 컴포넌트의 임베딩 - 사용자가 검색하면 입력을 먼저 임베딩으로 변환한다. - 텍스트 검색은 입력 문장을 임베딩 모델에 전달한다. - 스크린샷 검색은 이미지에서 임베딩을 생성한다. - 레이어 선택 검색은 선택 영역을 스크린샷으로 만든 뒤 임베딩한다. - 생성된 쿼리 임베딩과 인덱스의 임베딩 사이 거리를 계산해 가장 가까운 항목을 반환한다. - 전통적인 문자열 검색처럼 검색어와 색인 항목을 직접 비교하는 것이 아니라, 고차원 벡터 공간에서 최근접 이웃을 찾는다. ## 검색 가능한 프레임 식별 - Figma 파일 깊숙한 곳에 있는 모든 검색 대상 프레임을 찾아야 한다. - 각 프레임에 대해 다음 작업을 수행한다. - Figma 레이어를 렌더링해 썸네일을 생성한다. - 썸네일에서 임베딩을 생성한다. - 메타데이터와 임베딩을 검색 인덱스에 기록한다. - 게시되지 않은 프레임은 일반적인 방식으로 쉽게 열거할 수 없다는 문제가 있다. - 이를 해결하기 위해 비동기 작업에서 서버 측 C++ Figma 에디터를 헤드리스 방식으로 실행한다. - 서버에서 C++ 에디터를 실행하기 위해 별도의 샌드박싱 기술을 사용한다. ## 저장소와 인프라 선택 - Figma는 자체 RDS 클러스터도 운영하지만, AI 검색에는 DynamoDB를 사용한다. - AI 검색의 저장 요구사항이 복잡한 관계형 트랜잭션보다 단순한 키-값 저장에 가깝기 때문이다. - 주요 요구사항은 다음과 같다. - 임베딩과 관련 메타데이터의 대량 저장 - 높은 쓰기 처리량 - 검색 시 빠른 읽기 - 대규모 인덱스 생성 및 갱신 처리 - 전체 시스템은 수십억 개의 임베딩을 생성하고 색인해야 하므로 검색 품질뿐 아니라 생성 비용과 운영 비용도 중요한 설계 기준이 된다. Figma의 접근 방식은 이미지와 텍스트를 하나의 의미 공간에 매핑하고, 프레임·컴포넌트별 임베딩을 사전에 구축하는 것이다. 유사한 기능을 구현한다면 먼저 검색 대상을 안정적으로 열거하고, 렌더링·임베딩 생성·색인 갱신을 비동기 파이프라인으로 분리하며, 모델 학습 데이터와 고객 데이터의 경계를 명확히 관리하는 것이 중요하다.

datadog

엔지니어링 부문 VP 스포트라이트: 이보 디미트로프 (새 탭에서 열림)

데이터독(Datadog)의 엔지니어링 VP 이보 디미트로프(Ivo Dimitrov)는 30년 이상의 경력을 가진 베테랑으로서, 고성능 저수준 시스템 개발자에서 대규모 분산 시스템을 총괄하는 리더로 성장해 온 인물입니다. 그는 마이크로소프트와 링크드인에서 쌓은 대규모 스토리지 인프라 구축 경험을 바탕으로, 현재 데이터독에서 메트릭과 이벤트 플랫폼의 기술적 혁신을 이끌고 있습니다. 기술적 깊이와 조직적 비전 사이의 균형을 강조하는 그의 여정은 복잡한 데이터 시스템을 다루는 엔지니어와 관리자들에게 중요한 통찰을 제공합니다. ### 저수준 시스템 개발에서 엔지니어링 리더십으로의 전환 * 전기 공학 전공 중 실시간 운영체제(RTOS) 커널 기여를 통해 소프트웨어 개발에 입문했으며, 이후 10년간 C/C++ 기반의 고성능 시스템 프로그래밍에 집중했습니다. * 마이크로소프트의 Azure Blob Storage 초기 팀에서 근무하던 중 조직 개편을 계기로 관리직을 맡게 되었으며, 현장에서의 실무 교육과 멘토링을 통해 리더십 역량을 쌓았습니다. * 자신의 업무에만 집중하는 단계를 넘어 타인의 성장을 촉진하고 조직 간의 경계를 조율하는 '오너십(Ownership)'의 가치를 발견하며 매니지먼트의 매력을 느꼈습니다. ### 대규모 분산 스토리지 플랫폼 구축 경험 * 링크드인 재직 당시, 현재까지 전체 데이터셋의 95% 이상을 처리하는 독점 키-값(Key-Value) 저장소인 'Espresso'를 초기 단계에서 성숙한 플랫폼으로 성장시켰습니다. * 파생 데이터 서빙을 위한 'Venice', 오픈소스 블록 스토리지인 'Ambry', 클러스터 관리자인 'Helix' 등 인터넷 규모의 스토리지 인프라 프로젝트들을 주도했습니다. * 이러한 경험을 통해 대규모 레거시 환경의 제약에서 벗어나, 기술적 위험을 감수하고 빠르게 혁신할 수 있는 문화적 유연성의 중요성을 깨달았습니다. ### 데이터독의 분산 데이터 시스템과 기술적 지향점 * 현재 데이터독에서 메트릭(Metrics), 이벤트(Events), 로그 및 트레이스 등 반정형 데이터를 처리하는 분산 데이터 시스템 조직을 총괄하고 있습니다. * 온라인 분석 워크로드에 최적화된 특수 메인 메모리 데이터베이스인 'Driveline'을 통해 시계열 데이터 처리의 효율성을 극대화하고 있습니다. * 서로 다른 도메인별 API를 통합하는 '교차 플랫폼 쿼리(Cross-Platform Queries)' 팀을 운영하여, 고객과 엔지니어 모두가 통일된 인터페이스로 데이터에 접근할 수 있도록 추상화 계층을 구축 중입니다. * 전체 쿼리의 80% 이상을 차지하는 알람(Alerts) 플랫폼을 메트릭 및 이벤트 플랫폼과 통합하여 시스템의 일관성을 높이고 있습니다. **실용적인 제언** 개인 기여자(IC)에서 관리자로 전환할 때는 기술적 전문성을 포기하는 것이 아니라, 그 전문성을 바탕으로 조직의 비전을 설계하고 팀원들이 역량을 발휘할 수 있는 환경을 조성하는 데 집중해야 합니다. 특히 데이터독의 사례처럼 쿠버네티스(Kubernetes) 기반의 현대적 인프라와 실험을 장려하는 문화를 결합할 때, 기술적 부채를 최소화하면서도 폭발적인 성장을 뒷받침하는 시스템을 구축할 수 있습니다.

figma

C++ 빌드 시간 단축하기 (새 탭에서 열림)

피그마(Figma)는 C++ 코드베이스가 10% 증가할 때 빌드 시간이 50%나 급증하는 문제를 해결하기 위해, 컴파일러로 전송되는 데이터 양(바이트)을 줄이는 전략을 채택했습니다. 하드웨어 업그레이드나 캐싱만으로는 한계가 있음을 깨닫고, 불필요한 헤더 포함을 자동으로 찾아내고 방지하는 자체 도구인 'DIWYDU'와 'includes.py'를 개발하여 빌드 시간을 절반으로 단축했습니다. 결과적으로 빌드 시간의 핵심 지표가 전처리 후의 바이트 수에 비례한다는 점을 입증하며 대규모 개발 환경에서의 생산성을 확보했습니다. ### 헤더 포함 방식과 빌드 속도의 상관관계 * C++ 컴파일 과정에서 전처리기(Pre-processor)는 소스 파일에 포함된 모든 헤더 파일을 하나의 거대한 파일로 합치며, 이는 전이적 의존성(Transitive dependency)을 포함해 컴파일러가 처리해야 할 바이트 수를 기하급수적으로 늘립니다. * 피그마의 분석 결과, 실제 추가된 코드량보다 전처리 후 컴파일러로 전달되는 바이트 수의 증가 폭이 훨씬 컸으며, 이것이 빌드 시간 지연의 주요 원인으로 파악되었습니다. * 대형 파일에서 불필요한 헤더를 수동으로 제거하는 실험을 진행한 결과, 컴파일 바이트는 31%, 콜드 빌드 시간은 25% 감소하며 가설이 증명되었습니다. ### DIWYDU: 불필요한 헤더 제거 자동화 * 구글의 IWYU(Include What You Use)가 너무 엄격하여 적용이 어렵자, 피그마는 더 유연한 자체 도구인 DIWYDU(Don’t Include What You Don’t Use)를 개발했습니다. * 이 도구는 `libclang`의 파이썬 바인딩을 사용하여 추상 구문 트리(AST)를 분석하며, 특정 파일이 포함한 헤더에서 함수, 타입, 변수 등을 직접적으로 사용하는지 확인합니다. * 직접적인 의존성이 없는 헤더를 찾아내어 삭제하도록 플래그를 표시함으로써 모든 기능 브랜치에서 빌드 속도 저하를 방지합니다. * 다만, STL(표준 템플릿 라이브러리)의 프라이빗 헤더 구조나 `libclang` 파이썬 바인딩의 AST 노드 접근 제한(UNEXPOSED_EXPR 등)과 같은 기술적 한계는 존재합니다. ### includes.py를 통한 회귀 방지 및 측정 * 헤더를 실제로 사용하더라도 파일 크기가 너무 커서 빌드 속도를 늦추는 경우를 대비해, 전이적 바이트 수를 측정하는 `includes.py`를 구축했습니다. * Clang을 사용하지 않고 순수 파이썬으로 작성되어 실행 속도가 매우 빠르며(수 초 내외), CI(지속적 통합) 시스템에서 각 PR이 빌드 시간에 미치는 영향을 바이트 단위로 측정합니다. * 특정 PR이 컴파일 바이트 수를 과도하게 늘릴 경우 경고를 발생시켜 개발자가 전방 선언(Forward Declaration)을 사용하거나 헤더를 분리하도록 유도합니다. * 표준 라이브러리는 피그마 내부의 래퍼(Wrapper) 디렉토리를 통해 관리되므로, 표준 헤더의 바이트는 계산에서 제외하여 효율성을 높였습니다. C++ 프로젝트의 빌드 속도를 유지하기 위해서는 단순한 캐싱을 넘어 컴파일러가 처리하는 데이터의 총량을 관리해야 합니다. 불필요한 헤더 의존성을 제거하는 자동화 도구를 CI 파이프라인에 통합하고, '컴파일 바이트 수'를 성능 지표로 모니터링하는 것이 대규모 코드베이스의 개발 효율을 높이는 실질적인 방안이 될 수 있습니다.

figma

서버 측 샌드박싱 (새 탭에서 열림)

서버 측 샌드박싱은 악성 입력을 처리하는 애플리케이션의 취약점이 전체 인프라로 확산되는 것을 막는 방어 계층이다. 이미지·데이터 처리 라이브러리처럼 메모리 안전성이 낮고 취약점이 반복적으로 발견되는 소프트웨어를 완전히 제거하거나 재작성하기는 현실적으로 어렵기 때문에, VM·컨테이너·seccomp 등을 이용해 실행 환경과 접근 가능한 자원을 제한해야 한다. 중요한 것은 특정 기술 하나를 선택하는 것이 아니라 보안성, 운영 복잡도, 성능, 격리 수준 사이의 트레이드오프를 workload 특성에 맞게 평가하는 것이다. ## 사용자 입력을 처리할 때 발생하는 위험 - 이미지 처리, 파싱, 압축, 썸네일 생성은 SaaS 애플리케이션에서 흔히 필요한 작업이다. - 이러한 기능은 C++ 같은 메모리 비안전 언어로 작성된 라이브러리에 의존하는 경우가 많다. - 해당 라이브러리는 원래 악의적인 입력을 처리하도록 설계되지 않았으며, 메모리 손상 취약점이 반복적으로 발견되어 왔다. - 대표적인 사례가 2016년 ImageMagick에서 발견된 **ImageTragick**이다. - 사용자가 제공한 이미지를 서버에서 처리하는 서비스가 원격 코드 실행 공격에 노출될 수 있었다. - 모든 버그와 취약점을 사전에 제거하는 것은 사실상 불가능하므로, 취약점이 발생하더라도 피해 범위를 제한하는 방어책이 필요하다. ## 서버 측 샌드박싱의 역할 - 샌드박싱은 애플리케이션이나 작업을 제한된 환경에서 실행하는 **workload isolation** 기법이다. - 공격자가 취약한 작업을 장악하더라도 다음과 같은 접근을 제한하는 것이 목표다. - 다른 작업의 사용자 데이터 - 운영 환경의 내부 서비스 - 파일 시스템과 네트워크 자원 - 추가 시스템으로의 lateral movement - Figma는 C++로 작성된 서버 측 렌더링 시스템인 RenderServer와 사용자 생성 그래픽 데이터를 처리하는 서드파티 라이브러리를 사용한다. - 이러한 작업을 인프라 내부에서 직접 실행하면 단 하나의 심각한 버그가 다른 사용자 데이터나 운영 시스템 침해로 이어질 수 있다. - 모든 unsafe 코드를 메모리 안전 언어로 다시 작성하고 정적 분석으로 정확성을 증명하는 방법도 있지만, 비용과 시간이 크며 완벽한 보안을 보장하지도 않는다. - 따라서 취약점 예방과 함께, 취약점이 악용되었을 때 영향 범위를 줄이는 격리 전략을 병행한다. ## VM, 컨테이너, seccomp - 글에서는 서버 측 샌드박싱의 대표적인 구현 방식으로 다음 세 가지를 소개한다. - **가상 머신(VM)**: 하이퍼바이저 위에서 각 게스트 운영체제를 실행한다. 인프라와 작업 사이에 하이퍼바이저 및 게스트 OS 계층이 존재한다. - **컨테이너**: 호스트 운영체제의 기능과 커널을 공유하면서 컨테이너 엔진을 통해 작업을 분리한다. VM보다 가볍게 실행할 수 있지만 격리 특성이 다르다. - **seccomp**: 프로세스가 호출할 수 있는 시스템 콜을 제한하는 Linux 보안 기능이다. - 각 방식은 격리 강도, 실행 비용, 성능, 시작 시간, 운영 편의성, 설정 복잡도 등에서 서로 다른 특성을 가진다. - 실제 환경에서는 단일 기술만 사용하기보다 workload의 신뢰 수준과 필요한 권한에 따라 여러 샌드박싱 primitive를 조합할 수 있다. ## 샌드박싱 선택 시 고려할 점 - 샌드박싱은 보안 취약점을 없애는 기술이 아니라, 취약점이 발생했을 때 공격의 범위와 피해를 제한하는 방어 계층이다. - 선택 과정에서는 다음을 함께 검토해야 한다. - 처리 대상이 사용자 입력인지, 내부에서 신뢰할 수 있는 데이터인지 - 작업이 필요한 파일·네트워크·시스템 콜의 범위 - 강한 격리에 필요한 성능 및 비용 - 샌드박스의 생성·폐기와 패치·모니터링 운영 부담 - 샌드박스 자체의 탈출 가능성과 호스트에 미치는 영향 - 샌드박싱 기술은 과거보다 안정적이고 실용적으로 발전했지만, 여전히 보안 연구와 운영 경험이 중요한 분야다. 악성 입력을 처리하는 기능은 메모리 안전 언어로의 전환만으로 보호하려 하기보다, 최소 권한과 강한 실행 격리를 함께 적용하는 것이 현실적이다. 특히 사용자 데이터를 다루는 고위험 작업은 VM이나 컨테이너 격리를 검토하고, 불필요한 시스템 콜은 seccomp로 추가 제한하는 접근이 유용하다.

figma

피그마가 게임 세계에서 (새 탭에서 열림)

피그마는 단순한 웹 애플리케이션을 넘어 고성능 게임 엔진과 유사한 기술적 아키텍처를 기반으로 구축된 창의적 협업 도구입니다. 이 글은 피그마가 실시간 멀티플레이어 시스템, 물리 기반 애니메이션, 그리고 C++와 WebAssembly, Rust와 같은 고성능 스택을 통해 어떻게 디지털 세계를 구축하는지 설명합니다. 결과적으로 피그마는 게임 개발의 복잡한 시스템 상호작용 원리를 차용하여 사용자들에게 몰입감 있고 매끄러운 디자인 경험을 제공하고 있습니다. ## 디지털 세계를 구축하는 엔진으로서의 피그마 * 피그마의 핵심은 웹 기반의 2D 그래픽 및 렌더링 시스템으로, 이는 마인크래프트와 같은 게임 엔진의 근간과 동일한 구조를 가집니다. * 사용자가 생성하는 모든 텍스트, 도형, 선을 브라우저에서 실시간으로 구현하며, 방대한 캔버스에서의 팬(pan)과 줌(zoom) 조작 시에도 정확한 위치에 객체를 렌더링합니다. * 실시간 동시 편집 기능을 게임의 개념에서 착안한 '멀티플레이어(multiplayer)' 엔진이라고 명명하여 협업의 핵심 시스템으로 발전시켰습니다. * 브라우저 및 모바일 앱의 메모리와 성능 제약을 극복하기 위해 일반적인 웹 스택 대신 C++로 캔버스를 구축한 후 WebAssembly로 컴파일하여 로딩 속도를 3배 개선했으며, 서버 측 성능 향상을 위해 Rust 언어를 도입했습니다. ## 시스템 기반의 창의적 협업과 상호작용 * 게임 스튜디오에서 엔지니어와 아티스트가 협업하듯, 피그마 엔지니어들은 시스템의 한계를 밀어붙이기 위해 디자이너, PM, 데이터 과학자들과 긴밀하게 소통합니다. * '젤다의 전설: 브레스 오브 더 와일드'의 불(fire) 시스템이 빛, 온기, 공격 수단 등 다양한 방식으로 상호작용하는 것처럼, 피그마의 오토세이브, 멀티플레이어, 렌더링 시스템도 서로 유기적으로 연결되어 작동합니다. * 단순한 도구 기능을 넘어 스프링 물리 법칙을 적용한 애니메이션 시스템, 커서 채팅, 하이파이브 기능 등을 통해 사용자가 도구 내에서 살아있는 피드백을 느낄 수 있도록 설계했습니다. * 베리언트(Variants) 기능과 플러그인/위젯 시스템을 통해 디자인 컴포넌트와 코드를 긴밀하게 연결하고, 사용자가 직접 생태계를 확장할 수 있는 개방형 플랫폼을 지향합니다. 웹 환경에서 복잡하고 성능 집약적인 도구를 개발해야 한다면, 전통적인 웹 프레임워크의 틀을 벗어나 게임 엔진의 설계 방식과 고성능 언어(WASM, Rust) 도입을 검토해야 합니다. 기술적 한계를 극복하는 열쇠는 도구를 하나의 살아있는 '시스템'들의 집합으로 바라보고, 각 요소 간의 상호작용이 사용자 경험에 미치는 영향을 정교하게 설계하는 데 있습니다.

figma

피그마 내부 이야기: 신입 (새 탭에서 열림)

Josh Shi는 대학 졸업 후 Figma에 입사한 경험을 바탕으로, 취업을 “좋은 회사의 조건을 체크하는 일”이 아니라 자신과 일의 관계를 탐구하는 과정으로 바라보자고 말한다. 특히 일과 삶을 서로 상쇄되는 두 영역으로 보지 말고, 함께 삶을 구성하며 서로 영향을 주는 요소로 이해해야 한다고 강조한다. 신입 엔지니어에게는 회사의 명성보다 자신의 관심사·성장 방식·가치관이 실제 업무 환경과 맞는지를 질문하라고 조언한다. ## 정답이 아닌 질문으로 취업을 바라보기 - 저자는 대학 졸업 당시 Figma를 선택한 이유를 완벽하게 설명할 수 없었다고 고백한다. - 면접에서 만난 사람들이 친절하고 사려 깊으며, 자신을 한 사람으로 이해하려는 태도를 보였던 점이 인상적이었다. - “흥미로운 문제”, “똑똑한 동료”, “좋은 문화” 같은 일반적인 평가 기준만으로는 개인에게 의미 있는 직장을 판단하기 어렵다. - 회사 선택에서 중요한 것은 정해진 체크리스트보다 다음과 같은 자기 성찰이다. - 어떤 종류의 일에 관심이 있는가? - 회사가 그 관심사를 발전시킬 기회를 제공하는가? - 관심사가 바뀌었을 때 업무나 역할도 변화할 수 있는가? - 어떤 기술과 전문성을 쌓을 수 있는가? - 일이 직장 밖의 다른 관심사와 삶의 방향에도 어떤 영향을 주는가? ## ‘일과 삶의 균형’이라는 단순한 프레임의 한계 - 일과 삶을 시소의 양쪽처럼 보는 전통적인 “work-life balance” 개념은 지나치게 단순하다. - 일과 비업무 시간은 서로 독립된 영역이 아니라, 합쳐져 한 사람의 삶을 구성한다. - 업무 만족도는 개인 생활의 만족도에 영향을 주고, 반대로 삶의 상태도 업무 경험에 영향을 준다. - 단순히 근무 시간을 줄이거나 일정한 시간 비율을 맞춘다고 해서 올바른 균형이 만들어지는 것은 아니다. - 사람마다 일에 자신의 정체성을 얼마나 연결할지는 다르며, 어느 한 방식이 정답은 아니다. - 저자는 일과 삶을 어떻게 배치해야 자신이 원하는 방식으로 살 수 있는지 질문해야 한다고 말한다. - 다만 모든 사람이 업무 환경을 자유롭게 선택할 수 있는 것은 아니다. 생계와 고용 안정성이 우선인 상황에서는 일을 커리어의 일부로 바라볼 여유가 제한될 수 있다. ## 신입으로서 얻은 기술적·실무적 성장 - Figma에서 새로운 기술 경험을 쌓았다. - 풀스택 개발을 경험했다. - 웹 환경에서 C++를 사용하는 업무를 접했다. - 단순히 코드를 작성하는 것을 넘어 기능을 실제로 소유하고 제품 개발 과정에 참여했다. - 다음과 같은 제품 개발 역량을 배웠다. - 기능과 제품의 범위를 현실적으로 정하기 - 모호한 목표를 구체화하기 - 아이디어를 처음부터 출시까지 발전시키기 - 제품을 신중하게 설계하고 구현하기 - 신입 개발자에게 기술 스택보다 중요한 성장 요소는 기능의 전체 생명주기를 경험하고 결과에 책임지는 것이라고 볼 수 있다. ## 멘토와 조직 환경의 영향 - 저자의 성장에는 주변 동료들의 지원과 지도가 결정적인 역할을 했다. - 동료들은 의도적으로 멘토 역할을 하지 않았더라도, 도전할 기회와 업무 소유권을 제공하며 성장을 도왔다. - 면접 당시 함께 식사했던 동료들 중 상당수가 계속 Figma에 남아 있었고, 저자는 그들의 경험과 관대함으로부터 지속적으로 도움을 받았다. - 신입이 회사를 평가할 때는 공식적인 복지나 문화 설명뿐 아니라 다음 요소도 살펴볼 필요가 있다. - 질문하고 도움을 요청하기 쉬운가 - 신입에게 실제 책임과 소유권을 주는가 - 동료들이 지식을 공유하는가 - 새로운 역할이나 기술을 시도할 수 있는가 ## 회사와 역할은 계속 변한다 - 저자가 입사한 뒤 Figma는 회사와 제품 모두 크게 성장했다. - 입사 당시와 현재의 조직 환경은 달라졌으며, 회사는 하이브리드 모델로 전환하기 시작했다. - 따라서 취업 선택은 고정된 조건을 고르는 일이 아니라, 변화하는 회사 안에서 자신의 관심과 역할이 어떻게 발전할 수 있는지를 판단하는 일이다. - 좋은 직장은 처음부터 모든 조건이 완벽한 곳이라기보다, 개인의 성장과 변화에 맞춰 역할을 확장하거나 조정할 수 있는 환경일 수 있다. 취업을 준비하는 신입 개발자는 회사의 유명세나 기술 목록만 비교하기보다, 자신이 배우고 싶은 방식과 일의 의미를 먼저 정리하는 것이 좋다. 면접에서는 업무 내용뿐 아니라 멘토링, 기능 소유권, 역할 변화 가능성, 조직의 성장 방향을 구체적으로 질문하는 것이 실용적이다.

figma

피그마 내부: 원격 인 (새 탭에서 열림)

원격 인턴십은 관계 형성과 업무 맥락 습득에 어려움이 있을 수 있지만, 의도적으로 소통 기회를 만들고 적극적으로 질문하면 충분히 의미 있는 경험이 될 수 있다. Jenning Chen은 Figma에서 스타일 피커 개선 프로젝트를 맡아 검색, 색상 스타일 목록 보기, 텍스트 스타일 지표 표시를 구현했으며, 인턴도 실제 사용자 기능의 기획부터 출시까지 주도할 수 있음을 보여준다. 이 과정에서 협업과 피드백, 대규모 데이터 마이그레이션을 경험하며 제품 이해도와 기술 역량을 함께 넓혔다. ## 원격 환경에서의 따뜻한 온보딩 - 입사 직후 Slack 환영 메시지와 온라인 커피챗을 통해 팀원들과 관계를 형성했다. - 동료들이 만든 Figma 환영 카드와 낙서가 담긴 파일을 받으며 대면 없이도 회사의 개방적 문화를 느꼈다. - 원격 근무에서도 신입 구성원이 소속감을 느끼도록 의도적인 환영 절차가 중요했다. ## 원격 인턴십의 우려와 관계 형성 - Slack이나 이메일에서 메시지를 놓치거나 오해할 가능성, 팀원들과 깊은 관계를 만들기 어려울 가능성을 걱정했다. - 회사 전체 쇼앤텔, 기술 강연, 일대일 미팅 등을 통해 다른 팀의 업무와 구성원들의 관심사를 접했다. - 온라인 요리 수업, 방 탈출, 보물찾기 같은 활동은 업무 외적인 관계 형성에도 도움이 됐다. - 원격 환경에서는 우연한 대화가 줄어드는 대신, 조직이 교류 기회를 의도적으로 설계해야 했다. ## 제품 이해도와 질문하는 문화 - 프로젝트를 시작하기 전 Figma의 기능과 디자인 용어를 충분히 익혀야 했다. - 멘토, 팀원, Slack 채널에 적극적으로 질문하며 제품과 업무 맥락을 파악했다. - 문제가 생겼을 때 동료들이 기꺼이 화상 통화를 열어 함께 해결해 주었고, 이는 원격 환경에서도 빠르게 배울 수 있는 기반이 됐다. ## 스타일 피커의 기존 문제 - 스타일 피커는 페인트, 텍스트, 효과, 레이아웃 그리드 스타일을 찾아 적용하는 기능이다. - 스타일 수가 늘어나면서 기존 인터페이스가 복잡해졌다. - 긴 목록을 수동으로 스크롤해야 했고, 특히 색상 스타일의 이름처럼 중요한 정보가 잘 드러나지 않았다. - 사용자가 원하는 스타일을 빠르게 찾고 비교할 수 있도록 개선 요구가 컸다. ## 스타일 피커 개선 기능 - **검색 기능** - 사용자가 몇 글자만 입력해 원하는 스타일을 빠르게 찾을 수 있게 했다. - **색상 스타일 목록 보기** - 기존 격자 보기에서는 가려지던 스타일 이름을 썸네일 옆에 명확히 표시했다. - 목록 보기와 격자 보기를 전환할 수 있도록 했다. - **텍스트 스타일 지표 표시** - 텍스트 스타일을 선택할 때 중요한 글꼴 크기와 줄 높이를 직접 보여줬다. - 스타일을 적용하기 전에 핵심 속성을 확인할 수 있어 선택 시간을 줄였다. ## 여러 기술 스택을 활용한 구현 - 디자인 시스템 팀의 프로젝트 특성상 에디터부터 백엔드까지 전체 기술 스택을 다뤘다. - 에디터에서는 TypeScript와 C++를, 백엔드에서는 Ruby를 사용했다. - 단일 기능을 구현하면서 프론트엔드, 에디터 내부 로직, 백엔드 데이터 처리까지 폭넓은 경험을 쌓았다. ## 출시 과정의 협업과 기술적 난관 - 완성된 기능을 사내 쇼앤텔에서 발표하고 동료들의 피드백을 받았다. - 출시 전 수백만 개의 기존 텍스트 스타일에 글꼴 크기와 줄 높이 메타데이터를 추가하는 마이그레이션이 필요했다. - 해당 마이그레이션만 실행하는 데 하루가 걸렸으며, 리뷰 피드백 반영과 출시 직전 버그 수정도 진행했다. - 구현 과정의 어려움은 제품 구조와 데이터 흐름을 더 깊이 이해하는 계기가 됐다. ## 실용적인 시사점 원격 인턴십이나 신규 프로젝트에서는 정기적인 일대일 미팅, 공개적인 질문 채널, 업무 외 교류 기회를 미리 마련하는 것이 효과적이다. 또한 작은 기능이라도 사용자 문제를 명확히 정의하고, 기존 데이터와 마이그레이션 비용까지 고려하면 실제 출시 가능한 제품으로 발전시킬 수 있다.

figma

웹에서 전문적인 디자인 도구 (새 탭에서 열림)

Figma는 전문 디자이너가 받아들일 수 있는 고품질 편집 경험을 웹 브라우저에서 제공하기 위해, 사실상 “브라우저 안의 브라우저”를 구축했다. 웹 플랫폼의 제한적인 추상화 대신 WebGL·asm.js 같은 저수준 기술을 활용하고, C++ 기반 편집기와 자체 메모리·렌더링 시스템으로 성능과 플랫폼 간 일관성을 확보했다. 특히 Emscripten을 통해 네이티브에 가까운 성능과 예측 가능한 프레임률을 달성하는 것이 핵심 전략이다. ## 웹에서 전문 디자인 도구를 만들기 어려운 이유 - 웹은 원래 문서 표시를 위해 설계되었고, 애플리케이션 개발 기능은 이후 개별 API 형태로 덧붙여졌다. - 따라서 특정 기능은 제공하지만, 개발자가 이를 조합해 새로운 동작을 구현할 수 있는 범용적인 저수준 primitive가 부족하다. - CSS는 복잡한 텍스트 배치 알고리즘을 제공하지만: - 알고리즘을 직접 커스터마이즈하기 어렵고 - 브라우저가 계산한 결과를 읽어 다른 알고리즘에 재사용하기도 어렵다. - 브라우저의 GPU 컴포지터는 고성능이지만: - 렌더링 과정에 직접 개입하기 어렵고 - 사용자 정의 블렌드 모드나 애플리케이션 특화 최적화를 추가할 수 없다. - 이미지 디코더는 하드웨어 가속과 비동기 처리를 지원하지만: - EXIF 방향 정보를 어떻게 처리할지 지정하기 어렵고 - 디스플레이 색 공간을 이미지 데이터에 미리 반영하지 않도록 제어하기 어렵다. - WebGL과 asm.js의 등장으로 개발자가 브라우저에 기능 추가를 기다리지 않고 하드웨어에 가까운 수준에서 필요한 기능을 직접 구현할 수 있게 되었다. ## Emscripten으로 C++ 편집기 실행 - Figma 편집기는 C++로 작성하고 Emscripten으로 JavaScript로 크로스 컴파일했다. - Emscripten은 asm.js를 대상으로 하며, asm.js는 JIT가 예측 가능하고 compact한 기계어를 생성하기 쉬운 JavaScript 부분집합이다. - 이 방식의 장점: - 메모리 배치를 직접 제어할 수 있어 64비트 부동소수점 중심인 JavaScript보다 32비트 float나 byte를 효율적으로 사용할 수 있다. - 객체를 미리 할당한 typed array 영역에 배치해 JavaScript 가비지 컬렉터의 개입을 피한다. - GC 중단으로 인한 프레임 저하를 줄여 60fps 달성에 유리하다. - LLVM 최적화와 C++ 템플릿 특수화를 활용해 네이티브 성능의 약 2배 이내 수준까지 접근할 수 있다. - asm.js에는 일반 JavaScript의 JIT 추론에 따른 deoptimization 지점이 없어 실행 성능이 더 예측 가능하다. ## 대용량 메모리와 브라우저 제약 대응 - Emscripten은 전체 메모리 공간을 하나의 큰 typed array에 담기 때문에 연속된 주소 공간을 충분히 확보해야 한다. - 특히 32비트 Chrome on Windows에서는 ASLR이 주소 공간을 파편화해 256MB typed array조차 할당하지 못하는 문제가 있었다. - Figma는 대형 이미지·기하 버퍼를 주 힙 외부의 별도 typed array에 저장하고, 이를 C++에서 참조하는 `IndirectBuffer` API를 만들었다. - 이 방식은: - 장시간 실행 시 메모리 파편화를 줄이고 - 32비트 브라우저의 제한된 주소 공간을 더 효율적으로 사용하며 - 64비트 브라우저의 31비트 typed array 크기 제한을 우회한다. - 해당 `IndirectBuffer` 구현은 오픈소스로 공개되었다. ## asm.js 이후의 발전 방향 - WebAssembly는 asm.js 코드를 바이너리 형식으로 표현해 JavaScript 파싱 시간을 크게 줄이는 것을 목표로 한다. - 당시 웹의 멀티스레딩은 Web Worker와 메시지 전달 방식에 의존했다. - Shared Typed Array가 도입되면 여러 실행 흐름이 메모리를 공유하는 진정한 공유 메모리 기반 멀티스레딩이 가능해질 것으로 전망했다. ## 자체 렌더링 엔진 - 브라우저의 그래픽 기능을 그대로 사용하는 대신, 콘텐츠를 빠르고 플랫폼 간 일관되게 표시하기 위해 자체 렌더링 엔진을 구현했다. - 이는 브라우저마다 다른 그래픽 구현과 동작 차이를 통제하고, 전문 디자인 도구에 필요한 고성능 렌더링을 직접 최적화하기 위한 선택이다. - 제공된 글 내용은 자체 렌더링 엔진의 필요성을 설명하는 부분에서 끝나므로, 구체적인 렌더링 구조와 최적화 기법은 확인할 수 없다. 브라우저 기반 고성능 그래픽 애플리케이션을 만들 때는 DOM과 일반 JavaScript API만으로 해결하려 하기보다, C++/WebAssembly 계열의 실행 모델과 명시적인 메모리 관리, 자체 렌더링 계층을 고려하는 것이 효과적이다. 특히 60fps가 중요한 편집 도구라면 가비지 컬렉션과 브라우저별 렌더링 차이를 구조적으로 줄이는 설계가 중요하다.