Files
llm-wiki/raw/interviews/idempotency-rate-limit-design-tradeoffs-2026-06-09.md

2.6 KiB

title, source_type, status, related_branches, related_projects, tags, created
title source_type status related_branches related_projects tags created
interview / idempotency-rate-limit-design-tradeoffs-2026-06-09 interview-prep raw
feature-rate-limit-idempotency-contract
ca-skeleton
interview
ca-skeleton
idempotency
rate-limit
concurrency
2026-06-09

interview: 멱등성 / rate-limit 설계 트레이드오프

Layer: raw/interviews/ — feature-rate-limit-idempotency-contract 구현에서 나올 수 있는 질문.

Parent / 부모

예상 질문 / Q&A

  • Q. 동시에 같은 idempotency key가 오면? A. DB unique 제약((tenant, principal, idempotency_key, use_case_name))을 동시성 중재자로 사용. 첫 요청이 IN_FLIGHT row 선점(insert), 후속은 insert 실패 → read. read가 IN_FLIGHT면 200ms까지 poll 후 초과 시 409 IDEMPOTENT_IN_FLIGHT(retryable=false, client는 polling).

  • Q. 200ms wait는 표준인가? A. 아니다. IETF draft/Toss는 즉시 409 SHOULD. 200ms는 client retry 친화적 "변형"이고 thread를 잡는 비용이 있어 부하 테스트로 튜닝 대상. 면접에서 "표준 따름"으로 말하면 안 됨.

  • Q. 같은 key + 다른 body는? A. body SHA-256 fingerprint 비교 → 다르면 422 IDEMPOTENT_REQUEST_MISMATCH(IETF 422 권고 정합). 단 canonicalization(키 순서/공백) 미적용 시 false mismatch 위험 — 본 구현은 직렬화된 payload 기준.

  • Q. single-tenant인데 unique 제약이 동작하나? (tenant NULL) A. PostgreSQL은 NULL을 distinct로 취급 → NULL tenant면 dedup 실패. 그래서 tenant 컬럼을 NOT NULL DEFAULT ''로 두고 매퍼가 null↔'' 변환.

  • Q. 만료(TTL) 처리? A. 읽기에서 만료 row를 absent 취급 + tryBegin에서 만료 row reclaim(delete 후 insert) + 주기적 reaper(@Scheduled bulk delete) 3중. 읽기 필터와 쓰기 선점이 같은 만료 기준을 공유해야 "유령 충돌"이 없음.

  • Q. rate-limit 알고리즘은? A. single-node in-process fixed-window counter(ConcurrentHashMap.compute + AtomicInteger). 장점: X-RateLimit-Reset이 창 종료로 정확. 단점: 창 경계 burst 허용, 멀티 인스턴스면 N배(distributed limiter는 out of scope).

  • Q. 왜 filter가 아니라 interceptor? A. unauth key가 IP + route template을 요구하는데 servlet filter는 handler mapping 전이라 template을 모름. interceptor는 BEST_MATCHING_PATTERN_ATTRIBUTE/v1/worklogs/{id}를 얻음.

관련