StrictFirewallHttpRequest request = getRequest();
// 문제: header() 호출 후 타입이 바뀜
var result = request.mutate()
.header("X-Custom", "value") // StrictFirewallBuilder → DefaultBuilder
.build();
솔직히 처음엔 이렇게 생각했다.
"어차피 마지막에
build()
를 쓰고 이걸 사용할텐데, 중간에 타입이 바뀌면 어때? 최종 결과물만 제대로 나오면 되지!"
그래서 이 이슈를 그냥 무시하려고 했다. 그런데...
제가 "별거 아니네"라고 넘어가려던 순간, 프로젝트 메인테이너가 이 문제를 수정하는 PR을 올렸다.
"어? 메인테이너가 이걸 중요하게 생각하네? 내가 뭘 놓치고 있는 거지?"
// StrictFirewallBuilder의 실제 구현
@Override
public Builder header(String name, String value) {
// 이 순간! 바로 여기서 보안 검사가 일어난다
if (containsMaliciousPattern(value)) {
throw new SecurityException("악의적인 패턴 감지!");
}
return super.header(name, value);
}
"아, header()
를 호출하는 그 순간에 보안 검사가 일어나는구나! build()
까지 기다리는 게 아니라!"
처음엔 build()
가 마법처럼 모든 보안을 적용해줄 거라 생각했습니다:
// 내 착각
.header("Evil", "../../etc/passwd") // 일단 넣고
.build(); // 여기서 보안 마법이 일어날 거야!
// 실제 build() 구현
public ServerHttpRequest build() {
// 그냥... 조립만 합니다
return new MutatedServerHttpRequest(this.headers, this.cookies);
}
"build()
는 레고 조립하듯이 지금까지 쌓인 조각들을 합치기만 하는구나. 추가 검증은 없어!"
// 다른 개발자가 이 코드를 볼 때
StrictFirewallHttpRequest request = getRequest();
var builder = request.mutate(); // "오, 보안 적용된 빌더구나!"
// 하지만 실제로는...
builder = builder.header("X", "Y"); // 이제 일반 빌더로 변신!
// 개발자는 여전히 보안 빌더라고 착각 중...
"타입은 단순한 라벨이 아니라 '이 객체가 뭘 할 수 있는지'에 대한 약속이구나!"
6개월 후 프로덕션에서 보안 이슈가 터졌을 때:
// 로그 분석
DEBUG: Initial type: StrictFirewallHttpRequest ✓
DEBUG: After mutate(): StrictFirewallBuilder ✓
DEBUG: After header(): DefaultBuilder ✗ // 여기가 문제!
DEBUG: Final result: MutatedServerHttpRequest ?
// 팀원들의 반응
"코드 보면 StrictFirewall 쓰고 있는데요?"
"로그도 처음엔 StrictFirewall이네요?"
"그럼 왜 보안 검사가 안 된 거지...?"
"타입 불일치는 '조용한 버그'를 만든다. 겉으로는 정상인데 실제론 다르게 동작하니까!"
// 해커가 이런 요청을 보낼 때
request.mutate()
.header("X-Include", "../../etc/passwd") // 파일 접근 시도
.header("X-Command", "; DROP TABLE users;") // SQL 인젝션
.build();
// StrictFirewallBuilder였다면 → 즉시 차단
// 일반 Builder로 바뀐 후 → 그대로 통과
깨달음: "작은 타입 변경이 실제 보안 구멍을 만들 수 있구나!"
처음엔 "뭐 이런 걸로..."라고 생각했던 이슈가, 결국 API 설계와 보안에 대한 중요한 통찰을 주었다.
StrictFirewallBuilder
라는 이름은 "나는 보안 검사를 한다"는 약속이다.
평소에 당연하게 여겨 생각하지 못했던 부분인데 매우 중요하겠네요... 앞으로 저도 조심히 접근해봐야겠습니다. 좋은 글 감사합니다.