Clash 로컬 콘솔이 안 열릴 때: external-controller·external-ui 항목별 점검

이 증상이면 이 글부터 읽으면 됩니다

Clash·Clash Meta(mihomoClash Verge Rev 등에서 REST API와 웹 패널을 켰는데도, 브라우저 주소창에 localhost와 포트를 넣어도 “연결 거부”, “사이트에 연결할 수 없음”, 혹은 패널은 뜨는데 데이터만 비어 있고 오류가 반복되는 경우가 있습니다. YacdMetacubexd, 구독 프로필에 붙은 external-ui 주소를 그대로 따라가도 같은 증상이 나면, 원인은 단순히 “프록시 노드가 나쁘다”가 아니라 코어가 어디에 리슨하는지, 브라우저가 어떤 스킴(HTTP/HTTPS)으로 API를 호출하는지, 설정 파일이 mixin 등으로 덮였는지로 좁혀지는 경우가 많습니다.

본문은 Rule Provider 갱신이나 Sniffer, Allow LAN 같은 다른 튜토리얼과 달리, 오직 “대시보드·로컬 콘솔만 안 된다”는 장면에 초점을 맞춥니다. 포트가 다른 프로세스에 잡혀 코어 자체가 안 뜨는 패턴은 Windows 포트 점유·mixed-port 글과 맞물리므로, 로그에 bind 실패가 보이면 그쪽 절차를 먼저 보시면 됩니다.

핵심: external-controller는 “문자열로 한 줄 적어 두었다”에서 끝이 아니라, 코어가 실제로 그 주소·포트에서 TCP 리슨하고 있어야 하며, 패널에 적어 넣은 베이스 URL·포트·secret이 실행 중인 프로세스와 같아야 합니다. GUI가 생성한 실제 YAML과 로그를 한 번이라도 대조하면 헛발이 줄어듭니다.

1. 리슨 주소: 127.0.0.1과 0.0.0.0 차이

external-controller에 흔히 쓰는 형태는 127.0.0.1:9090 또는 0.0.0.0:9090 같은 문자열입니다. 127.0.0.1(루프백)만 열면 같은 기기 안의 브라우저에서 접근할 때만 자연스럽고, 다른 PC·스마트폰이 같은 네트워크에서 패널을 열려면 Allow LAN류 옵션과 함께 LAN 인터페이스 IP로 접근해야 합니다. 반대로 0.0.0.0은 모든 인터페이스에서 들어오는 연결을 받아들이려는 형태에 가깝습니다. 사용자 입장에서는 “로컬에서만 보면 된다”여도 설정 샘플이 0.0.0.0으로 되어 있으면 방화벽·보안 소프트웨어와 충돌 이야기가 나올 수 있으니, 의도와 보안 요구를 맞추는 것이 먼저입니다.

브라우저에 입력하는 주소도 리슨과 같아야 합니다. 예를 들어 코어가 127.0.0.1:9090인데 주소창에 다른 머신의 IP를 넣거나, 포트만 바꾼 채 저장했다면 연결이 거부됩니다. 클라이언트 GUI가 표시하는 “외부 컨트롤러 포트” 숫자와, 실행 중인 설정 파일 속 external-controller 문자열이 같은지 확인하세요.

2. YAML·mixin·프로필 덮어쓰기

YAML 문법 오류 한 글자로 코어가 기대한 키를 읽지 못하거나, 이전 설정이 남아 external-controller 줄이 무시되는 경우가 있습니다. mihomo·계열 클라이언트는 mixin·추가 프로필·구독 병합 규칙에 따라 마지막에 로드된 값이 우선할 수 있어, 화면에서 본 값과 디스크에 쓰인 최종 파일이 다를 수 있습니다. “GUI에는 9090인데 로그에는 9091만 listen” 같은 불일치가 나오면, 실제 로드 경로의 YAML을 한 파일로 펼쳐 중복 키를 찾아보는 것이 좋습니다.

구독 URL이 제공하는 베이스 설정에 external-controller가 이미 있고, 로컬에서 덧씌운 값이 없으면 원격 템플릿이 그대로 살아 있을 수 있습니다. 이때 포트 충돌이나 의도치 않은 외부 바인딩이 생기면 보안상 위험할 수 있으니, 로컬에서 명시적으로 덮어쓰거나 민감한 경우 secret을 함께 설정하는 편이 낫습니다.

3. secret·인증 헤더와 보안

API에 secret(또는 동일 목적의 토큰)이 걸려 있으면 패널 설정에 동일 값을 넣지 않으면 요청이 401 등으로 막힙니다. 일부 패널은 “비어 있는데도 된다”고 보이지만 코어에는 값이 있는 경우가 있어, 둘 다 비우거나 둘 다 같게 맞추어야 합니다. 공개 WiFi나 팀 네트워크에서 0.0.0.0으로 외부에 컨트롤러를 노출하면 타인이 규칙을 바꿀 수 있어 매우 위험합니다. 로컬 전용이라도 장비 분실·멀웨어 시나리오를 고려하면 secret 없는 외부 바인딩은 피하는 것이 안전합니다.

4. external-ui 경로와 내장 웹 자산

external-ui는 코어가 정적 파일을 서빙할 디렉터리를 가리키는 경우가 많습니다. 경로가 비어 있거나 잘못되면 패널 자바스크립트가 로드되지 않아 하얀 화면이나 깨진 레이아웃만 보일 수 있습니다. 패키지 매니저·GUI가 배포하는 기본 경로와 사용자가 내려받은 Yacd 빌드를 혼동하지 않도록, 실제 디렉터리에 index.html 등이 있는지 확인하세요.

Yacd·Metacubexd는 보통 브라우저에서 직접 열되, 내부에서 REST API 베이스 URL(예: http://127.0.0.1:9090)을 따로 입력하게 되어 있습니다. 여기 적은 호스트·포트가 실행 중인 external-controller와 다르면 노드 목록이 비거나 오류만 반복됩니다.

5. Mixed Content: HTTPS 페이지와 HTTP API

패널을 HTTPS 사이트나 파일이 아닌 https://으로 여는 브라우저 확장·북마크에서 열었다면, 페이지 보안 정책 때문에 http://127.0.0.1:9090 같은 로컬 HTTP API 호출이 차단되는 경우가 있습니다. 개발자 도구 콘솔에 Mixed Content 관련 메시지가 뜨는지 확인하세요. 해결 방향은 “패널도 로컬에서 HTTP로 연다”, “신뢰할 수 있는 로컬 HTTPS 종료를 둔다” 등 환경에 따라 달라지며, 단순히 Clash 노드만 바꿔서는 해결되지 않습니다.

6. 방화벽·Docker·WSL과 포트 매핑

Windows Defender 방화벽·맥 방화벽·보안 제품이 인바운드 규칙으로 해당 포트를 막으면 브라우저에서는 “연결 거부”에 가까운 증상이 납니다. 로컬 루프백만 쓸 때도 예외 규칙이 간섭하는 빌드가 있어, 테스트 시에는 잠깐 규칙을 확인해 보거나 같은 기기에서 curl 등으로 로컬 포트 응답을 먼저 확인할 수 있습니다.

Docker 안에서 mihomo를 돌리면서 호스트 브라우저로 패널을 열 때는 컨테이너 내부 127.0.0.1과 호스트의 127.0.0.1이 다릅니다. -p 9090:9090 식 매핑과 external-controller의 바인딩 주소가 맞는지, Docker Desktop과 Clash 문맥에서 자주 나오는 포트 매핑을 함께 보시면 됩니다. WSL2에서 코어를 돌리고 Windows 브라우저로 접속할 때도 루프백이 직통이 아니므로 WSL IP나 포워딩 규칙을 혼동하지 않도록 주의합니다.

7. 로그로 확인하는 순서

코어 로그에 external controller listen 또는 비슷한 문구가 찍히는지, 포트 번호가 기대와 같은지 확인합니다. 시작 직후 바인딩 실패가 있으면 설정 값 자체 문제이거나 다른 프로세스 점유일 가능성이 큽니다. GUI가 “API 사용 가능”이라고 해도 실제 프로세스가 다른 설정 파일을 읽었을 수 있으니, 로그상 설정 경로도 함께 봅니다.

한 페이지 체크리스트

  • 실행 중인 설정에서 external-controller 문자열과 브라우저·패널에 입력한 호스트·포트가 일치하는가.
  • mixin·프로필 병합 뒤 최종 YAML에 같은 키가 두 번 이상 없고, 의도한 값이 살아 있는가.
  • secret을 썼다면 패널 설정과 빈 값 여부까지 동일한가.
  • external-ui 디렉터리가 존재하고 정적 파일이 보이는가.
  • Mixed Content 때문에 브라우저가 로컬 HTTP API를 막고 있지 않은가.
  • 방화벽·보안 소프트웨어 인바운드가 해당 포트를 허용하는가(원격 바인딩 시 특히).
  • Docker·WSL이라면 호스트와 컨테이너의 127.0.0.1 혼동이 없는가.

주의: 문제 해결을 위해 0.0.0.0으로 무조건 열거나 secret 없이 외부망에 노출하면 규칙·구독이 타인에게 노출될 수 있습니다. 필요 최소 주소만 열고, 가능하면 secret과 함께 쓰세요.

마무리

Clash에서 API와 웹 패널은 프록시가 잘 되는지와 별개로, 리슨 주소·포트·YAML 최종본·브라우저 보안 정책이 한 줄로 맞아야 합니다. Yacd·Metacubexd는 편하지만 설정 입력 한 칸이라도 어긋나면 “연결만 안 된다”는 체감이 되므로, 이 글의 순서대로 좁히면 같은 증상을 반복 줄이기 쉽습니다. 기본 사용 흐름을 더 보강하려면 문서·빠른 시작과 함께 읽어도 좋습니다.

규칙 편집·노드 품질과 별개로, 로컬 콘솔만 안정적으로 열리면 이후 튜닝 시간이 크게 줄어듭니다. → Clash를 무료로 다운로드한 뒤, 위 체크리스트로 external-controllerexternal-ui를 다시 맞춰 보시기 바랍니다.