# 지루한 코드로 10억 웹 요청을 처리한 경험

> Clean Markdown view of GeekNews topic #21903. Use the original source for factual precision when an external source URL is present.

## Metadata

- GeekNews HTML: [https://news.hada.io/topic?id=21903](https://news.hada.io/topic?id=21903)
- GeekNews Markdown: [https://news.hada.io/topic/21903.md](https://news.hada.io/topic/21903.md)
- Type: news
- Author: [neo](https://news.hada.io/@neo)
- Published: 2025-07-10T09:51:01+09:00
- Updated: 2025-07-10T09:51:01+09:00
- Original source: [notes.billmill.org](https://notes.billmill.org/blog/2024/06/Serving_a_billion_web_requests_with_boring_code.html)
- Points: 46
- Comments: 18

## Summary

**Postgres, golang, React** 등 단순하고 검증된 기술만으로 **미국 메디케어 보험 비교 시스템**의 **10억 건 웹 요청**을 안정적으로 처리하고, 평균 10ms 이하 응답 속도와 낮은 장애율을 달성한 경험을 소개합니다. 핵심 구조는 3개 대형 모듈과 **gRPC**로 분리하고, ETL·로깅·문서화 등 운영 요소도 반복 가능하고 단순하게 구축해 팀 전체가 쉽게 유지보수할 수 있도록 했습니다. 엄격한 하위 호환성, 꾸준한 품질 관리와 강한 팀워크로 대규모 프로젝트에서 높은 안정성을 이룬 실전 사례로, **단순함과 반복 가능한 운영이 대규모 서비스 성공의 핵심 무기임을 보여줍니다.**

## Topic Body

- **미국 메디케어 건강보험 플랜 비교 시스템**을 재구축하며, **검증된 기술(Postgres, golang, React 등)** 로만 구성된 단순한 구조로 **10억 건 이상의 웹 요청**을 안정적으로 처리한 경험을 공유함  
- **단순함과 안정성**을 목표로 아키텍처를 설계해, **평균 10ms 이하 응답 속도**와 **아주 낮은 장애율**을 달성함  
- **혁신(innovation token)** 은 핵심적인 구조 분리(3개 대형 모듈, gRPC 통신)에만 최소한으로 적용하고, 그 외에는 모두 지루하지만 신뢰할 수 있는 방법론을 선택함  
- **DB 스키마 관리, ETL 파이프라인, 테스트, 로깅, 문서화, CLI 도구**까지 모든 운영 요소를 반복 가능하고 단순한 방식으로 구축해 **팀 전체가 쉽게 이해·유지보수할 수 있는 시스템**을 완성함  
- **지속적 품질관리와 강한 팀워크**가 대규모 정부 프로젝트에서도 통한다는 사례를 생생히 보여줌  
  
---  
  
### Serving a billion web requests with boring code  
  
#### High level  
  
- **2년 반**에 걸쳐 미국 정부의 메디케어 플랜 비교·구매 웹사이트를 리드 개발함  
- **일 평균 500만 API 요청**을 처리, 평균 응답 속도는 10ms 미만, 95% 요청은 100ms 이하로 유지  
- **장애 발생률이 매우 낮아** 실제 엔지니어가 새벽에 호출된 사례는 한 손에 꼽을 정도  
- **Postgres, golang, React** 등 누구나 이해할 수 있는 검증된 기술로만 구성해, 꾸준히 안정적인 시스템을 구축함  
  
#### Boring über alles  
  
- 최우선 원칙은 **'지루하고 검증된 기술'** 만을 우선하는 것(** Choose Boring Technology**)  
- 혁신 시도는 꼭 필요한 곳에서만 **innovation token**을 아껴서 사용  
- 복잡하고 화려한 솔루션보다 **안정적이고 명확한 기술과 프로세스**를 선호  
  
#### The boring bits  
  
- **Postgres**: 데이터 저장의 핵심, 신뢰성과 확장성을 모두 만족. 복잡한 검색(페이시티드 검색 등)도 Postgres로 해결  
- **golang**: 빌드와 배포가 빠르고, 바이너리 산출물이 명확함. 에러 핸들링이 직관적이고, 새로운 팀원도 쉽게 적응 가능  
- **React**: SPA 프레임워크 중 가장 검증되어 있고, 팀원들이 이미 익숙했음. 접근성과 다양한 기기 지원도 중요한 고려 요소였음  
    - 장기적으로는 번들 크기와 속도 저하 이슈가 발생했지만, 당시 상황에서는 시간 내에 결과를 내기 위한 최적의 선택이었음  
  
#### The innovation tokens  
  
- **Modular backend**: 전체 백엔드를 마이크로서비스도, 모놀리식도 아닌 **3개의 대형 모듈**(druginfo, planinfo, beneinfo)로 구성  
    - 각 모듈은 별도의 Postgres DB를 사용하고, 데이터 공유는 오직 gRPC를 통해서만 이뤄짐  
    - `druginfo`: 약국, 보험, 포장 등 조합이 기하급수적으로 늘어나는 약가 정보를 매우 정교하게 인덱싱하고, 복잡한 사전처리와 성능 최적화가 필요  
    - `planinfo`: 매일 새로운 CMS 데이터를 수신해, DB 전체를 새로 만들어 사용함(불변성 유지)  
    - `beneinfo`: 실제 가입자 정보를 보관하는 유일한 부분으로, 민감한 PII(개인정보)는 최소한만 저장. 데이터 유출 리스크 최소화를 위해 설계와 운영에 신경 씀  
- **gRPC**: 모듈간 통신 인터페이스를 코드로 명확히 정의할 수 있는 장점. 자동화 도구와 연동성이 뛰어남  
    - 단, 빌드·툴링·디버깅은 복잡하고, JSON API 대비 직관성이 떨어지는 단점도 경험  
    - grpc-gateway를 통해 웹클라이언트 지원 및 대량 트래픽을 무리 없이 처리함  
  
#### Strict backwards compatibility  
  
- **API 및 데이터베이스의 하위 호환성 유지**를 엄격하게 지킴  
    - 공개 API의 필드는 절대 삭제하지 않고, 보안 문제가 있지 않는 한 평생 유지  
    - DB 컬럼도 추가는 자유롭지만 삭제는 여러 단계 검증(참조 제거→몇 주 대기→실제 삭제) 절차를 거침  
- 이 규율이 높은 변화 속도와 안정적인 배포·운영의 핵심 기반이 됨  
  
#### Faceted search  
  
- **ElasticSearch 대신 Postgres만으로 페이시티드 검색 구현**  
    - well-indexed plan 테이블에 조건을 조합하는 250줄 함수 하나로 모든 검색 로직을 처리  
    - 비즈니스 요구에 집중, 불필요한 복잡성 없이 단순하게 해결함  
  
#### Database  
- ### creation  
  - DB 스키마를 숫자가 붙은 .sql 파일로 관리, 순서대로 로딩하여 신뢰성 보장  
  - `planinfo`/`beneinfo` DB는 매일 재생성, 마이그레이션 필요 없음. 버전 불일치 등 설정 오류 시 앱 자체를 아예 시작하지 않도록 설계  
- ### ETL  
  - 데이터 소스별 셸 스크립트로 S3에 적재 → cron으로 EC2 인스턴스가 최신 ETL 코드/데이터 가져와 신규 RDS DB 생성  
  - Postgres의 **COPY 구문**을 적극 활용, INSERT 대신 대량 데이터 적재를 효율적으로 처리  
  - 매일 2~4시간이면 수억 행 데이터를 새 DB로 전환 가능  
- ### models  
  - [xo](https://github.com/xo/xo) 라이브러리로 DB 모델 자동 생성, 커스텀 템플릿으로 팀에 맞는 코드 생성  
- ### testing  
  - **가장 큰 실수**는 sqlmock을 활용한 테스트를 과하게 만들어 데이터가 자주 바뀌는 상황에서 유지보수가 매우 번거로움  
  - 실제 불변 DB라면 실DB에 대한 테스트가 더 효율적이었을 것  
- ### Local database for development  
  - 각 테이블의 부분 데이터를 자동 생성하는 스크립트로, 개발자별로 작은 로컬 DB로 실제 데이터 기반 테스트와 개발 가능  
  - DB가 커지기 전에 이런 도구를 마련하면 전체 팀 개발 효율이 극대화됨  
  
#### Miscellaneous tooling  
  
- 각종 운영·관측 자동화를 위해 CLI 도구를 셸 스크립트로 구현, 모든 유틸리티 기능을 하나로 모아 관리  
- splunk 로그를 Slack 명령어로 바로 그래프로 시각화하는 등 현장 중심의 도구를 적극 개발·활용  
  
#### Logging  
  
- 요청 진입 시점에 request id를 생성, 그 id가 모든 로그 컨텍스트에 붙어서 어디서든 추적 가능  
- [zerolog](https://pkg.go.dev/github.com/rs/zerolog)로 안전하고 체계적인 로깅 설계  
- 시스템 입구·퇴출, 예외 상황 등 중요 시점마다 필수 로그 남기기  
  
#### Documentation  
  
- GitHub markdown 문서를 [sphinx-book-theme](https://sphinx-book-theme.readthedocs.io/en/stable/tutorials/get-started.html)으로 변환해 위키북으로 운영  
- 팀원 모두가 적극적으로 문서화에 기여, 한 곳에서 모든 시스템 문서를 찾을 수 있도록 함  
- 뛰어난 문서화 문화가 팀의 성장과 유지보수, 신입 온보딩 효율을 크게 높임  
  
#### Runtime integrations  
  
- 클라이언트의 성능 저하 요청(분석 스크립트 삽입 등)은 최대한 설득해 최소화  
- 쿼리도 브라우저 런타임이 아닌 빌드타임 처리로 전환해, 서비스 성능을 유지  
- 실제론 고객 요청을 모두 막지는 못해, 일부는 성능 저하로 이어졌음  
  
#### And more  
  
- 기술 이외에도 **긍정적이고 협력적인 팀 분위기**와 강한 동기 부여가 대규모 시스템 성공의 진짜 원동력임을 강조  
- 사소하지만 중요한 실무적 선택과 꾸준한 품질 관리의 힘을 실감한 사례였음

## Comments



### Comment 42055

- Author: bugprone
- Created: 2025-08-03T14:15:33+09:00
- Points: 1

이 지루한 걸 2.5년이나?!

### Comment 41367

- Author: kimjj81
- Created: 2025-07-14T10:57:01+09:00
- Points: 2

Faceted Search 가 무엇인가 궁금해서 따라갔다 더 읽을만한게 있네요.  
  
https://www.cybertec-postgresql.com/en/faceting-large-result-sets/  
https://roaringbitmap.org/about/  
https://github.com/cybertec-postgresql/pgfaceting

### Comment 41329

- Author: choijaekyu
- Created: 2025-07-13T18:36:49+09:00
- Points: 1

"지루"에 대한 의견들이 재밌네요ㅎㅎ 다른 말로 바꾼다면 뭐가 좋을까요? 뻔한, 흔한?

### Comment 41324

- Author: aqqnucs
- Created: 2025-07-13T14:46:05+09:00
- Points: 1

boring을 지루하다고 번역한게 원래 의미를 너무 못살리네요. boringness는 go 디자인 철학 중 하나에요.

### Comment 41278

- Author: iolothebard
- Created: 2025-07-11T19:04:00+09:00
- Points: 1

지루~한 척…

### Comment 41275

- Author: sinbumu
- Created: 2025-07-11T17:57:37+09:00
- Points: 1

한국은 기승전 자바민국이라 낯설어 하네 ㅋ

### Comment 41204

- Author: ethanhur
- Created: 2025-07-10T16:12:51+09:00
- Points: 1

golang, React 전부 새 시대의 지루한(boring) 엔터프라이즈 코딩 언어라고 생각합니다.  
  
boring -> 지루한 으로 100% 맞게 번역되는 게 아니다보니 한국 독자들에게는 뉘앙스가 제대로 전달되지 않는 거 같아 보이네요.

### Comment 41195

- Author: white9s
- Created: 2025-07-10T14:06:24+09:00
- Points: 3

Postgres, golang, React이 지루한 세계에서 살고 싶네요

### Comment 41224

- Author: helio
- Created: 2025-07-11T04:26:45+09:00
- Points: 1
- Parent comment: 41195
- Depth: 1

맞아요 제목보고 무슨 농담인가 했네요

### Comment 41196

- Author: riki3
- Created: 2025-07-10T14:45:41+09:00
- Points: 2
- Parent comment: 41195
- Depth: 1

외국에선 그게 지루한 스택인 것 같습니다.  
실제로 go는 뭐 그냥 웹서버 만드는데 가장 쉬운 선택이고..  
  
뭐 rust fp쪽 언어 이런걸로 개발해야 지루하지 않다고 하는 것 같네요.

### Comment 41192

- Author: kandk
- Created: 2025-07-10T13:13:15+09:00
- Points: 2

너무 당연한 이야기들.. 너무 당연해서 놓치고 있는 중요한 사항들..

### Comment 41188

- Author: vwjdalsgkv
- Created: 2025-07-10T11:25:51+09:00
- Points: 1

이정도는 그렇게 지루해보이지만은 않은 스택으로 보이네요. 정말 지루하다면 java 1.8 이하버전이나 vb 정도는 나와야하지 않을까... 하는 불충한 생각이 듭니다

### Comment 41200

- Author: beoks
- Created: 2025-07-10T15:22:15+09:00
- Points: 2
- Parent comment: 41188
- Depth: 1

>The nice thing about boringness (so constrained) is that the capabilities of these things are well understood. But more importantly, their failure modes are well understood.   
  
원문에 boring 과 관련된 링크가 있는데, 내용을 보면 boring = 너무 익숙한이라는 의미인 것 같습니다.

### Comment 41201

- Author: beoks
- Created: 2025-07-10T15:33:54+09:00
- Points: 3
- Parent comment: 41200
- Depth: 2

experienced, verified, skillful 같은 더 적절한 단어가 있는데 굳이 boring 을 쓴건 어그로를 끌 저의가 있는것 같네요

### Comment 41198

- Author: cocofather
- Created: 2025-07-10T15:07:13+09:00
- Points: 2
- Parent comment: 41188
- Depth: 1

쓰기에 지루한게 아니고 너무 많이써서 지루한 국밥스택이라고 표현한것 아닐까요

### Comment 41194

- Author: dongjinahn
- Created: 2025-07-10T14:01:02+09:00
- Points: 1
- Parent comment: 41188
- Depth: 1

리눅스 커널 2.6.29정도...

### Comment 41191

- Author: kandk
- Created: 2025-07-10T13:12:55+09:00
- Points: 1
- Parent comment: 41188
- Depth: 1

gRPC 썼다는거 자체가.. ㅋㅋ

### Comment 41190

- Author: click
- Created: 2025-07-10T12:57:28+09:00
- Points: 1
- Parent comment: 41188
- Depth: 1

저도 golang이 지루하다니? 같은 생각부터 들었습니다  
classic asp 정도면 지루하다고 할 수 있을법한데 말이죠
