연결 문제 해결 · Clash 기술 블로그

Clash TLS 핸드셰이크 실패 해결 방법: 인증서, 시간 및 SNI 점검

TLS 오류는 구독 다운로드, 노드 핸드셰이크, 대상 웹사이트 접속에서 발생할 수 있으며 각 단계의 인증서, 시간, SNI 확인 위치가 다릅니다. handshake failed 전체 오류와 대상을 기록해 해당 위치에서 수정하고 인증서 검증을 끄지 마세요.

  • TLS
  • 인증서 오류
  • SNI
  • 연결 문제 해결
이 글의 목차

handshake failed는 구독 다운로드, 프록시 서버 연결, 대상 웹사이트 접속 중 어느 단계에서도 나올 수 있습니다. 관련 인증서와 설정은 다르며 무작정 노드를 바꾸거나 검증을 끄면 원래 문제를 가릴 수 있습니다. 실패 위치를 찾고 정확한 오류 내용에 따라 시간, 신뢰 체인, 서버 이름을 확인한 뒤 같은 요청을 다시 시도하세요.

TLS 핸드셰이크 실패: 로그 원문과 실패 위치로 점검 대상 찾기

TLS 오류 전체를 보관하고 구독 다운로드, 노드 연결, 대상 사이트 접속 중 어디에서 발생했는지 기록하세요. 핸드셰이크는 암호화 통신 조건을 협의하며 일반 HTTPS에서는 보통 클라이언트가 서버의 신원을 검증합니다. 아래 표에서 시간, 인증서, 노드 필드별 확인 대상을 구분하세요.

일반적인 원문

로그 문구우선 확인 방향
x509: certificate has expired or is not yet valid시스템 시간과 인증서 유효 기간
x509: certificate signed by unknown authority시스템 CA, 기업 SSL 검사와 사설 인증서
remote error: tls: handshake failureSNI, 프로토콜 필드와 서버 TLS 구성
tls: failed to verify certificate: x509인증서 체인, servername과 실제 인증서 이름
EOF / connection reset by peer상대가 조기에 연결을 종료했거나 네트워크가 차단함. 이 문구만으로 인증서 문제라고 단정할 수 없음

오류 전후의 몇 줄을 복사하고 시간, 대상 도메인과 포트는 보존하되 구독 token, UUID와 비밀번호는 가립니다. 'TLS failed'만 캡처하면 원인을 구분할 핵심 내용을 잃게 됩니다.

구독, 특정 노드와 대상 웹사이트의 오류는 점검 대상이 다릅니다

Profile 업데이트에서 TLS 오류가 나지만 기존 노드는 사용 가능

구독 URL에서 실패했습니다. 해당 도메인 인증서, 시스템 시간과 네트워크 검사 장비를 확인합니다.

노드 하나에서만 handshake failure 발생

클라이언트와 프록시 서버 사이에서 실패했습니다. 해당 노드의 server, port, SNI와 TLS 필드를 비교하세요.

노드는 연결되지만 HTTPS 웹사이트 하나에서만 인증서 오류

대상 사이트 인증서, 브라우저/앱 인증서 저장소와 보안 소프트웨어의 복호화 여부를 확인합니다.

모든 노드에서 동시에 x509 오류가 시작됨

시스템 시간, 코어 업그레이드와 네트워크의 인증서 일괄 교체 여부부터 확인합니다.

인증서가 만료됐거나 아직 유효하지 않다고 표시되면 시스템 시간 확인하기

Linux와 Windows에서 먼저 확인
# Linux
date -R
timedatectl status

# Windows PowerShell
Get-Date
w32tm /query /status

인증서에는 Not Before와 Not After가 있습니다. 이중 부팅 전환, 가상 머신 스냅샷, 장기간 전원이 꺼진 OpenWrt 또는 자동 시간 동기화 비활성화로 시간이 어긋날 수 있습니다. 날짜, 시간대와 NTP 동기화를 복구한 뒤 Mihomo를 재시작하고 다시 재현하세요. 오류가 완전히 같을 때만 핸드셰이크 필드를 계속 확인합니다.

