VPN 을 켜면 localhost 가 안 될 때: 이름, 프록시, 바인드
검색 접미사나 프록시가 개입하면 localhost 는 더 이상 내 컴퓨터를 뜻하지 않습니다. 이름을 먼저, 그다음 경로, 마지막으로 도구의 연결 문자열을 고치세요.
개발 서버가 방금 전까지 응답했는데, 터널이 올라온 지금은 한 번도 입력한 적 없는 호스트 이름으로 요청이 시간 초과됩니다. 거의 모든 경우를 두 가지 메커니즘이 설명하며, 밖에서 보면 둘은 똑같아 보입니다. 검색 접미사는 짧은 이름을 사내 이름으로 바꾸고, 프록시는 루프백 트래픽을 도달할 수 없는 호스트로 보냅니다. 둘을 구분하는 데는 질의 한 번이면 되고, 쓰려던 방화벽 규칙을 아낄 수 있습니다.
localhost 가 사내 영역으로 해석될 때
터널이 올라와 있는 동안 이름이 어디로 해석되는지 확인하고, 그다음 터널을 내린 상태에서 같은 질의를 실행해 두 답을 비교하세요. 단서는 127.0.0.1 를 기대한 자리에서 사내 대역 주소가 나오는 것입니다. localhost.mycompany.corp 같은 레코드는 클라이언트가 그 접미사를 검색 목록에 추가하는 순간 루프백 항목을 이기고, 요청은 그 포트에서 아무것도 듣지 않는 사설 호스트로 갑니다. 검색 목록은 추측하지 말고 읽으세요, 클라이언트가 둘 이상의 도메인을 추가할 수 있고, 순서가 어느 후보를 먼저 시도할지 정하기 때문입니다:
getent hosts localhost
resolvectl domain
ss -ltnp | grep 8080
애플리케이션, 데이터베이스 클라이언트, 노트북 URL 에서 호스트 이름을 리터럴 주소로 바꾼 뒤 요청을 다시 보내세요. 실패가 사라지면 이름 문제였고 터널은 방아쇠였을 뿐입니다. 계속되면 리스너나 경로가 다음 용의자이고 이름은 잘못된 단서였습니다.
루프백을 가로채는 프록시 설정
터널이 올라올 때 적용되는 시스템 프록시는 127.0.0.1 로 가는 요청을 받아 무엇을 의도했는지 모르는 원격 프록시로 넘깁니다. 우회 목록이 비어 있으면 로컬 요청이 원격 요청이 되는데, 오류 메시지는 그 사실을 거의 말해 주지 않습니다. 루프백 주소를 단일 명령이 아니라 세션 전체의 우회 목록에 추가하고, 네트워크에 대해 결론을 내리기 전에 도구가 이를 지키는지 확인하세요.
애플리케이션 프레임워크는 자체 환경 변수와 때로 자체 설정 파일을 읽으므로, 한 도구에서 통하는 우회가 다음 도구에 대해서는 아무것도 증명하지 않습니다. 브라우저에는 변수가 하나 더 있습니다, Chromium 기반 브라우저는 루프백에 대해 프록시를 암묵적으로 우회하며, 우회 토큰이 있으면 그 동작이 사라집니다. 운영 체제 설정이 전부라고 가정하지 말고 실제 프록시 판정을 확인하세요. 셸에서 시작한 모든 것에 대해 두 명령이 이를 정리합니다:
curl --noproxy '*' http://127.0.0.1:8080/health
NO_PROXY=localhost,127.0.0.1,::1 your-tool
연결할 수 있는 상대는 바인드 주소가 정한다
127.0.0.1 에서 시작한 서버는 그 컴퓨터에서 오는 연결만 받는데, 개발에서는 보통 이것이 맞는 기본값입니다. 0.0.0.0 의 서버는 VPN 어댑터를 포함한 모든 인터페이스에서 응답하므로 대부분이 의도하는 것보다 노출이 큽니다. 리터럴 루프백 주소가 실패하면 무엇보다 먼저 바인드를 확인하세요.
듣고 있는 소켓을 보고 포트만이 아니라 어느 주소에 묶여 있는지 기록하세요. 다른 기기나 컨테이너가 터널을 통해 서비스에 닿아야 한다면 그것이 쓸 특정 인터페이스에 바인드하고 그 포트를 의도적으로 허용하세요. 내 컴퓨터만 필요하다면 좁은 바인드를 유지하고 서버를 넓히는 대신 클라이언트를 고치세요. 포트 포워딩이나 터널 계층이 둘을 이어 줄 수 있지만, 각각은 나중에 자체 디버깅이 필요한 구성 요소를 더합니다.
디버깅 도구가 LAN 을 기대하는 자리
디버깅 도구는 터널이 조용히 깨뜨리는 가정을 품고 있습니다. 휴대폰 디버깅 브리지는 VPN 이 기기의 서브넷을 잡으면 기기를 잃어버리므로, LAN 주소나 케이블로 다시 연결하면 충돌을 피할 수 있습니다. 브라우저 자동화 허브는 허브가 프록시로만 닿을 때, 또는 로컬 방화벽이 제어 포트를 떨어뜨릴 때 시간 초과됩니다. 원격 디버거는 클라이언트가 경로를 다시 쓴 자리에서 권한 상승과 루프백 주소를 요구할 수 있습니다.
제어 포트와 데이터 포트를 따로 파악하세요, 한쪽만 살아남는 일이 흔하기 때문입니다. 그다음 수정이 도구 설정에 속하는지, 그 서브넷의 경로에 속하는지, 아니면 분할 터널 규칙 에 속하는지 정하세요. 개발자마다 hosts 파일을 고치는 방식은 확장성이 가장 나쁘고 가장 먼저 잊힙니다. 프로필과 함께 살고 터널을 가진 누구나 검토할 수 있는 설정을 택하세요.
처음 실패한 단계에서 멈추기
세 단계를 차례로 내려가세요, 이름을 해석하고, 리터럴 주소로 소켓을 열고, 마지막으로 도구가 스스로 연결하게 하세요. 각 단계가 계층 하나를 없애므로 첫 실패가 고칠 계층을 알려 주고 그 뒤의 모든 것은 검증되지 않은 채 남습니다. 무엇이든 바꾸기 전에 결과를 적어 두세요, 측정 전에 적용한 수정은 운과 구별되지 않습니다. 첫 시도가 실패하고 재시도가 되면 도구가 시작될 때 터널이 준비되지 않았던 것입니다.
고정 대기를 경로를 기다리는 제한된 준비 확인으로 바꾸고, 실패한 단계를 로그에 남겨 다음 사람이 어디서 멈췄는지 보게 하세요. 스스로 회복하는 도구는 고쳐진 것이 아니라 운이 좋은 것이고, 그 운은 다른 사람의 컴퓨터에서 떨어집니다. 터널은 마지막에, 그리고 실제로 실패한 단계에 대해서만 바꾸세요. 그 순서는 작동하는 빌드로 돌아가는 가장 짧은 길이기도 합니다, 애초에 관여하지 않은 구성 요소를 다시 만들지 않게 해 주기 때문입니다.