"네트워크가 정확히 한 번 배달하게 만들 순 없어. 두 번 도착한 같은 배달이 한 번의 뜻만 갖게 만들 순 있어."
네트워크에 관한 불편한 진실
튼튼한 클라이언트라면 언젠가는 마주치는 사실이 있어. 불안한 네트워크 위에서는 정확히 한 번 배달을 얻어낼 수가 없다는 거. 더 열심히 한다고 되는 문제가 아냐. 고전적인 함정이 이래. 요청이 백엔드에 닿고, 백엔드가 처리하고, 그다음 응답이 돌아오다가 떨어져. 폰 입장에선 요청이 실패한 거야. 근데 아니지. 확인만 못 받은 거고. 여기서 클라이언트가 재시도하면 백엔드는 같은 요청을 두 번째로 보게 돼. 배달은 적어도 한 번이야. 메시지가 0번 올 수도, 한 번 올 수도, 여러 번 올 수도 있는데 클라이언트는 바깥에서 그 차이를 알아낼 방법이 없어.
보장을 한 층 위로 올려
배달을 못 고치니까 의미를 고치는 거야. 목표는 정확히 한 번 배달이 아냐. 그건 불가능하고. 정확히 한 번 의도야. 요청이 물리적으로 몇 번을 도착하든 효과는 한 번만 나게 하는 거. 그게 멱등성이 사주는 거고. 몇 번을 적용해도 한 번 적용한 거랑 결과가 같은 연산 말이야. 재시도가 안전해지는 건 반복이 안 일어난다고 보장해서가 아니라, 반복이 무해해서야.
- 배달 층. 불안하고, 적어도 한 번이고, 네 손 밖이야. 그냥 받아들여.
- 의도 층. 믿을 만하고, 정확히 한 번이고, dedupe 키만 있으면 온전히 네 손안이야. 여길 만들어.
이 트랙 전체가 이 생각의 전환에 걸려 있어. 선 위에서 중복을 막으려고 하지 마. 중복이 상관없어지게 만드는 쪽으로 가.
왜 이게 마음 놓고 재시도할 자유를 주나
중복이 무해해지면 재시도가 안 무서워져. 재연결될 때 다시 보내고, 앱 켤 때 다시 보내고, 사용자가 탭할 때 다시 보내. 신뢰성이 필요하다는 만큼 자주. 의도 층이 그 도착들을 전부 효과 하나로 접어 주니까. 재시도를 무서워하는 클라이언트는 결국 덜 해주게 돼. 안전하자고 그냥 버리거든. 멱등한 의도를 가진 클라이언트는 넉넉히 재시도하면서도 두 번 행동하는 법이 없고. 다음 레슨들이 이걸 진짜로 만들어 줄 dedupe 키를 만들어. device turn ID 야.