노드 하나만 실패하면 SNI와 서버 인증서 이름 비교

TLS 노드 연결의 server는 IP이지만 인증서는 도메인에 발급되었을 수 있습니다. 이때 구성에는 올바른 servername 또는 sni가 필요합니다. 값은 서버 구성에서 받아야 하며 인터넷에서 인기 도메인을 추측하면 안 됩니다. 포트, 전송 유형, ALPN, Reality public-key/short-id 등의 필드도 한 세트로 일치해야 합니다.

프록시 유형과 현재 Mihomo 문서를 기준으로 필드 이름 확인
proxies:
  # 下列 IP、域名和密码都是占位值,不能直接连接
  - name: tls-example
    type: trojan
    server: 203.0.113.10
    port: 443
    password: REDACTED
    sni: edge.example.com
    skip-cert-verify: false

같은 네트워크에서 서버가 실제 반환하는 인증서 확인

도메인과 포트를 실패한 대상으로 교체
openssl s_client -connect edge.example.com:443   -servername edge.example.com -verify_hostname edge.example.com -verify_return_error -showcerts </dev/null

curl -Iv https://edge.example.com/

openssl 출력에서 subject, issuer, 유효 기간과 Verify return code를 확인하세요. 도메인으로 연결하면 SNI가 자동 전송될 수 있으므로 인수 하나를 삭제했다고 SNI가 전송되지 않았다고 판단할 수는 없습니다.

SNI 없이 비교하기 전에 사용 중인 OpenSSL이 -noservername을 지원하는지 확인하세요. -servername과 그 값을 삭제한 뒤 -noservername을 추가합니다. 같은 대상, -verify_hostname, -verify_return_error는 그대로 유지하세요. 두 SNI 옵션은 함께 사용할 수 없습니다.

같은 대상이 모바일 핫스팟에서는 정상 인증서를 반환하지만 회사 네트워크에서는 기업 CA 인증서를 반환한다면 검사 장비가 인증서를 바꿨을 수 있습니다. 두 결과를 관리자에게 전달하고 낯선 루트 인증서를 직접 설치하지 마세요.

프록시 프로토콜 포트가 일반 HTTPS 페이지를 제공하는 것은 아니므로 curl 실패만으로 노드가 손상되었다고 판단할 수 없습니다. openssl의 인증서와 핸드셰이크 정보가 더 유용합니다. Reality 등의 프로토콜에도 일반 웹사이트 인증서 검사를 그대로 적용할 수 없으며 해당 프로토콜 문서로 돌아가야 합니다.

회사 네트워크의 HTTPS 검사로 인증서가 바뀌었나요?

기업 프록시, 보안 게이트웨이와 일부 백신 프로그램은 HTTPS 인증서를 다시 발급합니다. 관리되는 기기에서는 관리자가 조직 CA를 설치하고 검사 가능한 트래픽을 설명해야 합니다. 개인 사용자는 오류 웹페이지에서 낯선 루트 인증서를 받거나 Clash 업데이트를 위해 시스템 전체 인증서 검증을 끄면 안 됩니다.

모바일 핫스팟으로 바꾼 뒤 같은 구독 URL이 바로 정상화되면 네트워크 경로 차이의 근거가 됩니다. 회사 네트워크에서의 issuer, 오류 시각과 대상 도메인을 관리자에게 전달하는 편이 노드를 계속 바꾸는 것보다 유용합니다.

수정 후 기존에 실패하던 같은 연결 반복

검증 결과

  • 시스템 시간과 시간대가 올바르고 코어 재시작 후 not yet valid/expired가 더 이상 나타나지 않음
  • 구독이 실패한 경우 수동 업데이트에 성공하고 업데이트 시각이 바뀜
  • 노드가 실패한 경우 같은 노드에서 핸드셰이크를 완료하고 실제 연결 기록을 생성함
  • 대상 웹사이트가 실패한 경우 인증서 issuer와 도메인이 예상과 일치함
  • 임시로 끈 인증서 검사 또는 보안 설정을 복원함
  • 통제된 테스트에 명확한 이유가 없다면 skip-cert-verify를 false로 유지

참고 자료