터널을 연결하고 같은 북마크를 열면 허용 목록에 있는 사이트는 사무실에서와 정확히 똑같이 응답합니다. 이것이 대부분의 원격 접속 계획이 조용히 기대는 가정이며, 세 가지 별개의 조건이 동시에 참인 동안에만 성립합니다. 그중 어느 것도 VPN 클라이언트의 기능이 아니며, 어떤 DNS 레코드도 그것을 제공할 수 없습니다. 집에서 북마크가 실패하면 브라우저는 원인이 빠진 경로이든, 승인되지 않은 송신지 주소이든, 보고하는 출처를 바꿔치기한 프록시이든 하나의 일반 오류를 보여 줍니다. 이 셋을 하나의 문제로 다루는 것이 작은 정책 수정을 허용 목록을 넓히는 일주일로 만드는 길입니다.

실제 사무실 네트워크와 맞닥뜨려도 살아남는 설계는 그 가정보다 좁습니다: 명시적인 세 행 결정 표, 우회할 수 없는 단일 적용 지점, 그리고 무언가를 증명하는 거부 테스트입니다. 가정을 해체하는 일이 먼저인데, 그 뒤의 모든 것이 어느 계층이 출처를 잘못 표현하는지 아는 데 달려 있기 때문입니다.

신화: 연결은 라우팅이 아니다

터널이 수립되고 클라이언트가 일정한 프리픽스 집합에 대한 경로를 설치합니다. 연결이 하는 일은 그것뿐입니다. 무관한 HTTPS 요청이 터널을 지나는지, 도착할 때 어느 공용 주소에서 온 것으로 보이는지는 나중에 다른 구성 요소가 내리는 결정입니다: 라우팅 표가 경로를 고르고, 출구가 출처를 고릅니다.

그래서 같은 노트북, 같은 브라우저 프로필, 같은 북마크로도 사무실과 부엌 식탁의 결과가 갈립니다. 사무실에서는 사이트 운영자가 동의한 유지 관리되는 공용 주소로 요청이 나갑니다. 전체 터널에서는 VPN 출구로 나갈 수 있는데, 그것은 다른 주소이며 누군가 추가하기 전까지는 승인되지 않은 주소입니다. 분할 터널에서는 터널에 아예 들어가지 않을 수 있습니다. 그 세 경로 가운데 둘만이 사이트 소유자와의 합의에 포함되었고, 셋째는 allow 항목을 하나 더 추가해 덧대어야 할 결함이 아닙니다.

세 가지 요청 상태, 두 개의 승인된 출구

방화벽을 건드리기 전에 행렬을 적어 두십시오. 표가 설계이고 규칙은 그 구현 하나일 뿐이므로, 아래 주소는 문서용 대역이며 자신이 유지 관리하는 값으로 바꾸고 사이트 소유자가 감사할 수 있는 곳에 보관하십시오.

Request pathSource the site seesIntended decision
Office, no tunnelOffice public exitAdmit to the application login
Remote, approved full tunnelApproved VPN egressAdmit to the same login
Remote, ordinary connectionNeither approved addressDeny at the network boundary

이 계획 대부분이 깨지는 곳이 가운데 행입니다. 중요한 것은 적용 장치가 보는 주소이며, 노트북이 터널 안에서 가지는 사설 주소도, 그 LAN 주소도 아닙니다. 10.8.0.6 같은 값은 공용 사이트에 아무 의미가 없고 192.168.1.44 도 마찬가지입니다. 터널 주소는 터널 주소 지정의 세부 사항이지 사이트가 검증할 수 있는 자격 증명이 아닙니다.

VPN이 안정적이고 문서화된 출구를 제공할 수 없다면 행렬에는 유효한 가운데 행이 없으며, 허용 목록을 아무리 늘려도 만들어지지 않습니다. 그 지점에서 정직한 선택은 명시적 사설 경로로 도달하는 사설 사이트이거나, 애플리케이션 앞의 ID 인식 접근 게이트웨이입니다. 둘 다 공용 허용 목록과 다른 계약을 가지며, 둘 다 우연히 동작할 때까지 자란 목록보다 감사자에게 설명하기 쉽습니다.

결정이 내려지는 곳에서 출처를 읽으십시오

