YAML 구조 개요와 로드 순서
최상위 블록의 협업 방식
실행 가능한 Clash 또는 mihomo 설정은 일반적으로 공통 설정, DNS, 프록시 노드, 정책 그룹과 규칙의 다섯 부분으로 구성됩니다. 이들은 서로 독립된 목록이 아니라 참조 관계로 이어진 흐름입니다. proxies는 연결을 수립할 수 있는 노드를 정의하고, proxy-groups는 노드나 다른 정책 그룹을 선택 가능한 출구로 묶으며, rules는 연결을 특정 정책 그룹, DIRECT 또는 REJECT로 보냅니다. DNS는 도메인 조회 과정을 이 흐름에 포함하고, 공통 필드는 수신 포트, 실행 모드, LAN 접근 범위와 제어 인터페이스를 결정합니다.
필드의 위치는 들여쓰기로 결정됩니다. 최상위 키는 줄의 맨 앞에서 시작하고, 하위 필드는 보통 공백 두 칸을 들여쓰며, 목록 항목은 하이픈으로 시작합니다. YAML에서 탭은 계층 표현에 사용할 수 없으며, 같은 계층에 공백 두 칸과 네 칸을 섞어서도 안 됩니다. 텍스트 편집기에서 정상적으로 보인다고 해서 파서가 반드시 받아들이는 것은 아닙니다. 한국어 문장 부호, 전각 콜론, 보이지 않는 탭 문자와 잘못된 들여쓰기는 흔한 로드 실패 원인입니다. 문자열에 콜론, 샵, 중괄호 또는 앞뒤 공백이 포함되면 작은따옴표나 큰따옴표로 감싸는 편이 안전합니다.
mixed-port: 7890
allow-lan: false
mode: rule
log-level: info
ipv6: false
dns:
enable: true
enhanced-mode: fake-ip
nameserver:
- 1.1.1.1
- 8.8.8.8
proxies:
- name: "예시 노드"
type: ss
server: 192.0.2.10
port: 443
cipher: aes-128-gcm
password: "your-password"
proxy-groups:
- name: "노드 선택"
type: select
proxies:
- "예시 노드"
- DIRECT
rules:
- DOMAIN-SUFFIX,example.com,노드 선택
- MATCH,DIRECT
맵, 목록과 스칼라
설정 파일을 읽을 때는 먼저 세 가지 기본 데이터 유형을 구분하면 됩니다. 맵은 키와 값의 조합으로, 예를 들어 mode: rule과 같습니다. 목록은 하이픈으로 시작하는 항목들의 모음이며, nameserver 아래의 주소가 이에 해당합니다. 스칼라는 문자열, 숫자 또는 불리언 값입니다. true와 false에는 따옴표가 필요하지 않고, 포트는 보통 숫자로 작성하며 노드 이름은 문자열입니다. 불리언 값을 따옴표가 있는 "false"로 쓰면 일부 구현에서 일반 텍스트로 처리해 예상과 다른 결과가 나올 수 있습니다.
YAML은 인라인 배열도 지원합니다. 예를 들면 proxies: [노드 A, 노드 B, DIRECT]와 같습니다. 짧은 목록에는 적합하지만 노드가 많거나 이름에 문장 부호가 포함되거나 자주 수정해야 할 때는 가독성이 크게 떨어집니다. 체계적인 설정에는 항목을 줄마다 작성하는 목록이 더 적합합니다. 앵커, 참조와 복합 타입은 YAML 표준 기능이지만 모든 클라이언트의 오버라이드 시스템이 완전히 보존하는 것은 아닙니다. 여러 클라이언트에서 사용할 설정이라면 일반적인 맵과 목록을 우선하세요.
파싱부터 적용까지의 점검 순서
설정 로드는 세 단계로 점검할 수 있습니다. 첫째는 YAML 문법으로, 들여쓰기와 콜론, 목록 형식을 확인합니다. 둘째는 필드 구조로, 노드에 server가 빠졌는지 또는 정책 그룹이 존재하지 않는 이름을 참조하는지 확인합니다. 셋째가 런타임 문제로, 원격 서버에 연결할 수 없거나 DNS 업스트림이 시간 초과되거나 시스템 프록시가 트래픽을 넘겨받지 못하는 경우입니다. “연결할 수 없음”을 본 즉시 규칙을 바꾸지 마세요. 먼저 클라이언트 로그에 설정 파싱 오류가 있는지 확인하고, 이어 대상 정책 그룹에서 노드를 선택할 수 있는지, 마지막으로 연결과 DNS를 점검하면 문제 해결이 훨씬 빨라집니다.
공통 필드, 수신 포트 및 실행 모드
포트 필드의 역할
port는 HTTP 프록시 포트, socks-port는 SOCKS5 프록시 포트, mixed-port는 하나의 포트에서 HTTP와 SOCKS5 요청을 모두 받는 설정입니다. 데스크톱 그래픽 클라이언트는 보통 mixed-port만 설정한 뒤 클라이언트가 시스템 프록시를 자동으로 구성하도록 하면 됩니다. 특정 애플리케이션에서 프록시 유형을 따로 지정해야 할 때만 두 포트로 나누면 됩니다. 여러 필드를 동시에 사용할 수 있지만 포트 번호가 시스템의 다른 프로그램이나 다른 Clash 인스턴스와 충돌해서는 안 됩니다.
포트 충돌은 커널이 시작된 직후 종료되고 로그에 bind, listen 또는 address already in use가 나타나는 형태로 드러나는 경우가 많습니다. 먼저 남아 있는 프로세스를 종료하거나 설정 포트를 사용되지 않는 값으로 변경한 뒤, 브라우저·개발 도구·시스템 프록시의 포트도 함께 수정하세요. YAML만 바꾸고 수동 설정된 애플리케이션을 갱신하지 않으면 커널은 정상 실행되지만 애플리케이션은 연결하지 못할 수 있습니다. 클라이언트에 포트 설정 화면이 있다면 화면에서 수정하는 편이 좋습니다. 일부 클라이언트는 오버라이드 계층으로 구독의 원래 포트를 덮어쓰기 때문입니다.
| 필드 | 용도 | 일반적인 사용 방식 |
|---|---|---|
mixed-port |
HTTP 및 SOCKS5 동시 수신 | 데스크톱 클라이언트와 로컬 애플리케이션의 공용 진입점 |
port |
HTTP 프록시 전용 | HTTP 프록시만 지원하는 프로그램 |
socks-port |
SOCKS5 프록시 전용 | 명령줄 도구, 개발 환경 또는 특정 애플리케이션 |
redir-port |
투명 프록시 리디렉션 진입점 | 주로 Linux 네트워크 규칙과 함께 사용 |
tproxy-port |
TPROXY 투명 프록시 진입점 | 대상 정보를 유지해야 하는 Linux 환경 |
LAN 수신 및 제어 인터페이스
allow-lan은 다른 기기가 현재 기기의 프록시 포트에 연결할 수 있는지 제어합니다. false로 설정하면 로컬 전용으로 사용하기에 적합합니다. true로 설정한 뒤에는 bind-address와 시스템 방화벽을 함께 확인해 실제 접근 범위를 판단해야 합니다. LAN에 개방하면 같은 네트워크의 기기가 연결을 시도할 수 있으므로 제어 인터페이스와 프록시 포트를 신뢰할 수 없는 네트워크에 무조건 노출하지 마세요. 휴대폰이나 테스트 기기에 임시로 프록시를 제공해야 한다면 현재 네트워크의 성격을 확인하고 사용이 끝난 뒤 제한을 복원하세요.
external-controller는 클라이언트 화면과 커널이 통신하는 제어 주소이며, 일반적인 형식은 127.0.0.1:9090입니다. 로컬 화면에서 사용할 때는 루프백 주소에 바인딩하면 됩니다. secret은 제어 인터페이스 인증에 사용하며, 설정하면 패널 요청에 해당 값이 포함되어야 합니다. 이는 프록시 노드의 비밀번호가 아니며 프록시 프로토콜도 변경하지 않습니다. 그래픽 클라이언트가 제어 인터페이스를 자동으로 관리한다면 구독 원문을 반복해서 수정하지 않는 것이 좋습니다. 화면에서 커널 상태를 읽지 못하게 될 수 있습니다.
mixed-port: 7890
allow-lan: false
bind-address: "127.0.0.1"
mode: rule
log-level: info
ipv6: false
external-controller: "127.0.0.1:9090"
secret: "your-controller-secret"
Rule, Global 및 Direct
mode: rule은 rules를 위에서 아래로 매칭하는 일상적인 사용에 가장 흔한 모드입니다. global은 규칙 판단을 건너뛰고 트래픽을 전역 정책 그룹으로 일괄 전달합니다. 특정 노드의 사용 가능 여부를 짧게 확인할 때는 유용하지만 규칙 설정이 올바른지 판단하는 기준으로는 적합하지 않습니다. direct는 프록시 노드를 거치지 않고 직접 연결하므로 문제가 프록시 경로에서 비롯되었는지 확인할 때 사용할 수 있습니다. 많은 클라이언트가 화면에서 모드를 전환하며 런타임 설정으로 파일의 mode를 덮어쓸 수 있으므로, 문제를 해결할 때는 화면 상태와 실제 설정을 함께 확인해야 합니다.
log-level은 보통 silent, error, warning, info, debug 중에서 선택할 수 있습니다. 평소에는 info가 적절하며, 규칙 매칭·DNS 조회·연결 핸드셰이크 문제를 확인할 때는 일시적으로 debug로 바꿀 수 있습니다. 디버그 로그는 정보량이 많으므로 문제가 확인되면 일반 수준으로 되돌리세요. ipv6은 커널이 IPv6 관련 기능을 처리할지 결정하지만 최종 결과는 시스템 네트워크, DNS 응답과 노드 지원 여부에도 영향을 받습니다. 네트워크에 안정적인 IPv6가 없다면 이 필드를 끄는 것이 오류 경로를 줄일 수 있고, 완전한 IPv6 환경에서는 필요에 따라 활성화하면 됩니다.
DNS, Fake-IP 및 해석 경로
DNS 블록이 해결하는 문제
프록시 규칙은 도메인에 의존하는 경우가 많지만 애플리케이션은 연결을 설정할 때 시스템에 IP 주소만 전달할 수 있습니다. 도메인 해석이 커널 외부에서 모두 이루어지면 규칙 엔진이 원래 도메인을 잃고 IP 규칙만 처리하게 될 수 있습니다. dns.enable으로 커널 DNS 모듈을 활성화하면 도메인 조회가 규칙, 프록시 출구와 캐시와 함께 작동합니다. 단순히 시스템 DNS를 다른 주소로 바꾸는 것이 아니라 해석 과정을 트래픽 처리 흐름의 일부로 만드는 기능입니다.
nameserver는 주요 업스트림 해석기이며, default-nameserver는 주로 암호화된 DNS 서버 자체의 도메인을 해석하는 데 사용합니다. 후자에는 보통 직접 접근할 수 있는 IP 주소를 입력해 “해석기를 먼저 해석하는” 순환 의존을 피해야 합니다. fallback은 다른 해석 경로를 제공하며, 필터 조건과 함께 언제 대체 결과를 사용할지 결정합니다. 최신 mihomo 설정은 proxy-server-nameserver도 지원합니다. 이 필드는 프록시 서버 도메인을 전용으로 해석해 노드 서버 주소의 해석 경로가 일반 웹사이트 조회와 서로 간섭하지 않도록 합니다.
dns:
enable: true
listen: "127.0.0.1:1053"
ipv6: false
enhanced-mode: fake-ip
fake-ip-range: "198.18.0.1/16"
fake-ip-filter:
- "*.lan"
- "localhost.ptlogin2.qq.com"
- "+.stun.*.*"
default-nameserver:
- 1.1.1.1
- 8.8.8.8
nameserver:
- "https://1.1.1.1/dns-query"
- "https://8.8.8.8/dns-query"
proxy-server-nameserver:
- 1.1.1.1
Fake-IP 작동 방식
enhanced-mode: fake-ip를 활성화하면 커널은 애플리케이션에 예약 주소 대역의 매핑 주소를 반환하고, 이 주소에 대응하는 원래 도메인을 기록합니다. 애플리케이션이 이후 해당 주소에 연결하면 커널이 도메인을 복원해 도메인 규칙을 계속 적용할 수 있습니다. 따라서 애플리케이션이 IP 연결만 시작하더라도 DOMAIN, DOMAIN-SUFFIX와 GeoSite 계열 규칙이 정확히 매칭될 가능성이 있습니다. 기본 예약 범위는 보통 198.18.0.0/16이며, 이 주소는 벤치마크 네트워크용이므로 공용 인터넷 대상처럼 접근해서는 안 됩니다.
Fake-IP는 웹사이트가 실제로 예약 주소로 해석되었다는 뜻이 아니며, 예약 주소에 직접 연결해 공용 인터넷 연결을 테스트해서도 안 됩니다. 트래픽이 계속 현재 커널을 통과해야 작동합니다. 애플리케이션이 시스템 프록시와 TUN을 우회해 매핑 주소를 받은 뒤 네트워크로 직접 연결하면 접속에 실패합니다. 따라서 “해석 결과가 198.18로 시작한다”는 사실만으로는 장애의 증거가 아닙니다. 애플리케이션 트래픽이 실제로 인계되었는지를 함께 확인해야 합니다.
fake-ip-filter는 매핑에 적합하지 않은 도메인을 제외하는 데 사용합니다. LAN 기기 검색, 프린터, 게임 연결, STUN, 시간 동기화와 실제 주소가 필요한 일부 서비스는 실제 해석 결과를 요구할 수 있습니다. 인터넷에서 지나치게 큰 목록을 복사해 장기간 그대로 사용하는 것은 좋지 않습니다. 제외 범위가 너무 넓으면 도메인 복원 기능이 약해지기 때문입니다. 최소 설정에서 시작하고, 명확한 호환성 문제가 생겼을 때 해당 도메인을 추가하면서 이유를 기록하는 편이 안전합니다.
Redir-Host 및 DNS 누출 점검
redir-host는 실제 IP를 반환한 뒤 스니핑, 매핑 또는 기존 해석 정보를 통해 도메인과 연결하려고 합니다. Fake-IP와 호환되지 않는 일부 환경에서는 더 직관적이지만 도메인 규칙의 안정성이 요청 경로에 더 크게 의존합니다. 두 모드 중 어느 하나가 환경과 무관하게 항상 우월한 것은 아닙니다. 데스크톱에서 TUN을 사용하고 도메인 규칙을 완전히 적용해야 한다면 보통 Fake-IP부터 시도합니다. 라우터, 특수한 LAN 서비스 또는 명확한 매핑 호환 문제가 있을 때 Redir-Host를 검토하세요.
DNS 문제는 요청 경로를 따라 단계별로 확인해야 합니다. 시스템 요청이 커널의 수신 포트로 들어오는지, 커널이 어떤 업스트림을 사용하는지, 업스트림 연결이 직접 연결인지 프록시인지, 응답이 캐시되었는지, 최종 연결이 어떤 규칙에 매칭되었는지를 점검하세요. nameserver만 바꾼다고 모든 문제가 해결되지는 않습니다. 브라우저가 별도의 보안 DNS를 사용할 수도 있고 시스템이 이전 결과를 캐시할 수도 있습니다. 설정을 바꾼 뒤 커널을 다시 로드하고 필요하면 시스템과 브라우저 캐시를 비우세요.
검사 결과 DNS 출구가 예상과 다르면 먼저 브라우저의 독립 DNS 설정을 확인한 다음 nameserver-policy, 대체 해석기와 규칙 모드를 점검하세요. 자세한 방법은 Clash DNS 누출 검사 및 방지 설정 실전 가이드를 참고할 수 있습니다. “해석기 위치”와 “연결 출구”를 혼동하지 마세요. DNS 조회에 응답한 업스트림과 웹사이트 연결을 내보낸 노드는 서로 관련 있지만 완전히 같은 경로는 아닙니다.
프록시 노드 필드와 프로토콜별 차이
노드 정의의 공통 골격
proxies 아래의 각 항목은 사용할 수 있는 하나의 출구를 나타냅니다. 모든 노드에는 최소한 고유한 name, 프로토콜 type, 서버 server와 포트 port가 필요하며 나머지 필드는 프로토콜에 따라 달라집니다. 노드 이름은 화면 표시뿐 아니라 정책 그룹에서 문자열로 참조하는 데도 사용되므로 이름을 바꾸면 모든 proxy-groups도 함께 갱신해야 합니다. 이름은 대소문자를 구분하며 앞뒤의 불필요한 공백도 참조 실패를 일으킬 수 있습니다.
server에는 IP 주소나 도메인을 사용할 수 있습니다. 도메인을 사용하면 노드 서버 자체의 해석이 먼저 성공해야 이후 연결을 수립할 수 있으며, 이것이 proxy-server-nameserver가 유용한 이유입니다. 포트는 숫자로 작성하고 인증 정보는 보통 문자열로 작성합니다. 예시 설정의 주소와 인증 정보는 구조 설명용일 뿐이므로 실제 사용 시에는 구독 또는 서비스 제공자가 전달한 매개변수를 기준으로 하세요. 프로토콜 이름만 보고 암호화 방식, 전송 계층이나 서버 이름을 추측하지 마세요.
Shadowsocks, Trojan 및 VLESS 예시
proxies:
- name: "SS 예시"
type: ss
server: 192.0.2.10
port: 443
cipher: aes-128-gcm
password: "your-password"
udp: true
- name: "Trojan TLS 예시"
type: trojan
server: 192.0.2.20
port: 443
password: "your-password"
sni: "edge.example.net"
skip-cert-verify: false
udp: true
- name: "VLESS WS 예시"
type: vless
server: 192.0.2.30
port: 443
uuid: "11111111-2222-3333-4444-555555555555"
network: ws
tls: true
servername: "edge.example.net"
ws-opts:
path: "/proxy"
headers:
Host: "edge.example.net"
Shadowsocks의 핵심 필드는 cipher와 password이며 서버 측 설정과 반드시 일치해야 합니다. Trojan은 보통 TLS에서 실행되고 sni는 핸드셰이크의 서버 이름으로 사용됩니다. VLESS는 TLS, Reality, WebSocket, gRPC와 일반 TCP 등 조합이 더 다양합니다. 설정에 network: ws를 사용했다면 ws-opts의 경로와 Host도 서버 측 설정과 일치해야 합니다. 전송 계층을 잘못 입력하면 서버 포트와 TCP 연결은 성립해도 프로토콜 핸드셰이크는 실패할 수 있습니다.
skip-cert-verify: true는 인증서 검사를 건너뛰는 설정이며 범용 해결책처럼 사용해서는 안 됩니다. 인증서 오류는 기기 시간 오류, 서버 이름 불일치, 인증서 체인 문제 또는 중간 네트워크 간섭 때문에 발생할 수 있습니다. 먼저 sni, servername과 시스템 시간을 확인한 뒤 테스트 목적상 정말 필요한지 판단하세요. 실제 운영에서는 인증서 검사를 유지해야 설정 오류를 더 정확히 드러낼 수 있습니다.
UDP, 네트워크 인터페이스 및 체인 프록시
udp: true는 노드가 커널의 UDP 전달 시도를 허용한다는 뜻이지만 실제 사용 가능 여부는 프로토콜, 서버와 네트워크 환경에 따라 달라집니다. 이 필드를 활성화했다고 모든 UDP 애플리케이션이 자동으로 작동하는 것은 아닙니다. 애플리케이션 트래픽도 TUN 또는 투명 프록시에 의해 올바르게 인계되어야 합니다. 게임, 음성 통화와 QUIC에 문제가 생기면 먼저 로그로 UDP 세션이 커널에 들어왔는지 확인한 다음 노드의 지원 여부를 점검하세요.
interface-name은 출구에서 사용할 시스템 네트워크 인터페이스를 지정할 수 있어 다중 NIC, 전화 접속 또는 라우터 환경에 적합합니다. 일반적인 데스크톱 사용자는 보통 설정할 필요가 없습니다. 잘못된 인터페이스 이름은 모든 연결을 존재하지 않거나 접근할 수 없는 네트워크 카드로 보낼 수 있습니다. routing-mark는 주로 Linux 정책 라우팅에 사용되며 다른 설정에서 그대로 복사하는 것도 적절하지 않습니다.
mihomo는 dialer-proxy 등의 기능을 통해 한 노드가 다른 정책을 거쳐 하위 연결을 수립하도록 구성할 수 있으며, 특정 체인 출구에 사용할 수 있습니다. 체인이 길어질수록 DNS, 핸드셰이크와 문제 위치 파악이 복잡해집니다. 먼저 각 구간이 단독으로 작동하는지 확인한 뒤 체인을 조합하세요. 기본 노드가 테스트를 통과하기 전에 체인 프록시, 특수 전송과 인터페이스 바인딩을 동시에 추가하지 마세요.
구독에서 가져온 노드를 수정하는 방법
구독을 갱신하면 보통 노드 목록 전체가 교체됩니다. 구독으로 생성된 proxies를 직접 편집하면 다음 새로고침 때 변경 사항이 사라질 수 있습니다. SNI를 고정하거나 특정 노드를 제외하거나 UDP를 조정해야 한다면 클라이언트의 오버라이드, 스크립트 또는 노드 변환 기능을 우선 사용하세요. Clash Plus, Clash Verge Rev, FlClash와 Clash Nyanpasu는 오버라이드 메뉴 구성이 서로 다르지만 원칙은 같습니다. 원래 구독은 데이터 소스로 보존하고 로컬 변경 사항은 별도 계층에 둡니다.
정책 그룹 유형, 참조 관계와 선택 로직
Select, URL-Test, Fallback 및 Load-Balance
정책 그룹은 규칙과 노드 사이에서 트래픽을 조정하는 계층입니다. select는 사용자가 노드나 하위 정책 그룹을 직접 선택하는 방식으로, “노드 선택”, “스트리밍”, “다운로드”처럼 출구를 명확히 제어해야 할 때 적합합니다. url-test는 테스트 결과에 따라 조건을 충족하는 노드를 자동으로 선택하므로 사용 가능한 연결로 자동 전환하려는 환경에 적합합니다. fallback은 목록 순서대로 사용 가능한 첫 노드를 선택해 테스트 값보다 우선순위를 중시합니다. load-balance는 정책에 따라 여러 노드로 연결을 분산하며, 세션 일관성의 영향을 이해하는 사용자에게 적합합니다.
자동 테스트에는 보통 url과 interval이 필요합니다. 테스트 주소는 안정적이고 응답이 가벼우며 대상 네트워크 경로를 반영할 수 있어야 합니다. 간격이 너무 짧으면 불필요한 요청이 늘고, 너무 길면 노드 변화를 발견하는 데 늦어집니다. tolerance는 테스트 값이 비슷할 때 잦은 전환을 줄이는 기능이며, 단일 테스트 결과를 실제 다운로드 속도로 해석해서는 안 됩니다. 노드 측정 속도, 웹페이지 첫 응답, 지속 처리량과 피크 시간대 안정성은 서로 다른 지표입니다.
proxy-groups:
- name: "노드 선택"
type: select
proxies:
- "자동 선택"
- "장애 조치"
- "SS 예시"
- "Trojan TLS 예시"
- DIRECT
- name: "자동 선택"
type: url-test
url: "https://www.gstatic.com/generate_204"
interval: 600
tolerance: 80
proxies:
- "SS 예시"
- "Trojan TLS 예시"
- name: "장애 조치"
type: fallback
url: "https://www.gstatic.com/generate_204"
interval: 600
proxies:
- "Trojan TLS 예시"
- "SS 예시"
정책 그룹은 다른 정책 그룹을 참조할 수 있습니다
그룹의 proxies에는 노드뿐 아니라 다른 정책 그룹과 내장 출구 DIRECT, REJECT도 작성할 수 있습니다. 이를 활용하면 계층 구조를 만들 수 있습니다. 하위 그룹은 노드 상태 점검을 담당하고, 중간 그룹은 서비스별 선택을 담당하며, 최상위 그룹은 규칙의 대상으로 사용합니다. 예를 들어 “스트리밍” 그룹에 “노드 선택”과 몇 개의 지역 그룹을 포함하고, 지역 그룹 내부에서 자동 테스트를 사용할 수 있습니다.
참조 관계에서 순환이 발생하지 않도록 해야 합니다. A 그룹이 B를 포함하고 B가 다시 A를 포함하면 커널은 최종 출구를 결정할 수 없습니다. 정책 그룹 이름과 노드 이름도 혼동하지 않아야 합니다. 대규모 설정에서는 그룹 이름에 일관된 접두사를 사용할 수 있지만 기호를 지나치게 쌓을 필요는 없습니다. 장식 문자보다 의미가 분명한 서비스 이름이 로그 검색에 유리합니다. 규칙 대상은 정책 그룹 이름과 완전히 일치해야 하며, 그렇지 않으면 로드 단계에서 정책을 찾을 수 없다는 오류가 발생합니다.
Provider로 노드 채우기
노드가 proxy-providers에서 제공되는 경우 정책 그룹은 use로 Provider를 참조할 수 있으므로 모든 노드 이름을 proxies에 직접 작성할 필요가 없습니다. 원격 노드 목록이 갱신되면 자동 테스트 그룹도 새 노드를 받습니다. filter와 exclude-filter로 이름을 필터링할 수 있지만 필터는 정규 표현식과 구독의 노드 이름에 의존하므로 제공자가 이름을 바꾸면 결과가 비어 있을 수 있습니다. 필터 그룹을 점검할 방법을 마련하고 지역 키워드가 영원히 유지된다고 가정하지 마세요.
proxy-providers:
main-subscription:
type: http
url: "https://config.example.net/subscription.yaml"
path: "./providers/main.yaml"
interval: 3600
health-check:
enable: true
url: "https://www.gstatic.com/generate_204"
interval: 600
proxy-groups:
- name: "구독 노드"
type: select
use:
- main-subscription
- name: "자동 테스트"
type: url-test
use:
- main-subscription
url: "https://www.gstatic.com/generate_204"
interval: 600
유지 관리가 쉬운 그룹 계층 설계
정책 그룹은 많을수록 세밀해지는 것이 아닙니다. 계층이 하나 늘어날 때마다 사용자가 이해해야 할 선택 상태와 문제 해결 분기가 증가합니다. 기본 설정은 총괄 진입 그룹 하나, 자동 선택 그룹 하나와 명확한 요구가 있는 소수의 서비스 그룹으로 세 계층을 유지할 수 있습니다. 규칙은 기본적으로 총괄 진입 그룹을 가리키고, 별도 출구가 꼭 필요한 서비스만 서비스 그룹으로 만드세요. 이렇게 하면 수동 제어를 유지하면서도 구독을 가져올 때 의미가 비슷한 그룹 수십 개를 마주하는 일을 피할 수 있습니다.
“규칙이 매칭되었지만 예상한 노드를 사용하지 않는” 문제를 해결할 때는 로그의 규칙 대상부터 확인하고 정책 그룹을 단계별로 펼쳐 보세요. 먼저 규칙이 어느 그룹으로 전달되었는지, 다음으로 해당 그룹이 현재 어떤 하위 그룹을 선택했는지, 마지막으로 실제 하위 노드가 무엇인지 확인합니다. 화면의 최상위 그룹 이름만 보면 하위 자동 선택을 놓치기 쉽습니다. 노드를 바꿔도 이미 연결된 세션이 즉시 이동하지 않을 수 있으므로 검증할 때는 연결을 새로 만들거나 관련 애플리케이션 세션을 종료하세요.
규칙 문법, 매칭 순서와 기본 처리 전략
규칙은 위에서 아래로 처음 매칭된 항목을 사용합니다
rules는 순서가 있는 목록입니다. 커널은 첫 항목부터 확인하고 처음 매칭되는 항목을 찾으면 검색을 중지한 뒤 규칙 끝에 지정된 정책으로 연결을 전달합니다. 따라서 규칙은 개수보다 순서가 중요합니다. 정확한 도메인, 특수 서비스와 거부할 항목은 보통 앞에 배치하고, 범위가 넓은 도메인 접미사·IP 대역·지역 규칙은 뒤에 둡니다. 마지막에는 MATCH로 매칭되지 않은 연결을 처리합니다.
MATCH를 중간에 배치하면 그 뒤의 모든 규칙이 작동하지 않습니다. 범위가 지나치게 넓은 DOMAIN-SUFFIX를 정확한 예외보다 앞에 두면 다른 정책을 사용해야 할 하위 도메인까지 먼저 가로챌 수 있습니다. 규칙을 수정할 때는 해당 항목이 올바른지만 보지 말고 앞에 더 넓은 매칭이 있는지도 확인하세요. 로그에 표시되는 규칙 유형과 정책 이름이 실제 매칭 위치를 판단하는 직접적인 근거입니다.
rules:
- DOMAIN,api.example.com,노드 선택
- DOMAIN-SUFFIX,example.net,노드 선택
- DOMAIN-KEYWORD,stream,스트리밍
- IP-CIDR,192.168.0.0/16,DIRECT,no-resolve
- IP-CIDR,10.0.0.0/8,DIRECT,no-resolve
- GEOIP,LAN,DIRECT
- GEOSITE,private,DIRECT
- GEOSITE,category-ads-all,REJECT
- MATCH,노드 선택
도메인 규칙의 차이
DOMAIN은 api.example.com처럼 완전한 도메인만 매칭하며 다른 하위 도메인을 자동으로 포함하지 않습니다. DOMAIN-SUFFIX,example.com은 루트 도메인과 하위 도메인을 모두 매칭하므로 사이트 전체에 같은 정책을 적용할 때 적합합니다. DOMAIN-KEYWORD는 도메인에 해당 문자열이 포함되기만 해도 매칭될 수 있어 범위가 넓으며, 짧은 키워드는 관련 없는 사이트까지 잘못 매칭할 수 있습니다. 완전한 도메인이나 접미사를 사용할 수 있다면 키워드 규칙을 우선하지 마세요.
GEOSITE는 분류 데이터베이스의 도메인 집합을 참조하며 규모가 큰 서비스 범주를 관리하는 데 적합합니다. 매칭 결과는 로컬 GeoSite 데이터의 존재 여부, 규칙 세트 이름의 정확성 및 데이터 업데이트 상태에 좌우됩니다. 데이터베이스가 오래되면 새 도메인이 매칭되지 않을 수 있고, 분류 이름을 잘못 입력하면 설정 로드나 규칙 초기화 단계에서 오류가 드러납니다. 관련 관리 방법은 GeoIP 및 GeoSite 데이터베이스 업데이트 가이드를 참고하세요.
IP 규칙과 no-resolve
IP-CIDR은 IPv4 대역을, IP-CIDR6은 IPv6 대역을 매칭합니다. 규칙 끝의 no-resolve는 현재 연결에 대상 IP가 없을 때 이 규칙을 매칭하기 위해 별도의 DNS 조회를 실행하지 않는다는 뜻입니다. LAN 대역과 이미 알고 있는 IP 집합에 자주 사용하면 불필요한 해석을 줄이고 도메인 규칙 이후 조회가 다시 발생하는 것도 막을 수 있습니다. 다만 특정 IP 규칙이 도메인 해석 결과에 의존한다면 이 매개변수를 무조건 추가해서는 안 됩니다.
GEOIP는 대상 IP가 속한 지리 데이터베이스 분류에 따라 연결을 처리합니다. IP 계층에서 작동하므로 도메인 분류인 GEOSITE와는 다릅니다. 하나의 도메인이 전 세계에 분산된 주소를 사용할 수 있고 해석 결과도 네트워크 위치에 따라 달라질 수 있으므로 GeoIP가 서비스의 사업 지역을 항상 정확히 표현하는 것은 아닙니다. 웹사이트나 서비스 기준으로 분기하려면 도메인 집합을 우선 사용하고, 실제 대상 네트워크 대역 기준으로 처리해야 할 때 IP 규칙을 사용하세요.
DIRECT, REJECT 및 MATCH
DIRECT는 연결을 로컬 네트워크에서 직접 내보내며 LAN, 시스템 서비스 또는 로컬 출구가 명확히 필요한 대상에 적합합니다. REJECT는 연결을 거부하며 확인된 광고나 추적 도메인에 자주 사용합니다. 거부 범위가 너무 넓으면 페이지 리소스 누락, 로그인 실패 또는 애플리케이션의 반복 재시도가 발생할 수 있으므로 로그를 보며 항목별로 조정해야 합니다. MATCH는 최종 기본 처리로 도메인이나 IP 조건을 판단하지 않으며, 앞에서 매칭되지 않은 모든 연결을 해당 정책으로 보냅니다.
이해하기 쉬운 기본 구성은 다음과 같습니다. LAN과 사설 도메인은 직접 연결하고, 명확한 거부 대상은 필요에 따라 허용하거나 거부하며, 특정 서비스는 서비스 그룹으로 보내고 나머지 트래픽은 총괄 진입 그룹으로 전달합니다. 출처가 불분명한 규칙을 대량으로 바로 병합한 뒤 한 번에 작동하기를 기대하지 마세요. 규칙끼리 서로 덮어쓸 수 있고 목록마다 같은 도메인에 반대 정책을 지정할 수도 있습니다. 새 규칙 세트를 추가한 뒤에는 대표 도메인 몇 개를 선택해 로그에서 매칭 순서를 확인하세요.
프록시 Provider, 규칙 세트 및 외부 파일
Provider가 해결하는 유지 관리 문제
노드와 규칙의 수가 계속 늘어나면 모든 내용을 하나의 YAML에 넣어 관리하기 어려워집니다. proxy-providers는 노드 집합을 불러오고, rule-providers는 규칙 집합을 불러옵니다. 기본 설정에는 출처, 캐시 경로, 업데이트 간격과 참조 관계만 남기므로 원격 내용이 바뀌어도 기본 파일 전체를 다시 작성할 필요가 없습니다. Provider는 구독과 공개 규칙 세트에 적합하지만 다운로드, 캐시와 형식이라는 세 가지 의존성도 추가합니다. 문제를 해결할 때는 기본 설정 파싱 실패와 원격 파일 업데이트 실패를 구분해야 합니다.
type: http는 네트워크 주소에서 가져온다는 뜻이고, type: file은 로컬 파일을 읽는다는 뜻입니다. path는 캐시 또는 파일 위치이며 보통 실행 디렉터리를 기준으로 한 상대 경로를 사용합니다. 클라이언트마다 설정 디렉터리가 다르므로 다른 기기의 절대 경로를 그대로 복사하지 마세요. interval은 초 단위로 업데이트 간격을 제어합니다. 너무 짧으면 요청이 잦아지고 너무 길면 변경 사항을 받는 시점이 늦어집니다. 클라이언트에서 구독을 수동으로 갱신할 때 Provider 새로고침이 함께 실행될 수도 있습니다.
rule-providers:
private-domain:
type: http
behavior: domain
format: yaml
path: "./rules/private-domain.yaml"
url: "https://rules.example.net/private-domain.yaml"
interval: 86400
private-network:
type: http
behavior: ipcidr
format: yaml
path: "./rules/private-network.yaml"
url: "https://rules.example.net/private-network.yaml"
interval: 86400
rules:
- RULE-SET,private-domain,DIRECT
- RULE-SET,private-network,DIRECT,no-resolve
- MATCH,노드 선택
behavior와 파일 내용은 서로 일치해야 합니다
behavior: domain은 규칙 세트가 주로 도메인 항목으로 구성된다는 뜻으로, 완전한 도메인·접미사 또는 해당 도메인 규칙 형식을 사용할 수 있습니다. ipcidr은 IP 대역을, classical은 더 완전한 기존 규칙 문법을 규칙 세트에 보존할 수 있음을 의미합니다. behavior와 실제 내용이 일치하지 않으면 규칙을 파싱하지 못하거나 예상대로 매칭하지 못할 수 있습니다. 유형은 파일명만 보고 판단하지 말고 규칙 출처가 제공하는 형식에 맞춰 선택하세요.
일반적인 YAML 규칙 세트는 항목을 payload 아래에 배치합니다. domain 유형의 단순 항목에는 도메인 접미사 형식을 사용할 수 있고, classical 유형에는 유형이 포함된 완전한 규칙을 작성할 수 있습니다. 기본 설정은 RULE-SET으로 정책을 지정하므로 Provider 파일은 보통 매칭 내용만 설명하고 각 줄에 정책 그룹을 반복하지 않습니다. 규칙 출처에 이미 정책 필드가 포함되어 있다면 형식상 classical이 필요한지 확인하세요.
payload:
- "example.com"
- "+.example.net"
- "service.example.org"
업데이트, 캐시 및 실패 시 대체 처리
원격 규칙 업데이트에 실패하면 커널은 보통 기존 캐시를 계속 사용하려고 합니다. 하지만 최초 로드 시 로컬 캐시가 없으면 해당 Provider를 사용할 수 없을 수 있습니다. 로그의 HTTP 상태, 시간 초과, 파일 권한과 형식 오류는 각각 다른 문제를 가리킵니다. 먼저 브라우저나 명령줄에서 주소에 접근할 수 있는지 확인하고, 클라이언트가 path가 가리키는 디렉터리에 쓸 수 있는지 점검한 다음, 다운로드한 내용이 로그인 페이지나 오류 페이지가 아닌 예상한 YAML 또는 MRS 형식인지 확인하세요.
캐시 파일을 여러 실행 인스턴스가 동시에 기록해서는 안 됩니다. 같은 기기에서 두 클라이언트를 실행하고 동일한 설정 디렉터리를 사용하면 포트 충돌이 발생하거나 Provider 파일을 서로 차지하려 할 수 있습니다. 설정을 옮길 때는 필요한 로컬 규칙 파일도 함께 이전하거나 새 환경에서 원격 출처에 접근할 수 있도록 해야 합니다. 기본 YAML만 복사하고 로컬 Provider를 빠뜨리면 기본 설정에는 참조가 남아 있지만 실제 파일은 없는 상태가 됩니다.
규칙 세트 순서는 여전히 기본 설정이 결정합니다
Provider는 많은 항목을 하나의 참조로 묶을 뿐 위에서 아래로 처음 매칭되는 원칙을 바꾸지 않습니다. 두 규칙 세트의 범위가 겹치면 앞에 작성된 RULE-SET이 먼저 매칭 기회를 얻습니다. 대규모 규칙 세트를 모든 정확한 규칙보다 무조건 앞에 두면 로컬 예외가 가려질 수 있습니다. 공개 규칙 세트를 덮어써야 한다면 해당 RULE-SET 앞에 소수의 정확한 규칙을 배치하세요.
규칙 출처가 많을수록 충돌 검토가 중요합니다. 각 규칙 세트의 용도, behavior, 업데이트 출처와 대상 정책을 기록하고 오랫동안 사용하지 않았거나 기능이 중복되는 세트는 삭제하는 것이 좋습니다. 서비스 분기 이상이 발생하면 수만 개의 원격 규칙을 무작정 검색하기보다 최근 추가한 Provider를 잠시 비활성화하는 편이 효율적입니다. 데이터베이스와 규칙 세트를 업데이트한 뒤에는 다운로드 상태가 성공으로 표시되는지만 보지 말고 주요 도메인 몇 개를 다시 검증하세요.
오버라이드, 병합, 구독 업데이트 및 시스템 문제 해결
로컬 수정을 오버라이드 계층에 두는 이유
구독 설정의 수명 주기는 보통 “원격 생성, 클라이언트 다운로드, 로컬 로드, 정기 새로고침”으로 이어집니다. 다운로드한 원본 파일을 직접 편집하면 다음 새로고침 때 교체되기 쉽습니다. 오버라이드 계층은 고정 포트, DNS 조정, 소수의 규칙 추가와 정책 그룹의 기본 선택 변경 같은 로컬 차이를 저장하는 데 사용합니다. 이렇게 하면 구독은 노드와 기본 구조를 제공하고 로컬 계층은 기기별 설정을 담당해 역할이 명확해집니다.
클라이언트마다 오버라이드를 부르는 이름과 지원 기능이 완전히 같지는 않습니다. 오버라이드, 확장, 병합, 스크립트 또는 사전 처리로 표시될 수 있습니다. Clash Plus, Clash Verge Rev, FlClash, Clash Nyanpasu 등의 그래픽 클라이언트는 대체로 설정 관리 메뉴를 제공하지만 지원하는 병합 의미는 현재 클라이언트의 화면과 문서를 기준으로 확인해야 합니다. 단순한 키-값 덮어쓰기는 이해하기 쉽지만 배열 병합은 특히 주의해야 합니다. rules, proxies와 proxy-groups는 순서나 참조 관계가 있는 목록이기 때문입니다.
맵 덮어쓰기와 배열 병합의 차이
맵 필드는 보통 키 단위로 덮어씁니다. 예를 들어 기본 설정의 log-level: info를 오버라이드 계층에서 debug로 설정하면 최종 값은 하나만 남습니다. 중첩된 맵은 깊게 병합될 수도 있고 블록 전체가 교체될 수도 있습니다. 오버라이드 시스템이 전체 dns 블록을 교체한다면 ipv6: false만 작성했을 때 기존 nameserver가 사라질 수 있습니다. 오버라이드를 적용한 뒤에는 오버라이드 조각만 읽지 말고 클라이언트가 생성한 최종 설정을 확인하세요.
배열은 더 복잡합니다. 규칙을 추가할 때는 삽입 위치를 고려해야 합니다. 먼저 매칭되어야 하는 로컬 예외는 공개 규칙 세트보다 앞에 두고, 일반 기본 규칙은 MATCH 뒤에 추가해서는 안 됩니다. 정책 그룹 배열을 통째로 교체하면 원래 구독의 그룹이 모두 사라질 수 있고, 단순히 추가하면 이름이 중복될 수 있습니다. 노드 배열을 이름으로 중복 제거할지 위치 기준으로 추가할지도 구현에 따라 다릅니다. 병합 동작을 확신할 수 없다면 먼저 최소 테스트 설정으로 확인한 뒤 기본 구독에 적용하세요.
# 기본 설정
mode: rule
log-level: info
rules:
- GEOSITE,private,DIRECT
- MATCH,노드 선택
# 로컬 대상
# 1. 기존 사설 도메인 규칙 유지
# 2. MATCH 앞에 정확한 예외 추가
# 3. 로그 수준만 일시적으로 debug로 변경
위의 로컬 대상은 “파일 끝에 규칙 하나를 추가하는” 방식만으로는 구현할 수 없습니다. 기존 MATCH가 먼저 기본 처리하기 때문입니다. 올바른 방법은 클라이언트가 지원하는 규칙 앞부분에 예외를 추가하거나, 병합된 전체 규칙 배열을 생성하는 것입니다. 클라이언트가 rules 블록 전체 교체만 지원한다면 보존하려는 기존 규칙도 오버라이드 결과에 함께 작성해야 합니다.
반복 가능한 문제 해결 절차
첫 단계는 설정이 정상적으로 파싱되었는지 확인하는 것입니다. YAML 줄 번호, 알 수 없는 필드, 중복 이름과 존재하지 않는 참조 오류에 주의하세요. 두 번째는 커널이 시작되어 예상 포트에서 수신 중인지 확인하는 단계입니다. 시작 직후 종료된다면 포트 충돌, 설정 디렉터리 권한과 제어 인터페이스 충돌을 먼저 확인하세요. 세 번째는 애플리케이션 트래픽이 커널에 들어오는지 확인하는 것입니다. 로그에서 대상 도메인이나 연결이 보이는지 확인하세요. 연결이 보이지 않으면 노드를 바꾸기보다 시스템 프록시, TUN과 애플리케이션 자체 프록시를 점검해야 합니다.
네 번째는 규칙 매칭을 확인하는 단계입니다. 로그에 도메인이나 IP가 어떤 규칙 유형에 매칭되었고 어느 정책 그룹으로 들어갔는지 표시되어야 합니다. 정책이 잘못되었다면 규칙 순서와 Provider 내용을 확인하고, 정책이 올바르다면 정책 그룹을 펼쳐 실제 하위 노드를 확인하세요. 다섯 번째는 DNS를 점검합니다. 도메인 해석 실패, Fake-IP가 인계되지 않는 문제와 브라우저의 독립 DNS 사용은 모두 웹페이지가 열리지 않는 현상으로 나타날 수 있습니다. 여섯 번째는 노드 연결 단계입니다. 시간 초과는 보통 경로에 접근할 수 없다는 뜻이고, 연결 거부는 포트가 수신 중이지 않은 경우가 많습니다. TLS 오류는 서버 이름과 시간을 확인해야 하며, 인증 오류는 인증 정보를 확인해야 합니다.
각 단계를 마칠 때마다 명확한 결론을 남겨야 합니다. 예를 들어 “설정 파싱 성공, 7890 포트 수신 중, 브라우저 연결이 커널에 들어옴, 노드 선택 그룹에 매칭되었지만 TLS 핸드셰이크 실패”처럼 기록할 수 있습니다. 이런 기록은 모든 설정 블록을 번갈아 수정하지 않고 문제 범위를 노드 필드로 좁혀 줍니다. 시작 직후 종료되는 문제는 Clash 클라이언트 시작 직후 종료 문제 해결 체크리스트를 참고할 수 있으며, 화면 메뉴가 익숙하지 않다면 프록시·설정·로그 세 가지 주요 화면 해설을 읽어 보세요.
구독 업데이트 후 회귀 점검
구독을 새로고침하면 노드 이름, 정책 그룹, 규칙 대상과 Provider 주소가 바뀔 수 있습니다. 새로고침 후에는 최소한 네 가지를 확인하세요. 기존 로컬 오버라이드가 계속 활성화되어 있는지, 규칙이 참조하는 정책 그룹이 여전히 존재하는지, 자동 선택 그룹에 사용 가능한 노드가 있는지, DNS와 포트가 구독 필드에 의해 의도치 않게 덮어쓰이지 않았는지 확인합니다. 특정 정책 그룹이 갑자기 비었다면 필터 정규 표현식이 새 노드 이름에도 여전히 매칭되는지 점검하세요.
장기적으로 관리할 때는 구독 내부 구조에 대한 의존을 최대한 줄이세요. 예를 들어 규칙이 안정적인 로컬 총괄 진입 그룹 하나를 가리키고 그 그룹이 구독 노드를 참조하도록 하면, 수십 개의 규칙이 구체적인 노드 이름을 직접 작성하는 것보다 업데이트에 강합니다. 노드 변경은 구독이 처리하고 정책 의도는 로컬 설정이 표현하도록 분리하면 클라이언트 이전도 쉬워집니다.
최종 설정 자체 점검 목록
- YAML이 공백으로 들여쓰기되어 있고 최상위 키와 목록 계층이 명확하며 탭 문자나 전각 문장 부호가 없습니다.
- 수신 포트가 충돌하지 않고 시스템 프록시 또는 TUN이 실제 실행 중인 커널을 가리킵니다.
- 각 정책 그룹이 참조하는 노드, 하위 그룹과 Provider가 모두 존재하며 그룹 간 순환 참조가 없습니다.
- 규칙이 정확한 항목부터 넓은 항목 순서로 배치되고 모든 기본 처리 규칙이 마지막에 있으며 규칙 대상 이름이 정확합니다.
- DNS 업스트림에 접근할 수 있고 Fake-IP 필터 범위가 필요한 수준으로 유지되며 브라우저의 독립 DNS도 점검 대상에 포함되어 있습니다.
- 오버라이드를 적용한 최종 설정에도 원래 구독에 필요한 필드가 남아 있고 구독을 새로고침한 뒤 회귀 검증을 완료했습니다.
필드 확인을 마쳤다면 입문 가이드로 돌아가 가져오기, 정책 선택, 연결과 검증 순서에 따라 진행하세요. 클라이언트를 바꾸려면 클라이언트 다운로드 페이지로 이동하면 됩니다. 일반적인 현상과 간단한 답변은 자주 묻는 질문에 모아 두었으며, 오류 단계까지 확인한 뒤 해당 해결 방법을 빠르게 찾기에 적합합니다.