
“락을 잘 잡아라”가 아니라, 락을 못 잡으면 못 지나가게 만들기
로그를 처음 봤을 때는 평범했다. 응답이 느렸다. 가끔 멈췄다.
그런데 이상한 건 ‘에러’가 아니라 ‘조용함’이었다. CPU는 치솟지 않았고, 예외도 안 터졌다. 그냥… 일을 안 했다.
나는 습관적으로 네트워크를 의심했다가, 다음엔 DB를 의심했다가, 결국 스트림 쪽으로 왔다.
Reader를 열어놓고, 닫지 않은 채로, 또 열었다.
그 순간부터는 디버깅이 아니라 수사였다. 누가 언제 락을 잡았고, 누가 안 놨고, 왜 다음 단계가 영원히 기다리는지.
스크린샷 하나로 설명이 안 됐다. “여기서 잠겨요”라고 말해도, 재현이 안 되면 끝이다.
결국 내가 한 건 ‘조심하자’가 아니라 ‘못 하게 하자’였다.
Cloudflare가 Web Streams API를 더 나은 형태로 만들자고 주장하는 이유를, 그날은 몸으로 이해했다. 제대로 쓰는 방법이 어려우면, 사람은 언젠가 실수한다. 실수했을 때는 조용히 망가진다. (참고자료)
락을 못 잡으면, 지나가면 안 된다
Streams를 쓰면서 제일 불쾌한 순간은 “이제부터는 네가 잘해야 돼”라는 암묵적인 책임이 생길 때다.
락을 잘 잡고, 잘 풀고, 리더를 잘 닫고, 실수하지 말 것.
그런데 실무에서 이런 메시지는 사실상 실패다. 실수는 반드시 난다.
요즘 에이전트 도입도 똑같다. “락을 잘 잡아라”가 아니라, 락을 못 잡으면 아예 못 지나가게 만들어야 한다.
여기서 ‘락’은 기술 디테일이 아니다. 팀에서 자주 깨지는 경계선이다.
- 범위를 넘는 수정
- 금지된 작업
- 끝없이 반복되는 실패
- 근거가 없는 결론
이걸 “조심해서 지켜주세요”로 두면, 언젠가 안 지켜진다. 그래서 UI가 필요하다. 못 지나가게 강제하는 UI.
“업무 UI 1장” 스펙(필드 6개)
내가 요즘 자주 쓰는 방식은, ‘한 장짜리 입력’부터 강제하는 거다. 문장으로 말하면 다들 빠져나간다. 필드로 만들면 빠져나갈 구멍이 줄어든다.
아래 6개가 채워지지 않으면, 다음 단계로 못 가게 만든다.
내가 말하는 UI는 결국 PR 템플릿/체크리스트다. 이 6개가 비면 머지 버튼이 아니라 “질문”만 남게 만든다.
목표
- 이 작업이 끝났다고 말할 수 있는 한 문장.
- 예:
CI green + “왜 바꿨는지” 릴리스 노트 1줄
범위
- 수정 가능한 경로/리소스의 경계.
- 예:
수정 가능: /docs, /configs (그 외는 제안만)
금지
- 건드리면 즉시 중단되는 구역.
- 예:
금지: /auth, /billing, /payments
중단조건
- 실패를 ‘습관’으로 만들기 전에 멈추는 숫자.
- 예:
동일 실패 3회면 중단 + 사람 호출
evidence_ref
- 근거는 여러 개 링크가 아니라 하나로 고정.
- 예:
TICKET-2319(PR은 그 티켓에 매단다)
결과물 위치
- 결과가 어디로 가야 하는지.
- 예:
PR 본문 + 변경 요약 3줄
이걸 넣으면 인터페이스가 거칠어 보일 수 있다. 그래도 좋다. 거칠어도, ‘아무 일도 안 일어나는 듯한 장애’보단 낫다.
이걸 UI로 올릴지 판단하는 3개
나도 모든 걸 UI로 올리진 않는다. 올리기 전에 딱 세 가지만 본다.
되돌리기 시간
- 30분(예시 임계값) 안에 원복이 가능하면 UI로 올려도 된다. 아니면 ‘제안’까지만.
중단 조건 숫자
- “상황 봐서”는 금지. 숫자가 없으면 UI로 올리면 안 된다.
evidence_ref 고정
- 근거가 퍼지면(슬랙, 메일, 문서, PR…) 다시 그날 밤이 온다. 한 군데로 고정할 수 있어야 한다.
이 6개 필드 중 하나라도 비면, 에이전트는 “수정”이 아니라 “질문”만 하게 한다.
참고자료
- Cloudflare Blog — We deserve a better streams API for JavaScript
- https://blog.cloudflare.com/a-better-web-streams-api/
실전 적용
“락을 잘 잡자”는 말은 늘 맞는데, 그래서 늘 실패한다. 잘 잡는 건 개인 기술이고, 제품/팀은 개인 기술에 기대면 늦게 무너진다. 실전에서는 락 자체보다 ‘락이 필요한 상황’이 들어왔을 때 어떻게 막고, 어떻게 질문하고, 어떻게 사람에게 넘길지의 흐름을 먼저 만든다. 아래는 내가 배포/자동화/에이전트 작업을 붙일 때 실제로 손보는 부분들이다. 완벽한 규칙집이 아니라, 실수의 비용을 줄이는 장치들.
- “실행” 버튼보다 “요청” 버튼을 먼저 둔다: 실행은 PR/티켓으로만 나오게 하고, UI에서는 요청을 만든다(실행은 승인 뒤에만).
- 입력 필드가 비면 결과를 내지 않게 한다: 목표/범위/금지/중단조건 같은 최소 입력이 없으면, 수정 대신 질문만 하게 만든다.
- 권한을 역할로 나눈다: 제안하는 사람, 승인하는 사람, 실제로 누르는 사람을 분리하면 “누가 눌렀지?”가 줄어든다.
- 재시도는 자동이 아니라 이벤트로 만든다: 같은 실패가 반복되면 조용히 재시도하지 말고, 바로 중단하고 사람에게 던진다.
- 되돌리기 경로를 UI에 같이 놓는다: 리버트/롤백이 어디에 있는지 모르면, 사람은 ‘안 누르는 선택’을 한다.
- 락 실패의 “다음 행동”을 고정한다: 실패 메시지에 원인 설명보다, 무엇을 채워야 다시 진행되는지(필드/승인/티켓)를 적는다.
흔한 함정은 두 가지다. 둘 다 “바쁘니까”로 정당화되기 쉬운데, 결국 그 바쁨이 더 커진다.
- 함정 1) 불완전한 입력으로도 일단 진행시키기: 그 순간부터 팀은 결과가 아니라 ‘누가 뭘 의도했는지’ 복원하는 데 시간을 쓴다.
- 함정 2) 락 해제를 사람 기억력에 맡기기: 한 번 놓치면 조용히 멈추고, 조용히 멈추면 누군가는 두 번 눌러서 더 크게 만든다.
실전 적용
이 글을 읽고 나서 바로 할 수 있는 건 “더 조심하자”가 아니라, 팀이 매번 같은 실수를 반복하기 어렵게 만드는 작은 장치들을 박는 일이다. 특히 신규 합류자나 야간 온콜처럼 맥락이 끊긴 사람이 들어오는 순간에 터지는 사고를 줄이려면, ‘잘하면 통과’가 아니라 ‘빠뜨리면 멈춤’이 작동해야 한다. 아래는 내가 실제로 리포지토리와 배포 파이프라인에 붙이는 메모들이다. 문서로는 예쁘지 않지만, 다음 배포에서 시간을 아껴준다.
- PR 템플릿에 “실행 대신 질문” 게이트를 둔다: 목표/범위/금지/중단조건이 비면 자동으로 리뷰 요청만 남기고, 머지 관련 체크는 비활성으로 두기.
- 중단조건을 코드로 고정한다: 같은 실패가 N번 반복되면 재시도 루프에 들어가지 말고 즉시 중단+사람 호출(슬랙/이슈 생성)로 넘기기.
- evidence_ref는 자동 생성/연결로만 남긴다: 사용자가 ‘아무거나’ 붙일 수 있게 두지 말고, 티켓 하나가 없으면 실행 단계로 못 가게 하기.
- 권한을 “제안/승인/실행”으로 쪼갠다: 한 사람이 다 할 수 있으면 결국 누구도 책임을 못 진다.
- 되돌리기 경로를 배포 UI에 같이 보여준다: 실패했을 때 문서 찾지 말고, 같은 화면에서 롤백/리버트 버튼 또는 명령을 바로 제시하기.
- 중복 클릭/중복 실행을 가정한다: 동일 요청이 두 번 들어와도 두 번째는 ‘이미 처리됨’으로 끝나게(멱등) 만들기.
흔한 함정은 두 가지다. 둘 다 “빨리 가자”는 마음에서 시작하지만, 결과는 반대로 온다.
- 함정 1) 입력이 비어도 일단 실행시키기: 다음날 남는 건 결과물이 아니라 “누가 뭘 의도했지?”를 복원하는 회의다.
- 함정 2) 실패를 조용히 삼키는 재시도: 사용자(또는 팀)가 더 누르고 더 돌려서, 원인도 비용도 같이 커진다.
댓글
댓글 쓰기