개발 slecs

B2B 쿠폰 외부 연동 암호화 헤더 적용으로 버전 업그레이드

목차

B2B 쿠폰 외부 연동 버전을 v2.4.10에서 v2.5.0으로 올리면서 암호화 헤더 스펙을 맞춰 넣는 작업을 했다.

왜 이번 업그레이드가 필요했나

외부 쿠폰 제공사(이하 Zlgoon) 측에서 API 스펙 변경 공지가 왔다. v2.5.0부터 요청 헤더에 암호화 서명 값을 포함시키지 않으면 인증 오류를 내뱉도록 서버 정책이 바뀐 것. 기존 v2.4.x 방식은 일정 기간 병행 지원하다가 Deprecated될 예정이라, 어차피 해야 할 작업이었다.

이런 류의 "외부 API 버전업"은 항상 두 가지 관점에서 판단을 해야 한다.

  • 긴급도: 기존 버전이 언제 막히는지, 실 서비스에 영향이 언제부터 오는지
  • 변경 범위: 단순 파라미터 추가냐, 인증 흐름 전체가 바뀌는 수준이냐

이번 건은 헤더에 암호화 값을 얹는 형태라 "인증 흐름 레벨"의 변경이었다. 헤더 하나 추가처럼 보이지만, 서명 생성 로직·키 관리·에러 코드 대응까지 묶여 있어서 생각보다 손댈 파일이 여럿이었음.

변경 범위 정리

파일/영역 변경 내용
CouponProviderFactory Provider 생성 시 v2.5.0 암호화 헤더 빌드 로직 분기
쿠폰 외부 Provider 내부 클래스 헤더 생성·서명 로직 적용, 기존 v2.4.x 호출 흐름 유지
시스템 웹 내부 클래스 연동 설정값(키·알고리즘 등) 주입 경로 수정
결제 유틸 내부 클래스 암호화 헤더 생성 공통 유틸 추가
ZlgoonErrorCode v2.5.0 신규 에러 코드 추가 정의
쿼리 매퍼(SQL) 연동 이력/설정 조회 쿼리 수정

CouponProviderFactory가 핵심이었다. 외부 쿠폰 제공사가 여럿 붙을 수 있는 구조라 Factory 패턴으로 Provider를 조립하고 있었는데, v2.5.0 분기를 여기서 잡아야 하는지, 아니면 Provider 내부에서 알아서 처리하게 해야 하는지 잠깐 고민했다.

결론은 Factory에서 버전별 분기를 처리하는 방향. Provider 내부가 버전을 직접 알아야 하면 결합도가 높아지고, 나중에 v2.6.x가 또 나왔을 때 Provider를 건드려야 하는 상황이 반복된다. Factory 한 곳에서 "어떤 버전용 Provider를 만들지"를 결정하고 내부 Provider는 넘겨받은 설정대로만 동작하는 구조가 훨씬 낫다고 판단했음.

암호화 헤더 도입 시 챙겨야 할 것들

헤더에 서명을 넣는 패턴은 외부 B2B 연동에서 자주 보인다. HMAC-SHA256이나 RSA 기반 서명을 타임스탬프·nonce와 함께 묶어서 헤더에 실어 보내는 방식이 대표적. 이번 Zlgoon v2.5.0도 비슷한 패턴이었다.

// 암호화 헤더 생성 패턴 (일반 예시)
String timestamp = String.valueOf(System.currentTimeMillis());
String nonce = UUID.randomUUID().toString().replace("-", "");
String rawSignature = apiKey + timestamp + nonce + requestBody;
String signature = HmacUtils.hmacSha256Hex(secretKey, rawSignature);

headers.set("X-Api-Key",    apiKey);
headers.set("X-Timestamp",  timestamp);
headers.set("X-Nonce",      nonce);
headers.set("X-Signature",  signature);

이런 서명 로직에서 실수가 잦은 포인트가 몇 가지 있다.

  • 문자열 직렬화 순서: 서명 원문(rawSignature)을 만들 때 어느 값을 어떤 순서로 이어 붙이는지 제공사 스펙 문서를 꼼꼼히 확인해야 함. 순서 하나 틀리면 서명 불일치로 403이 그냥 떨어짐
  • 타임스탬프 허용 오차: 제공사 서버와 내 서버 간 시각 차이가 허용 범위를 벗어나면 replay attack 방어 로직에 의해 거부되는 경우가 있음. 서버 NTP 동기화 상태 확인 필요
  • 에러 코드 매핑: v2.5.0에서 신규 에러 코드가 추가됐기 때문에 ZlgoonErrorCode에 빠짐없이 정의해두지 않으면 알 수 없는 오류로 묻혀버림. 이번에 이 파일도 같이 손봄

ZlgoonErrorCode 같은 에러 코드 enum/상수 파일은 외부 API 버전업 때 가장 놓치기 쉬운 파일인데, 코드리뷰에서 "신규 에러 코드 전부 반영됐나요?" 체크포인트를 리뷰어에게 명시적으로 요청하는 편이다.

팀 내 영향과 리뷰 포인트

이번 작업을 리뷰할 때 팀원들에게 두 가지를 특히 봐달라고 했다.

첫째, 기존 v2.4.x 흐름이 깨지지 않는지. 병행 지원 기간 동안 두 버전이 공존해야 하는 상황이라 분기 로직이 잘 격리돼 있는지 확인이 필요했음.

둘째, 시크릿 키 관리 경로. 암호화 서명에 쓰이는 secretKey가 코드에 하드코딩되거나, 잘못된 설정 파일에 들어가면 보안 문제가 된다. 설정값 주입 경로(시스템 웹 내부 클래스 쪽)를 건드렸기 때문에 이 부분 리뷰를 꼼꼼히 요청했다.

SQL 매퍼(쿼리 매퍼) 쪽도 바뀐 게 있어서, DB 스키마 변경이 수반되는지 여부를 QA 배포 전에 확인하는 절차를 거쳤다. 다행히 이번엔 기존 컬럼 범위 안에서 처리 가능한 수준이었음.

외부 제공사 API 버전업은 "단순 업그레이드"처럼 보이지만 인증 흐름·에러 처리·설정 경로 세 군데가 동시에 얽히는 작업이다. 변경 범위를 미리 테이블로 정리하고 리뷰 체크리스트를 만들어서 들어가는 게 나중에 디버깅 시간을 훨씬 줄여준다는 걸 이번에도 다시 확인했다.

끝.

댓글 0

첫 댓글 달아줘.