도해 B-01매뉴얼 안내와 읽는 순서
이 사이트의 콘텐츠는 두 갈래로 나뉩니다. 입문 가이드는 빠르게 시작하는 메인 흐름으로, "클라이언트 설치 → 구독 가져오기 → 모드 선택 → 연결 확인" 순서를 따라가면 바로 정상적으로 사용할 수 있으며, 설정 파일을 읽을 필요가 전혀 없습니다. 이 페이지는 또 다른 갈래로, config.yaml을 직접 열어 읽거나 수정해야 하는 상황을 위한 참조 매뉴얼입니다. 예를 들어 특정 규칙이 왜 적용되지 않는지 확인하거나, 구독 외에 몇 가지 커스텀 분기 규칙을 추가하거나, 처음부터 최소 설정을 직접 작성해야 할 때입니다. 두 갈래는 서로 연결되어 있습니다: Clash를 처음 접하는 분은 먼저 가이드 페이지의 절차를 완료하고, 설정이 정상 동작한 뒤 이 페이지로 돌아와 필드 번호별로 참조하세요.
필드 기준을 먼저 짚어야 합니다. 현재 주요 GUI 클라이언트—Clash Plus, Clash Verge Rev, FlClash 등, 전체 목록은 설치 페이지와 클라이언트 비교 페이지 참고—는 모두 내부적으로 mihomo 커널 또는 호환 커널을 사용하며, 동일한 YAML 설정 형식을 읽습니다. 이 페이지는 각 커널이 공통으로 지원하는 필드를 위주로 다루며, 최신 커널에서만 지원하는 확장 기능은 해당 절에서 별도로 표시합니다. 이를 구식 커널에 그대로 적용하면 "필드를 인식할 수 없음" 오류가 발생할 수 있으니 주의하세요.
읽는 순서 추천: 분기 규칙을 바꾸려면 도해 B-07과 B-08을 바로 참고하세요. 구독을 갱신할 때마다 수동 수정 내용이 사라진다면 도해 B-09를 참고하세요. 특정 노드에 연결되지 않으면 먼저 노드 타임아웃 점검 글을 확인한 뒤 설정 변경을 고려하세요. 인터넷 접속이 전혀 안 될 때는 FAQ 페이지와 가이드 페이지에서 클라이언트와 시스템 프록시 상태를 먼저 확인하고, 문제가 있는 상태에서 설정 파일을 함부로 수정하지 마세요.
example.com, your-password 등). 필드 구조를 보여주기 위한 것일 뿐 실제로 연결되지 않습니다. 실제 값은 구독이나 직접 구축한 서버에서 제공하는 값을 사용하세요.
도해 B-02YAML 구조 개요
세 가지 필수 작성 규칙
config.yaml은 여러 최상위 키로 구성된 표준 YAML 문서이며, 각 최상위 키는 하나의 하위 시스템을 담당합니다. YAML 작성에는 세 가지 필수 규칙이 있고, "설정 로드 실패"의 대부분은 이 중 하나를 위반해서 생깁니다. 첫째, 들여쓰기는 공백만 사용하고 보통 2칸씩 한 단계로 하며 Tab 문자는 금지입니다. 둘째, "키: 값" 형식에서 콜론 뒤에 반드시 공백이 있어야 합니다. port:7890처럼 쓰면 키-값이 아니라 하나의 문자열로 인식됩니다. 셋째, 목록 항목은 "- "로 시작하며 같은 계층의 하이픈은 같은 열에 정렬되어야 합니다.
문자열 인용부호도 자주 문제가 됩니다: 값에 #, 콜론, 중괄호가 포함되거나 특수 기호로 시작할 경우 반드시 인용부호로 감싸야 합니다. 그렇지 않으면 # 이후 내용이 주석으로 처리되어 잘려나갑니다. 노드 이름에 이모지, 공백, 전각 문자가 포함될 경우 항상 쌍따옴표로 감싸서 해석 모호성을 없애는 것이 좋으며, 정책 그룹에서 참조할 때도 동일한 인용부호 형태로 작성해야 합니다.
최상위 키 색인
| 최상위 키 | 타입 | 역할 | 관련 도해 |
|---|---|---|---|
port / socks-port / mixed-port | 정수 | 로컬 프록시 수신 포트 | B-03 |
allow-lan / bind-address | 불리언 / 문자열 | LAN 요청 허용 여부 및 수신 주소 | B-03 |
mode | 열거형 | 동작 모드: rule / global / direct | B-03 |
log-level | 열거형 | 로그 상세도 | B-03 |
external-controller / secret | 문자열 | 제어 인터페이스 주소와 접근 비밀번호 | B-03 |
dns | 맵 | 커널의 DNS 해석 동작 | B-04 |
tun | 맵 | 가상 네트워크 카드(TUN) 사용(클라이언트 UI 스위치로 켜는 것을 권장) | B-03 |
proxies | 배열 | 프록시 노드 정의 | B-05 |
proxy-groups | 배열 | 정책 그룹(출구 편성) | B-06 |
rules | 배열 | 분기 규칙, 위에서부터 순서대로 매칭 | B-07 |
rule-providers | 맵 | 외부 규칙셋 소스 | B-08 |
최소 구성 뼈대
아래는 구조가 완전한 최소 설정 뼈대로, 다섯 부분만 갖추면 커널이 로드할 수 있습니다. 이후 각 도해에서 항목별로 자세히 설명합니다:
mixed-port: 7890
allow-lan: false
mode: rule
log-level: info
dns:
enable: true
enhanced-mode: fake-ip
nameserver:
- https://doh.pub/dns-query
proxies:
- name: "예시 노드"
type: ss
server: example.com
port: 8388
cipher: aes-128-gcm
password: "your-password"
proxy-groups:
- name: "노드 선택"
type: select
proxies:
- "예시 노드"
- DIRECT
rules:
- GEOIP,CN,DIRECT
- MATCH,노드 선택
낯선 설정을 읽는 추천 순서: 먼저 mode와 포트 부분을 확인해 동작 방식을 파악하고, 다음으로 proxy-groups를 보며 출구 구조를 이해하고, 마지막으로 rules를 확인해 트래픽 방향을 파악하세요. proxies 부분은 보통 구독에서 자동 생성되므로 개별 노드 문제를 조사할 때만 필드 단위로 자세히 볼 필요가 있습니다.
도해 B-03공통 필드: 포트, 모드, 제어 인터페이스
포트 세 종류
port는 HTTP 프록시 포트, socks-port는 SOCKS5 포트이며, mixed-port는 한 포트에서 두 프로토콜을 동시에 처리합니다. 현재 대부분의 클라이언트는 기본적으로 mixed-port: 7890을 사용하며, 시스템 프록시, 브라우저 수동 프록시, 터미널 환경변수 모두 이 하나의 포트만 지정하면 됩니다. 세 값을 0으로 두거나 생략하면 해당 포트를 열지 않는다는 뜻입니다. 주의할 점: 포트 번호를 바꾼 뒤에는 시스템 프록시 설정도 함께 바꿔야 합니다. 그렇지 않으면 "클라이언트는 실행 중인데 트래픽이 들어오지 않는" 가짜 오류가 발생할 수 있습니다. 자세한 점검은 시스템 프록시 미작동 점검 글을 참고하세요.
LAN 공유
allow-lan: true로 설정하면 같은 LAN의 다른 기기가 이 PC를 프록시 서버로 사용할 수 있습니다. 클라이언트를 설치하기 어려운 TV, 게임기 등에 프록시 출구를 지정할 때 주로 사용하며, bind-address와 함께 사용하면 특정 네트워크 카드에서만 수신하도록 제한할 수 있습니다. 카페나 공항 같은 공용 네트워크에서는 false로 유지해야 합니다. 그렇지 않으면 같은 네트워크에 있는 누구나 이 출구를 사용할 수 있습니다.
동작 모드 mode
| 값 | 동작 | 적용 상황 |
|---|---|---|
rule | rules 항목을 순서대로 매칭해 출구 결정 | 일상적인 기본값, 중국 본토는 직결, 해외는 프록시 |
global | 모든 트래픽이 선택된 정책 그룹으로, 규칙 무시 | 노드 임시 확인, 규칙 의심 시 대조 테스트 |
direct | 모든 트래픽 직결, 프록시 미경유 | 프록시를 임시로 끄되 클라이언트는 계속 실행 |
로그와 제어 인터페이스
log-level의 값은 간단한 것부터 silent / error / warning / info / debug 순입니다. 평소에는 info면 충분합니다. 특정 규칙이 적용되는지 확인할 때는 debug로 전환하면 커널이 연결마다 매칭 결과를 출력하므로 확인 후 다시 되돌리세요. debug를 오래 켜두면 로그가 많이 쌓입니다. external-controller는 RESTful 제어 인터페이스의 수신 주소를 정의하며(주로 127.0.0.1:9090), 클라이언트의 연결 패널, 노드 전환, 지연 테스트 모두 이 인터페이스를 통해 커널 상태를 읽고 씁니다. secret은 이 인터페이스의 접근 비밀번호입니다. ipv6: false로 설정하면 커널이 IPv6 주소를 해석하거나 연결하지 않으므로, 네트워크의 IPv6 회선이 불안정할 때는 꺼두는 것이 좋습니다.
mixed-port: 7890
allow-lan: false
bind-address: "*"
mode: rule
log-level: info
ipv6: false
external-controller: 127.0.0.1:9090
secret: "xxxx"
또 하나 규모가 큰 최상위 키인 tun이 있습니다: 가상 네트워크 카드 방식으로 시스템 전체 트래픽을 가로채며, 일부 프로그램이 시스템 프록시를 읽지 않는 문제를 해결할 수 있습니다. 하위 필드는 커널 버전에 따라 차이가 크고 시스템 권한과도 관련이 있으므로, 직접 작성하지 말고 클라이언트 UI의 "TUN 모드" 스위치를 사용해 클라이언트가 올바른 필드를 생성하도록 하는 것을 권장합니다. 켜기 전 주의사항은 FAQ 페이지의 해당 항목을 참고하세요.
allow-lan과 external-controller는 모두 "외부에 노출되는" 필드입니다: 전자는 프록시 포트를 노출하고, 후자는 제어 인터페이스를 노출합니다. 다른 기기에서 접근할 필요가 명확히 없다면 수신 주소는 127.0.0.1로 유지하고, 제어 인터페이스에는 secret을 설정하세요.
도해 B-04DNS 설정: 해석 단계의 분기 기반
프록시 환경에서 왜 DNS를 별도로 설정해야 하는가
규칙 매칭은 대부분 도메인 단계에서 이루어집니다. 도메인이 커널로 들어오기 전에 로컬 네트워크에서 오염되어 잘못된 IP로 해석되면, IP 소속으로 판단하는 GEOIP 같은 규칙도 함께 오판하게 되어 "규칙은 맞게 작성했는데 트래픽이 잘못된 출구로 나가는" 현상이 발생합니다. dns 섹션의 역할은 커널이 해석 과정을 직접 담당하도록 해, 매칭에 사용되는 해석 결과를 신뢰할 수 있게 만드는 것입니다. enable: true가 이 섹션 전체가 작동하는 전제 조건입니다.
enhanced-mode의 두 가지 동작 방식
fake-ip 모드에서는 커널이 각 도메인에 예약된 대역(기본값 198.18.0.1/16) 안의 가상 주소를 반환하고, 실제 연결이 이루어질 때 도메인 기준으로 규칙을 매칭한 뒤 해석합니다. 장점은 사전 해석 단계를 줄여 지연이 낮고, 근본적으로 해석 결과가 로컬 네트워크에 의해 방해받는 것을 막을 수 있어 현재 기본 권장 방식입니다. redir-host 모드는 실제 IP를 반환해 호환성이 더 좋지만 연결마다 해석이 한 번 더 필요합니다. fake-ip를 사용할 경우, fake-ip-filter에는 실제 IP가 필요한 도메인—LAN 기기 관리 도메인, NTP 시간 동기화, 일부 게임 매칭 플랫폼 등—을 반드시 나열해야 합니다. 그렇지 않으면 이런 서비스들이 가상 주소를 받아 동작하지 않게 됩니다.
세 그룹 서버의 역할 구분
default-nameserver는 한 가지 역할만 합니다: nameserver에 적힌 DoH/DoT 서버 자체의 도메인을 해석하는 것이므로, 반드시 순수 IP 주소만 적어야 하며 도메인을 다시 적으면 "닭이 먼저냐 알이 먼저냐" 같은 순환 문제가 생깁니다. nameserver는 주 해석 그룹으로 일상적인 조회를 모두 담당하며 암호화 DNS 주소를 권장합니다. 일부 커널은 fallback 그룹도 지원합니다: 주 그룹의 결과가 오염 특징을 보이면 이 그룹(주로 해외 해석 서비스)의 결과를 사용하는 선택적 강화 기능입니다.
dns:
enable: true
listen: 0.0.0.0:1053
enhanced-mode: fake-ip
fake-ip-range: 198.18.0.1/16
fake-ip-filter:
- "*.lan"
- "+.local"
- "time.windows.com"
default-nameserver:
- 223.5.5.5
nameserver:
- https://doh.pub/dns-query
- https://dns.alidns.com/dns-query
ping하면 198.18.x.x 대역 주소가 나오는데, 이는 오류가 아니라 의도된 동작입니다. 실제 주소가 필요하면 해당 도메인을 fake-ip-filter에 추가하세요.
도해 B-05프록시 노드 필드: proxies 배열
proxies는 노드 정의 배열입니다. 구독을 사용하는 경우 이 부분은 구독 변환 서비스가 자동으로 생성하므로 평소에는 직접 작성할 필요가 없습니다. 직접 작성이 필요한 대표적인 경우는 서버를 직접 구축했거나 개별 노드를 디버깅할 때입니다. 모든 프로토콜은 4개의 공통 필드를 공유합니다: name(노드 이름, 파일 전체에서 고유해야 하며 정책 그룹에서 이름으로 참조), type(프로토콜 종류), server(서버 주소, 도메인 또는 IP), port(서버 포트). 나머지 필드는 프로토콜마다 다르며, 아래에서 다운로드 페이지가 다루는 주요 프로토콜별로 정리했습니다.
Shadowsocks(type: ss)
핵심 필드는 두 가지입니다: cipher(암호화 방식)와 password(비밀번호). 둘 다 서버 측과 정확히 일치해야 하며, 하나라도 맞지 않으면 연결이 성립된 직후 바로 끊기거나 응답이 없는 형태로 나타납니다:
- name: "ss-예시"
type: ss
server: example.com
port: 8388
cipher: aes-128-gcm
password: "your-password"
VMess(type: vmess)
인증 정보는 uuid이며 서버 측과 한 글자도 다르지 않아야 합니다. alterId는 현재 배포에서는 0으로 고정입니다. cipher는 보통 auto로 설정합니다. WebSocket + TLS를 사용하는 노드는 network: ws와 ws-opts 하위 항목이 추가로 필요하며, 그중 path와 headers.Host는 서버 설정과 정확히 일치해야 합니다. 이 두 항목의 오류는 VMess 노드 타임아웃의 주된 원인입니다:
- name: "vmess-예시"
type: vmess
server: example.com
port: 443
uuid: 00000000-0000-0000-0000-000000000000
alterId: 0
cipher: auto
tls: true
network: ws
ws-opts:
path: /your-path
headers:
Host: example.com
Trojan과 Hysteria2
Trojan은 password를 인증 정보로 사용하며 실제 TLS 인증서에 의존하므로, sni는 인증서에 대응하는 도메인을 지정해야 합니다. Hysteria2는 QUIC(UDP 전송) 기반으로, password 외에 up / down으로 대역폭을 지정해 혼잡 제어를 활성화할 수 있습니다. 사용 중인 네트워크가 UDP를 막고 있으면 이 프로토콜 자체가 사용 불가하니 문제 조사 시 먼저 이 부분을 확인하세요:
- name: "trojan-예시"
type: trojan
server: example.com
port: 443
password: "your-password"
sni: example.com
- name: "hy2-예시"
type: hysteria2
server: example.com
port: 443
password: "your-password"
skip-cert-verify: true는 서버 인증서 검증을 포기하는 것으로 위장 방지 능력을 잃게 됩니다. 자체 구축 환경에서 임시로 디버깅할 때만 사용하고, "true로 하니 연결된다"는 이유로 계속 사용하지 마세요. 연결이 안 되는 근본 원인은 대부분 sni나 인증서 설정 오류입니다.
필드를 정확히 확인했는데도 연결이 안 될 경우, 문제는 보통 설정 파일 자체가 아니므로 노드 타임아웃 점검 목록 순서대로 구독 유효성, 시스템 시간, 방화벽을 확인하세요.
도해 B-06정책 그룹 필드: proxy-groups 배열
정책 그룹은 규칙과 노드 사이의 중간 계층입니다: 규칙의 출구는 그룹 이름을 지정하고, 그룹이 실제로 어떤 노드를 사용할지 결정합니다. 이 계층을 분리해두는 이유는, 구독 노드의 이름이 바뀌거나 추가·삭제되어도 그룹의 구성원 목록만 관리하면 되기 때문입니다(보통 구독 변환에서 자동으로 처리됨). 규칙은 한 줄도 손댈 필요가 없습니다. 자주 쓰는 네 가지 유형은 다음과 같습니다:
| type | 동작 | 대표 용도 |
|---|---|---|
select | 구성원을 수동으로 선택, 다시 전환하기 전까지 선택 유지 | 총 출구 그룹, 클라이언트 패널에서 사용자가 직접 선택 |
url-test | 주기적으로 속도 측정, 지연이 가장 낮은 구성원 자동 선택 | 자동 최적 선택 그룹, select 그룹의 구성원으로 사용 |
fallback | 목록 순서대로 사용 가능한 첫 번째 구성원 사용 | 메인-백업 전환, 우선 노드 장애 시 다음으로 넘어감 |
load-balance | 연결을 여러 구성원에 분산 | 다중 노드로 트래픽 분산 |
자동 속도 측정 매개변수
url-test와 fallback은 세 가지 매개변수에 의존합니다: url은 경량 상태 확인용 주소(보통 https://www.gstatic.com/generate_204를 사용, 빈 응답을 반환해 부담이 매우 적음), interval은 측정 주기(초 단위, 보통 300), tolerance는 밀리초 단위로 새 노드의 지연이 현재 노드보다 이 값만큼 더 낮아야 전환된다는 의미이며 지연이 비슷한 두 노드 사이에서 오락가락 전환되는 것을 막습니다. 선택적으로 lazy: true를 설정하면 그룹이 실제로 사용될 때만 속도 측정을 시작해 백그라운드 요청을 줄일 수 있습니다.
중첩과 내장 출구
그룹은 중첩할 수 있습니다: 흔한 방식은 select 총 출구 그룹을 하나 만들고, url-test 자동 그룹과 여러 수동 노드를 함께 구성원으로 넣어, 평소에는 자동 그룹을 쓰고 필요할 때 특정 노드로 한 번에 전환하는 것입니다. DIRECT(직결)와 REJECT(거부)는 커널에 내장된 두 출구로, 별도 정의 없이 어느 그룹이나 규칙의 출구로 바로 사용할 수 있습니다:
proxy-groups:
- name: "노드 선택"
type: select
proxies:
- "자동 측속"
- "홍콩-01"
- "일본-01"
- DIRECT
- name: "자동 측속"
type: url-test
url: https://www.gstatic.com/generate_204
interval: 300
tolerance: 50
proxies:
- "홍콩-01"
- "일본-01"
이름 규칙: 그룹 이름과 노드 이름이 중복되지 않도록 하세요. 규칙과 그룹 구성원에서 참조하는 이름은 정의된 곳과 이모지, 공백, 전각/반각까지 한 글자도 다르지 않아야 합니다. 하나라도 다르면 커널이 "proxy not found" 같은 오류로 설정 전체 로드를 거부하는데, 이는 구독 노드 이름 변경 후 설정에 갑자기 오류가 나는 흔한 원인입니다.
도해 B-07규칙 문법과 매칭 순서
rules 배열은 위에서부터 순서대로 매칭되며, 첫 번째로 일치하는 규칙에서 멈추고 그 뒤 규칙은 보지 않습니다—작성 순서가 곧 우선순위이며, 이것이 모든 분기 동작을 이해하는 첫 번째 원칙입니다. 각 규칙의 기본 형식은 "타입,매칭값,출구"이며, 일부 타입은 추가 매개변수를 지원합니다. 출구는 정책 그룹 이름, 노드 이름, 또는 내장된 DIRECT / REJECT일 수 있습니다.
| 타입 | 매칭 기준 | 예시 |
|---|---|---|
DOMAIN | 도메인 완전 일치 | DOMAIN,dl.google.com,노드 선택 |
DOMAIN-SUFFIX | 도메인 접미사(자기 자신 포함) | DOMAIN-SUFFIX,github.com,노드 선택 |
DOMAIN-KEYWORD | 도메인에 키워드 포함 | DOMAIN-KEYWORD,google,노드 선택 |
GEOIP | 대상 IP의 지역 소속 | GEOIP,CN,DIRECT |
IP-CIDR / IP-CIDR6 | 대상 IP가 특정 네트워크 대역에 속함 | IP-CIDR,192.168.0.0/16,DIRECT,no-resolve |
DST-PORT | 대상 포트 | DST-PORT,22,DIRECT |
PROCESS-NAME | 연결을 시작한 프로세스 이름(데스크톱 전용) | PROCESS-NAME,Steam.exe,DIRECT |
RULE-SET | 외부 규칙셋에 매칭(B-08 참고) | RULE-SET,reject-list,REJECT |
MATCH | 무조건 매칭, 최종 처리 | MATCH,노드 선택 |
정렬 원칙과 no-resolve
권장 순서: 정확 매칭(DOMAIN)을 앞에, 범위 매칭(DOMAIN-SUFFIX / DOMAIN-KEYWORD)을 중간에, IP 매칭(GEOIP / IP-CIDR)을 뒤에, MATCH는 반드시 마지막 한 줄에만 있어야 합니다. IP 매칭 규칙은 매칭 전에 도메인을 IP로 해석해야 하므로 추가 해석 부담이 생깁니다. 내부망 대역, 예약 대역처럼 "원래 IP가 대상인" 규칙은 줄 끝에 no-resolve를 붙여 "대상이 IP가 아니면 이 규칙을 건너뛴다"고 선언해 불필요한 해석을 피하세요:
rules:
- DOMAIN,dl.google.com,노드 선택
- DOMAIN-SUFFIX,github.com,노드 선택
- DOMAIN-KEYWORD,google,노드 선택
- DOMAIN-SUFFIX,cn,DIRECT
- IP-CIDR,192.168.0.0/16,DIRECT,no-resolve
- GEOIP,CN,DIRECT
- MATCH,노드 선택
자주 발생하는 실수 세 가지
첫째, MATCH 뒤에도 규칙을 계속 적는 경우—매칭되면 즉시 멈추므로 그 뒤 규칙은 절대 실행되지 않는 무의미한 줄이 됩니다. 둘째, DOMAIN-SUFFIX,cn이 중국 본토 사이트 전체를 다 커버한다고 오해하는 경우—이는 .cn 접미사만 매칭하며, 많은 중국 본토 서비스가 .com 도메인을 사용하므로 중국 본토 트래픽의 최종 처리는 GEOIP,CN에 맡겨야 합니다. 셋째, 출구 이름이 정책 그룹 정의와 다른 경우(공백이나 이모지 하나 차이)—설정 전체가 로드를 거부합니다. 중국 본토/해외 분기의 완전한 작성법과 매칭 계산은 규칙 분기 설정 실전 글을 참고하세요. 바로 사용하고 싶다면 입문 가이드에 있는 완성된 규칙 세트를 그대로 적용하세요.
log-level을 임시로 debug로 바꾸고 대상 사이트에 접속해 로그에서 해당 도메인을 검색하면 실제로 어떤 규칙에 매칭되어 어느 출구로 나갔는지 바로 확인할 수 있습니다. 계속 추측하는 것보다 훨씬 효율적입니다.
도해 B-08규칙셋: rule-providers 외부 규칙
수천 줄의 규칙을 수동으로 관리하는 것은 현실적이지 않습니다. 규칙셋 메커니즘은 대량의 규칙을 별도 파일로 외부화해, 설정에는 소스 선언과 참조 한 줄만 남기고 커널이 주기적으로 자동으로 갱신하도록 합니다. 이는 두 부분이 함께 작동합니다: 최상위 키 rule-providers가 소스를 정의하고, rules 안의 RULE-SET 항목이 이를 사용합니다.
필드별 설명
type은 http(원격에서 가져오기) 또는 file(로컬 파일)을 사용합니다. behavior는 파일 내용 형태를 나타내며 세 가지입니다: domain은 도메인 목록만 포함, ipcidr은 네트워크 대역 목록만 포함, classical은 각 줄이 "타입,매칭값" 형식의 완전한 규칙입니다. behavior는 파일의 실제 내용과 반드시 일치해야 합니다—일치하지 않으면 규칙셋이 오류 없이 조용히 작동하지 않게 되는데, 이는 규칙셋이 "로드된 것처럼 보이지만 작동하지 않는" 가장 흔한 원인입니다. format은 파일 형식(yaml 또는 text)을 지정하고, url은 원격 주소, path는 로컬 캐시 경로입니다. 서로 다른 규칙셋이 같은 path를 공유하면 서로 덮어쓰게 되니 주의하세요. interval은 갱신 주기(초 단위)로, 86400은 하루에 한 번을 뜻합니다.
rule-providers:
reject-list:
type: http
behavior: domain
format: yaml
url: https://example.com/rules/reject.yaml
path: ./ruleset/reject.yaml
interval: 86400
cn-cidr:
type: http
behavior: ipcidr
format: yaml
url: https://example.com/rules/cn-cidr.yaml
path: ./ruleset/cn-cidr.yaml
interval: 86400
rules:
- RULE-SET,reject-list,REJECT
- RULE-SET,cn-cidr,DIRECT,no-resolve
- GEOIP,CN,DIRECT
- MATCH,노드 선택
두 가지 보충: RULE-SET 항목도 rules 안에서 "위에서부터, 매칭되면 즉시 멈춤"이라는 전체 순서를 그대로 따릅니다. 규칙셋이라고 우선순위가 특별해지는 것은 아닙니다. ipcidr 타입 규칙셋을 참조할 때는 IP-CIDR 규칙과 마찬가지로 참조하는 줄 끝에 no-resolve를 추가하는 것이 좋습니다. 원격 규칙셋은 처음 가져올 때 네트워크 연결이 가능해야 하며, 설치 초기에 아직 연결되지 않았다면 type: file로 클라이언트와 함께 배포되는 로컬 파일을 임시로 지정해 넘어갈 수 있습니다.
도해 B-09오버라이드와 병합: 수동 수정이 구독 갱신 후에도 살아남게 하기
문제와 원칙
구독으로 생성된 설정 파일을 직접 편집하는 것은 초보자가 가장 자주 빠지는 함정입니다: 다음 구독 갱신 시 파일 전체가 다시 생성되면서 모든 수동 수정이 사라집니다. 올바른 방법은 하나의 원칙을 지키는 것입니다—구독 원본은 손대지 않고, 모든 수정은 "오버라이드 계층"에 둡니다. 클라이언트는 설정을 로드할 때마다 오버라이드 내용과 구독 원본을 병합해 커널에 전달하므로, 구독이 어떻게 갱신되든 커스터마이징에 영향을 주지 않습니다.
클라이언트별 오버라이드 진입점
주요 클라이언트는 모두 이 메커니즘을 제공하며, 이름은 다르지만 원리는 같습니다: Clash Verge Rev는 "전역 확장 설정"을 제공하며 Merge(선언형 병합)와 Script(스크립트 수정) 두 방식이 있습니다. Clash Plus는 설정 오버라이드 입력창을 제공합니다. FlClash는 설정 오버레이를 지원합니다. 진입점 위치와 필드 이름은 클라이언트 버전에 따라 다르므로 클라이언트 내 설명을 기준으로 하세요. Merge 방식 예시로, 구독 규칙 맨 앞에 커스텀 규칙 두 개를 삽입하면서 DNS 섹션을 함께 덮어써 보겠습니다:
prepend-rules:
- DOMAIN-SUFFIX,intra.example.com,DIRECT
- PROCESS-NAME,Steam.exe,DIRECT
dns:
enable: true
enhanced-mode: fake-ip
prepend- 접두사는 구독의 같은 이름 배열 앞에 삽입한다는 뜻(우선순위가 가장 높음)이고, append-는 끝에 추가한다는 뜻입니다. 최상위 키를 그대로 적으면(위 예시의 dns처럼) 구독의 해당 섹션 전체를 대체합니다. 커스텀 규칙은 대부분 prepend를 사용합니다—규칙은 매칭되면 즉시 멈추므로, 맨 앞에 넣어야 우선적으로 적용됩니다.
수정 후 검증 절차
오버라이드 내용을 수정할 때마다 정해진 절차로 검증하세요: 오버라이드 저장 → 클라이언트에서 설정 다시 로드 → 로그에 로드 오류가 없는지 확인 → 아래 명령으로 프록시 포트가 정상적으로 전달되는지 확인 → 연결 패널에서 대상 사이트에 실제로 접속해 매칭된 규칙과 출구가 예상과 맞는지 확인. 명령이 HTTP/2 204 또는 204 No Content를 반환하면 연결이 정상입니다:
curl -x http://127.0.0.1:7890 https://www.gstatic.com/generate_204 -I
도해 B-10로드 오류 대조표: 오류 문구에서 구체적인 줄까지 찾기
설정을 잘못 수정하면 커널이 로드를 거부하고 로그에 한 줄의 오류 메시지를 남깁니다. 이 메시지의 표현은 클라이언트마다 다소 다르지만 범주는 고정되어 있어, 범주만 알아도 오류가 난 필드를 바로 찾을 수 있으며 파일 전체를 한 줄씩 읽을 필요가 없습니다. 아래 표는 가장 흔한 오류 메시지와 실제 원인을 대응시켜 놓았으니, 문제 조사 시 먼저 메시지로 분류하고 해당 도해로 돌아가 작성법을 확인하세요.
| 오류 키워드 | 실제 원인 | 처리 방법 |
|---|---|---|
yaml: line N / did not find expected key | 들여쓰기 단계가 어긋나거나 Tab을 혼용함 | N번째 줄 근처로 이동해 Tab을 모두 공백 2칸으로 바꾸고 하이픈이 정렬되어 있는지 확인 |
could not find expected ':' | 콜론 뒤에 공백이 없거나 값에 특수 기호가 있는데 인용부호를 안 씀 | 콜론 뒤에 공백을 추가하고, #, 콜론, 중괄호가 포함된 값은 쌍따옴표로 감싸기 |
proxy not found / proxy 'X' not found | 정책 그룹이나 규칙이 존재하지 않는 노드/그룹 이름을 참조함 | 정의된 곳과 참조하는 곳을 한 글자씩 대조, 공백, 이모지, 전각/반각 차이 확인 |
rules[N] error / unsupported rule type | 규칙 타입 오타 또는 매개변수 개수가 맞지 않음 | 도해 B-07의 타입 표로 돌아가 오타를 확인하고 "타입,매칭값,출구" 세 부분이 다 있는지 확인 |
address already in use | 포트가 다른 프로세스(주로 이전에 종료되지 않은 커널)에 점유됨 | 남아있는 프로세스를 종료하거나 mixed-port를 다른 포트로 바꾸고 시스템 프록시도 함께 변경 |
초기화 DNS 실패 / dns error | default-nameserver에 순수 IP가 아니라 도메인을 적음 | 223.5.5.5 같은 순수 IP로 변경, 자세한 내용은 도해 B-04 참고 |
범용 이분법 위치 찾기
오류 메시지가 모호한 줄 번호만 알려주는데 그 줄이 문제없어 보인다면, 대부분 이전 섹션의 구조가 제대로 닫히지 않아 오류가 다음 줄로 "밀려간" 경우입니다. 이때는 이분법이 가장 시간을 절약합니다: 먼저 rules 섹션 전체를 주석 처리하고 다시 로드해보세요. 로드가 되면 문제가 규칙에 있다는 뜻입니다. 안 되면 proxy-groups도 주석 처리하며 위로 범위를 좁혀가다가, 구체적인 섹션을 찾으면 그 안에서 다시 절반씩 주석 처리하세요. YAML 주석은 줄 앞에 #를 붙이면 되고, 어떤 텍스트 에디터에서든 일괄 주석 처리가 가능해 몇 번 반복하면 반드시 오류가 난 줄을 찾을 수 있습니다.
"오류는 없지만 작동하지 않는" 경우가 더 많은 시간을 잡아먹습니다: 커널 로드는 성공하고 로그도 깨끗한데 동작이 예상과 다른 경우입니다. 이런 문제의 근본 원인은 대부분 문법이 아니라 의미에 있습니다—위쪽의 더 넓은 규칙에 먼저 매칭되어 버렸거나, 규칙셋의 behavior가 파일 내용과 맞지 않거나, 오버라이드 계층 해석이 실패해 조용히 원본으로 되돌아간 경우입니다. 판단 방법은 동일합니다: log-level을 debug로 바꾸고 대상 사이트에 한 번 접속해, 로그에서 이 연결이 실제로 어떤 규칙에 매칭되어 어느 출구로 나갔는지 확인하면 "추측"이 "확인"으로 바뀝니다. 로그에 해당 도메인의 기록조차 없다면 트래픽이 커널로 전혀 들어오지 않았다는 뜻이므로, 시스템 프록시 미작동 점검 글로 돌아가 입구 문제를 먼저 해결하세요.
도해 B-11백업, 버전 관리, 장기 유지관리 규칙
백업해야 할 것
장기간 보관해야 할 것은 실제로 세 가지뿐입니다: 첫째는 구독 링크 자체(잃어버리면 서비스 제공자 패널에서 다시 가져와야 함), 둘째는 직접 작성한 오버라이드 계층 내용(자동으로 복구할 수 없는 유일한 수동 자산), 셋째는 커스텀 규칙셋의 로컬 파일(type: file을 사용한 경우). 구독으로 생성되는 config.yaml 자체는 백업할 필요가 없습니다—언제든 다시 가져올 수 있으며, 오히려 백업해두면 "백업 파일을 수정했는데 왜 적용이 안 되는지" 하는 혼란을 일으키기 쉽습니다. 이 세 가지를 순수 텍스트 폴더에 모아두면, 시스템을 재설치하거나 기기를 바꿔도 클라이언트 새로 설치 → 구독 다시 입력 → 오버라이드 계층 붙여넣기만 하면 몇 분 안에 완전히 복구됩니다.
기억 대신 주석 남기기
오버라이드 계층에 커스텀 규칙을 추가할 때마다 바로 위 줄에 "왜 추가했는지"와 "언제 삭제해도 되는지"를 적는 것이 좋습니다. 반년쯔음 지나면 주석 없는 규칙은 삭제하기도 무섭고 용도도 기억나지 않아 계속 남겨두게 됩니다. 반면 주석이 있는 규칙은 정기적으로 정리할 수 있습니다. 주석을 쓰는 비용은 한 줄이지만, 그 덕분에 설정 파일이 시간이 지나도 관리 불가능한 부담으로 커지지 않습니다:
prepend-rules:
# 회사 내부 OA, 반드시 직결, 퇴사 후 삭제 가능
- DOMAIN-SUFFIX,intra.example.com,DIRECT
# Steam 다운로드는 대역폭을 다 쓰기 위해 직결, 2026-07 추가
- PROCESS-NAME,Steam.exe,DIRECT
정기적으로 확인해야 할 세 가지
첫째, 규칙셋의 interval과 path: 여러 규칙셋이 같은 path를 공유하면 서로 덮어쓰게 됩니다. 규칙셋을 새로 추가할 때 복사·붙여넣기 실수가 자주 발생하니 매번 추가 후 확인하는 것이 좋습니다. 둘째, 정책 그룹 구성원: 구독 노드 이름이 바뀌면 오버라이드 계층에 수동으로 적어둔 노드 이름이 이미 무효화될 수 있으며, 그룹에 구성원이 빠지거나 proxy not found 오류가 나타납니다. 셋째, 커널과 클라이언트 버전: 새 필드는 구식 커널에서 인식되지 않을 수 있으므로 클라이언트를 업그레이드한 뒤 새 필드를 사용하는 것이 안전합니다. 각 클라이언트의 업데이트 주기와 차이는 클라이언트 비교 페이지를 참고하고, 설치 파일은 설치 페이지에서 받으세요.
언제 계속 수정하지 말고 새로 만들어야 하는가
설정을 반복해서 수동으로 고치다가 어떤 필드가 여전히 작동하는지도 헷갈리는 상태가 되면, 계속 고치는 것보다 새로 만드는 것이 더 빠릅니다: 기존 설정을 삭제하고 구독을 다시 가져와 깨끗한 원본을 얻은 뒤, 오버라이드 계층에서 여전히 필요한 규칙만 골라 다시 붙여넣고 나머지는 모두 버리세요. 도해 B-02의 최소 뼈대를 기준으로 다섯 부분만 갖추면 바로 동작하며, 그 위에 필요한 부분을 하나씩 추가하면서 매번 다시 로드하면 오류가 난 부분을 즉시 찾을 수 있습니다. 이 방법이 돌아가는 길처럼 보이지만, 실제로는 엉망인 파일을 하나씩 뒤지는 것보다 훨씬 시간을 절약합니다.
도해 B-12자주 쓰는 상황별 필드 조합
이 절에서는 앞서 다룬 필드들을 조합해 실제로 바로 사용할 수 있는 몇 가지 완성 예시를 제공하며, 일상에서 가장 많이 필요한 네 가지 상황을 다룹니다. 모두 오버라이드 계층에 작성하므로 구독 갱신에 영향을 받지 않으며, 복사한 뒤 주석에 따라 자신의 도메인과 프로세스 이름으로 바꾸면 됩니다.
상황 1: 특정 사이트는 반드시 직결해야 함
회사 내부 시스템, 은행, 정부 사이트처럼 국내 출구만 인식하는 서비스는 프록시를 거치면 거부되거나 계속 인증을 요구받습니다. DOMAIN-SUFFIX로 DIRECT를 지정하고, prepend 섹션에 두어 구독에 포함된 다른 규칙보다 우선 적용되도록 합니다:
prepend-rules:
- DOMAIN-SUFFIX,intra.example.com,DIRECT
- DOMAIN-SUFFIX,example-bank.com,DIRECT
상황 2: 특정 프로그램 전체를 직결 또는 프록시로 보내기
데스크톱에서는 프로세스 이름으로 분기할 수 있어, 프록시가 필요 없으면서 대역폭을 많이 쓰는 게임 다운로더나 대용량 파일 동기화 도구에 적합합니다. 프로세스 이름은 시스템의 실제 실행 파일 이름을 적어야 하며, Windows는 .exe 확장자를 포함하고 macOS와 Linux는 보통 포함하지 않습니다. 이름은 클라이언트의 연결 패널에서 바로 확인할 수 있습니다:
prepend-rules:
- PROCESS-NAME,Steam.exe,DIRECT
- PROCESS-NAME,Docker Desktop.exe,노드 선택
상황 3: 광고 및 추적 도메인 차단
연결하고 싶지 않은 도메인을 REJECT로 지정하면 커널이 해당 연결을 바로 거부합니다. 소수의 도메인이라면 직접 작성해도 되지만, 규모가 큰 목록은 규칙셋에 맡겨 rule-providers가 자동으로 갱신하도록 하는 것이 좋습니다. 수천 줄을 수동으로 관리할 필요가 없습니다:
prepend-rules:
- DOMAIN-KEYWORD,doubleclick,REJECT
- DOMAIN-SUFFIX,ads.example.com,REJECT
상황 4: 지역별 출구 지정
스트리밍, AI 서비스처럼 지역별로 콘텐츠를 제공하는 사이트는 특정 지역의 노드로 고정해서 나가야 합니다. 방법은 먼저 해당 지역 노드만 포함된 select 또는 url-test 그룹을 만든 뒤, 해당 도메인을 이 그룹으로 지정하는 것입니다. 이렇게 하면 노드가 늘거나 줄어도 그룹 구성원만 관리하면 되고 규칙은 손댈 필요가 없습니다:
prepend-proxy-groups:
- name: "일본 출구"
type: url-test
url: https://www.gstatic.com/generate_204
interval: 300
proxies:
- "일본-01"
- "일본-02"
prepend-rules:
- DOMAIN-SUFFIX,example-stream.jp,일본 출구
네 가지 조합 모두 같은 원칙을 따릅니다: "어떤 트래픽인지"(도메인, 프로세스, IP 대역)를 정하고, "어느 출구로 보낼지"(내장 출구 또는 정책 그룹)를 정한 뒤, prepend 섹션에 두어 우선순위를 보장하는 것입니다. 이 세 단계를 이해하면 어떤 새로운 요구사항도 직접 조합해낼 수 있으며 완성된 설정을 기다릴 필요가 없습니다. 규칙 간 매칭 계산과 더 복잡한 국내외 분기 방안은 규칙 분기 설정 실전을 참고하세요.
이제 config.yaml의 주요 필드를 모두 다루었습니다. 이 페이지에서 다루지 않은 구체적인 오류 현상은 FAQ 페이지에서 분류별로 검색하세요. 어떤 클라이언트로 이 설정을 사용해야 할지 확실하지 않다면 클라이언트 비교 페이지의 선택 결론을 참고하세요. 아직 클라이언트를 설치하지 않았다면 설치 페이지에서 플랫폼별로 받으세요. 각 플랫폼에서 우선 추천은 Clash Plus입니다.