CASE STUDY
한눈에 보는 변화
2022년 COMS에 Lucy XSS Filter를 처음 적용하고 허용 목록에서 빠진 구간을 보완했습니다. 2024~2025년에는 검사 범위를 GET·JSON·Multipart까지 넓혔습니다. 공통 Request 처리 방식을 바꾸자 Forward 파라미터, 파일 Part, 메뉴 링크가 서로 다르게 영향을 받아 요청 유형별 처리와 기존 업무 기능을 함께 다시 확인했습니다.
기존 XSS 필터가 일부 POST 요청 중심으로 적용되어 요청 방식에 따라 입력값 검증 수준이 달랐습니다. 적용 범위를 확대하자 Forward 파라미터 누락, 파일 업로드, 메뉴 렌더링과 다운로드 링크 등 정상 기능에 부작용이 발생했습니다.
직접 담당한 범위
- 기존 필터·Wrapper·Forward 요청 흐름 분석
- GET 필터링 확대와 요청 유형별 처리 구조 설계·구현
- 예외 URL·허용 태그 속성 정리, 본사·일본·유럽법인 적용과 검증
- 싱가포르 COMS의 확인된 보안 개선 4건 개발·테스트·운영 배포
| 구분 | 변경 전 | 변경 후 | 확인된 변화 |
|---|---|---|---|
| 검증 범위 | 일부 POST 요청 중심으로 Lucy XSS Filter 적용 | GET·일반 POST·JSON·Multipart별 전용 처리 경로 구성 | 4개 요청 흐름의 입력 검증 범위 보완 |
| Forward 파라미터 | Wrapper 내부 Map만 조회해 Forward에서 추가된 필수 값 누락 | 원본 Request 대체 조회와 동일한 필터링 규칙 적용 | 기존 Forward 호출 방식 유지 |
| Body·파일 처리 | JSON Body 재사용과 Multipart 일반 파라미터의 검사 구간이 불명확 | Body 캐시와 파일 Part·일반 Form Data 처리를 분리 | Controller 재사용과 파일 업로드 흐름 보존 |
| 적용 범위 | 본사 중심으로 적용한 요청 방어 방식 | 법인별 URL·외부 연계 차이를 검증해 일본·유럽 COMS로 확산 | 본사+2개 해외법인 운영 반영 |
| 싱가포르 후속 보안 개선 | XSS·비밀번호·마스킹·민감정보 접근 경로별 보완 필요 | 확인된 4개 항목의 검증·노출 제어·재인증 로직 개선 | 개선·테스트·운영 배포 완료 |
EVIDENCE CHAIN
문제를 좁힌 과정
- 01 · 요청 방식 분리
요청 데이터가 저장된 위치에 따라 처리 방식을 나눴습니다
GET·일반 POST는 Parameter Map, JSON은 Request Body, Multipart는 파일 Part와 Form Data를 사용합니다. Forward는 새 요청을 만들지 않고 기존 Request를 이어서 사용하므로, 같은 Filter를 통과해도 데이터 생명주기가 같지 않았습니다.
판단모든 요청을 하나의 Wrapper로 감싸기보다 Method와 Content-Type에 따라 읽고 검사하는 방식을 나눠야 했습니다.
- 02 · 장애 재현
Forward에서만 필수 파라미터가 사라지는 조건을 재현했습니다
JSP가 필수 값을 추가해 Controller로 Forward하는 경로를 추적했습니다. 최초 파라미터는 Wrapper 내부 Map에 있었지만, Forward에서 추가된 값은 Servlet Container가 원본 Request에 반영하고 있었습니다.
판단값은 전달됐지만 Override된 getParameter가 원본 Request에 추가된 새 값을 읽지 못했습니다.
- 03 · 우회 방지
원본 값을 다시 읽는 경로가 검사를 우회하지 않는지 확인했습니다
Wrapper에 값이 없을 때 원본 Request를 조회하도록 보완하되, 원본에서 찾은 값에도 같은 필터링 규칙을 다시 적용했습니다. getParameterValues·getParameterMap·getParameterNames도 서로 다른 결과를 내지 않는지 함께 확인했습니다.
판단기존 Forward 동작을 복구하면서도 원본 Request 조회가 XSS 검사를 건너뛰는 경로가 되지 않아야 했습니다.
- 04 · 부작용 분리
메뉴·다운로드와 파일 업로드 문제를 각각 재현했습니다
href 제한으로 DB 기반 메뉴와 다운로드 링크가 사라진 문제는 최소 예외 URL로 분리했습니다. Multipart는 파일 스트림을 유지하고 일반 Form Data만 검증했으며, JSON은 Body를 캐시해 이후 Controller가 다시 읽을 수 있게 했습니다.
판단예외 URL·Body·파일은 처리 방식이 서로 다르므로 각각의 정상 동작 조건을 별도로 정의해야 했습니다.
- 05 · 확산 검증
법인별 메뉴·업로드·연계 기능을 다시 확인했습니다
본사 검증 후 일본·유럽법인의 메뉴, 업로드, 다운로드, 외부 연계 URL 차이를 별도 회귀 범위로 확인했습니다. 공통 방어 방식은 유지하되 법인별 예외는 확인된 최소 범위만 반영했습니다.
판단공통 보안 정책을 다른 법인에 적용할 때는 설정만 복사하지 않고 법인별 메뉴·업로드·연계 기능을 다시 확인해야 했습니다.
DECISION LOG
검토한 대안과 선택 근거
Forward를 Redirect로 전환
브라우저가 새 요청을 만들면서 URL·파라미터 전달·화면 이동이 함께 바뀌어 기존 기능의 회귀 범위가 커지기 때문입니다.
모든 요청에 단일 Wrapper 적용
Parameter Map·JSON Body·Multipart Part의 읽기 방식이 달라 Body 소진과 파일 누락 가능성을 만들기 때문입니다.
문제가 난 경로를 넓게 예외 처리
예외 URL은 공통 Filter를 거치지 않으므로 메뉴·다운로드처럼 실제 사용이 확인된 최소 범위로 제한했습니다.
요청 유형별 Wrapper와 최소 예외
각 데이터 형식의 읽기 방식을 유지하면서 차단 규칙과 기존 기능을 함께 검증할 수 있었습니다.
IMPLEMENTATION
설계와 구현
GET·Forward 파라미터
- HttpServletRequestNormalWrapper에서 정제된 Parameter Map 제공
- Forward 이후 추가된 값은 원본 Request에서 다시 찾되 동일한 필터 재적용
- getParameter 계열 메서드가 일관된 값을 반환하도록 전달 경로 보완
JSON Body
- BodyReaderWrapper로 Filter 이후에도 Controller가 Body를 다시 읽을 수 있게 캐시
- JSONObject·JSONArray의 중첩 값을 재귀적으로 탐색해 문자열 값 필터링
- 요청 검사 뒤에도 JSON 역직렬화가 같은 Body를 읽을 수 있도록 처리
Multipart 업로드
- MultipartWrapper에서 파일 Part와 일반 Form Data를 분리
- 파일 스트림·메타데이터는 유지하고 일반 파라미터에만 XSS 규칙 적용
- 기존 Controller가 기대하는 Multipart 요청 타입과 파일 조회 흐름 보존
예외·법인 확산
- 메뉴 렌더링·가이드·결과 다운로드에 필요한 URL과 태그 속성의 영향도 확인
- 예외 URL은 실제 사용이 확인된 최소 범위로 설정하고 별도 회귀 대상으로 관리
- 본사 방어 구조와 추가 차단 정책을 일본·유럽법인 COMS 환경에 맞춰 반영
싱가포르 COMS 후속 개선
- 저장 프라이머 검색 입력에 Lucy XSS 검증 적용
- 회원정보 변경 시 비밀번호 강도 검증 보완
- 비밀번호 재설정의 마스킹 정보 노출 범위 축소
- 민감정보 조회 전 비밀번호 재인증 적용
VERIFICATION
테스트 매트릭스
| 검증 영역 | 검증 방법 | 완료 기준 |
|---|---|---|
| 차단 동작 | GET·POST·JSON·Multipart별 허용 입력과 공격 입력 실행 | 정상 값은 유지되고 차단 대상은 요청 유형과 관계없이 필터링 |
| Forward 파라미터 | Forward 전후 기존 값과 새로 추가된 필수 파라미터 비교 | Controller에서 필요한 값 유지 및 원본에서 다시 읽은 값도 동일 규칙으로 검증 |
| Body·파일 | 중첩 JSON과 일반 파라미터를 포함한 파일 업로드 수행 | Body 재사용·파일 조회 정상 및 문자열 입력 필터링 |
| 업무 회귀 | 조회·등록·수정·메뉴·가이드·결과 다운로드 시나리오 실행 | 보안 적용 전과 동일한 정상 업무 흐름 유지 |
| 해외법인 | 일본·유럽의 법인별 메뉴·업로드·외부 연계 경로 점검 | 공통 방어 정책과 법인별 필수 예외가 함께 정상 동작 |
| 싱가포르 후속 개선 | XSS·비밀번호·마스킹·재인증 4개 경로의 정상·차단 조건 확인 | 기존 기능을 유지하면서 확인된 보안 보완 항목을 운영 환경에 반영 |
OPERATION
운영 반영과 후속 안정화
Forward 필수 파라미터 누락
- 분리한 원인
- Wrapper 내부 Map과 원본 Request에 값이 저장되는 시점 차이
- 대응
- 원본 Request 대체 조회와 재필터링으로 기존 호출 방식 복구
메뉴·다운로드 링크 제거
- 분리한 원인
- href 제한이 DB 기반 정상 링크에도 동일하게 적용
- 대응
- 사용 경로를 확인한 최소 예외 URL·속성만 분리하고 회귀 테스트
업로드 파라미터 미검증
- 분리한 원인
- Multipart의 파일 Part와 일반 Form Data를 기존 Filter가 분리하지 못함
- 대응
- 파일은 보존하고 일반 파라미터만 검증하는 전용 Wrapper 적용
- 요청 방식에 따라 달랐던 XSS 검증 범위를 일관되게 개선
- 보안 적용 확대로 발생한 기존 기능의 부작용 해결
- 본사에서 확인한 방어 방식을 일본·유럽법인 시스템에 확산 적용
- 싱가포르 COMS의 확인된 보안 개선 4건을 테스트하고 운영에 반영
TAKEAWAYS
이 사례에서 드러난 역량
- 공통 XSS Filter는 문자열뿐 아니라 이후 코드가 Request를 읽는 방식까지 바꿀 수 있으므로 인프라 코드로 다뤄야 합니다.
- Forward 문제는 값의 존재 여부보다 Wrapper와 원본 Request 중 어느 경로를 읽는지 추적해야 원인을 찾을 수 있습니다.
- 보안 예외를 추가하면 해당 요청이 공통 필터를 거치지 않으므로 적용 범위를 최소화하고 별도로 검증해야 합니다.
- 입력 필터는 보완 수단이므로, 실제 출력 지점에서는 HTML 본문·속성·JavaScript 등 문맥에 맞는 인코딩이 별도로 필요합니다.