WebSocket 하네스 (H-B)
업그레이드는 일반 요청과 처리 경로가 다릅니다. 프록시가 일반 요청에 걸어 둔 처리(세션 쿠키 제거 등)가 업그레이드에는 안 돌 수 있습니다.
읽는 법
- #1 이 실패하면 나머지는 의미가 없다 — 업그레이드 자체가 프록시를 통과하지 못한 것이다. 프록시의 ws 배선부터 본다.
- 브라우저는 실패 이유를 주지 않는다 — WebSocket 의 onerror 는 이유 없는 이벤트 하나뿐이다. 그래서 서버가 받은 업그레이드 기록(
/api/lab/ws-upgrades
)을 함께 본다. 그 기록이 비어 있으면 요청이 서버까지 오지도 못한 것이다. - #6 은 보안 케이스다 — 일반 요청에서는 프록시가 자기 세션 쿠키를 지우고 업스트림에 보낸다. 업그레이드에도 그 처리가 도는지 확인한다. 실패하면 우리 세션 쿠키가 고객사 앱에 새는 것이다.
접속 경로
브라우저가 보는 주소
https://aws-insider-e1e444fd-dfae-480a-b782-5eaa35682f5e.feelanet.ai요청 유도
WebSocket 엔드포인트
/api/ws/echo— 페이지 origin 의 스킴을 ws/wss 로 바꿔 접속합니다. https 페이지에서는 wss 여야 브라우저가 막지 않습니다.
케이스 11개. 유휴 유지(#9)에 15초가 걸립니다.
/api/ws/echo
ws:// 또는 wss:// 로 연결해 101 Switching Protocols 를 받는다. 프록시가 upgrade 를 나르지 못하면 여기서 전부 멈춘다.
★ 이것이 실패하면 아래 케이스는 전부 의미가 없다. 프록시의 ws 배선부터 본다.
문자열을 보내고 같은 문자열이 돌아오는지 본다. 가장 기본적인 왕복.
바이너리 프레임을 보내고 **바이너리로** 돌아오는지 본다. 중간에서 텍스트로 바뀌면 프레임 종류가 보존되지 않는 것이고, 파일 전송이나 프로토콜 버퍼가 깨진다.
1MB 페이로드를 왕복시킨다. 프록시가 프레임을 버퍼링하거나 쪼개면 여기서 드러난다. H-A 의 8MB 바이너리와 같은 성격의 케이스다.
업그레이드는 일반 요청과 헤더 처리 경로가 다르다. 서버가 본 cookie 헤더를 그대로 돌려받아 확인한다. 세션이 필요한 앱이라면 이것이 실려야 한다.
일반 요청에서는 on.proxyReq 가 prism_proxy 세션 쿠키를 지운다. **업그레이드에는 그 콜백이 돌지 않는다.** 서버가 본 쿠키 이름 목록에 우리 세션 쿠키가 있으면 유출이다.
★ 보안 관점의 핵심 케이스. 통과해야 정상이고, 실패하면 프록시 수정이 필요하다.
업스트림이 Origin 으로 교차 사이트 업그레이드를 막는 경우가 있다. 프록시가 Origin 을 어떻게 넘기는지에 따라 앱이 스스로를 차단할 수 있다.
Sec-WebSocket-Protocol 을 실어 보내고 서버가 고른 값이 돌아오는지 본다. 프록시가 이 헤더를 떨어뜨리면 협상이 실패해 클라이언트가 연결을 끊는다.
15초 동안 아무것도 주고받지 않은 뒤 다시 에코가 되는지 본다. 중간 장비가 유휴 연결을 끊으면 여기서 드러난다 — 하이브리드 커넥션 구간이 특히 의심 대상이다.
15초 걸린다. 실제 운영에서는 더 긴 유휴가 문제가 되므로 이건 하한선 확인이다.
소켓 4개를 동시에 열어 각각 에코가 되는지 본다. 프록시의 커넥션 풀 상한 (UPSTREAM_MAX_SOCKETS)과 릴레이 슬롯 소모를 함께 본다.
server.mjs 는 /api/ws/echo 외의 업그레이드를 socket.destroy() 로 끊는다. 연결이 성립하면 오히려 문제다 — 중간에서 누군가 업그레이드를 가로채고 있다는 뜻이다.