제한을 요청을 종료하는 장치에 두고, 다른 출발 경로가 그것을 우회하지 않는지 확인하십시오. Nginx 접근 모듈 allow와 deny 지시문을 순서대로 평가하고 첫 일치가 이기며, 감싸는 블록에서 상속된 규칙은 location 내부에서도 계속 적용됩니다. 같은 위치에서 좁은 allow가 넓은 allow 옆에 있으면 보통 넓은 쪽이 결정합니다. 그 location의 유효한 전체 구성을 한 줄이라도 편집하기 전에 읽으십시오.

server {
    listen 443 ssl;
    server_name intranet.example.com;

    set_real_ip_from 10.20.0.10;
    real_ip_header X-Forwarded-For;
    real_ip_recursive on;

    location /app/ {
        allow 203.0.113.24;    # office public exit
        allow 198.51.100.77;   # approved VPN egress
        deny  all;
        proxy_pass http://app_backend;
    }
}

로드 밸런서나 리버스 프록시 뒤에서는 달리 말하지 않는 한 그 규칙은 프록시를 봅니다. 호출자 주소는 지원되는 신뢰 프록시 메커니즘을 통해서만, 프록시 주소의 명시적 목록과 함께 복원하십시오. 승인된 주소를 주장하는 요청 헤더는 호출자가 그것을 소유한다는 증거가 아니며, 공용 리스너에서 검증되지 않은 전달 헤더는 허용 목록을 장식으로 만듭니다.

다음으로 다른 주소 체계를 확인하십시오. IPv4만 포괄하는 규칙 집합은 AAAA에서도 응답하는 호스트 이름에 대한 불완전한 결정이며, IPv6가 동작하는 클라이언트는 검토한 적 없는 경로로 같은 애플리케이션에 도달합니다.

분할 터널: 결코 들어가지 않는 요청

분할 터널은 목록에 있는 프리픽스만 전달합니다. 사무실 내부 서브넷은 보통 그 목록에 들어가고, 공용 웹사이트는 들어가지 않습니다. 브라우저는 이름을 확인하고, 선택한 주소를 라우팅 표와 비교하며, 그래도 앞에 있는 로컬 기본 게이트웨이를 찾습니다.

그래서 요청은 사용자의 가정 연결에서 도착해 거부되고, 보고서에는 VPN이 고장 났다고 적히지만 터널은 설정된 대로 정확히 동작하고 있습니다. 정당한 수정은 두 가지인데, 그 목적지를 터널로 보내 승인된 출구가 나르게 하거나, 사이트에 직접 도달함을 인정하고 원격 사용자에게 접근 게이트웨이 같은 다른 승인 경로를 주는 것입니다. 가정 주소가 우연히 포함될 때까지 사이트의 공용 허용 목록을 넓히는 것은 둘 다 아니며, 설계가 적용해야 할 경계를 없앱니다. 처음 두 가지는 행렬을 정직하게 유지하고, 셋째는 거기서 한 행을 조용히 지웁니다.

거부를 증명하고, 그다음 복구를 증명하십시오

표의 각 행에 선 클라이언트에서 실제 결정을 행사하는 요청으로 시험하십시오. 무관한 주소 표시 페이지에 대한 도달성 점검은 그 목적지가 애플리케이션과 다른 경로를 따를 수 있으므로 아무것도 증명하지 못합니다.

curl -sS -o /dev/null -w 'status=%{http_code}
' https://intranet.example.com/app/login
# repeat with the tunnel up, then with it down
tail -f /var/log/nginx/access.log | grep ' /app/'

경계의 접근 기록을 표가 예측한 것과 비교하십시오. 그다음 터널을 내리고 거부되어야 할 새 요청을 보내되, 이미 로드된 페이지나 이미 열린 연결은 아무것도 시험하지 않습니다. 거부가 나타나지 않으면 적용 지점은 당신이 생각하는 곳이 아닙니다.

네트워크 허용 뒤에도 애플리케이션 인증을 유지하십시오(사무실 출구와 VPN 출구는 각각 많은 사람을 대표하며 어느 것도 개인을 식별하지 않습니다). 사용자 지침은 승인된 터널을 올린 뒤 다시 시도하라는 짧은 것으로 유지됩니다. 이것이 출처 규칙을 추측이 아닌 결정으로 유지하면서 하나의 URL을 편리하게 지켜 줍니다.

관련 글