claude code에서 잘 사용하지 않는 skills 다루기

#claude-code#skills

Pasted image 20260529005608.png

이번 글에서는 Claude Code의 Skills 설정을 다룬다.

GitHub에는 Claude Code용 오픈소스 스킬 번들이 넘쳐난다. gstack, superpowers 같은 잘 알려진 컬렉션부터 개인이 묶어 올린 모음집까지, 한 번 설치하면 적게는 한두 개, 많게는 20개가 넘게 따라온다. 그렇게 스킬 세트를 한두 개 추가하면서 Claude Code를 사용하다 보니 어느새 글로벌 스킬 디렉터리에 65개가 쌓여 있었다.

문제는 그중에서 실제로 자주 쓰는 스킬은 몇 개 안 된다는 점이었다. /qa, /ship, /review 같은 핵심 워크플로우는 매일 쓰지만, /benchmark-models/design-shotgun 같은 건 한 달에 한 번 쓸까 말까다. 그런데 설치만 해두면 65개 전부가 세션마다 Claude의 컨텍스트를 차지한다. 안 쓰는 62개 때문에 토큰이 새고, Claude의 주의도 분산되는 셈이다.

이때 Claude Code /skills4가지 상태값을 잘 다루면 이 문제를 완화할 수 있다. 결론부터 얘기하면, 정말 안 쓸 스킬이 아닌 이상 off보다는 user-only로 두는 편이 낫다. 그래야 스킬 간 의존 관계도 어느 정도 지킬 수 있고, 토큰·컨텍스트 측면에서도 이득이다.

참고로 이 글은 공식적인 내용이 아니라 직접 써 보며 얻은 개인적인 관찰과 인사이트를 정리한 글이므로, 틀린 정보가 있다면 지적해 주시면 감사하겠습니다! 토큰 측정값은 직접 재 본 수치이지만, Claude의 내부 동작이나 비용 계산처럼 공개되지 않은 부분에는 추측이 섞여 있을 수 있습니다.
이 글은 Claude Code

2.1.129 이상을 기준으로 한다. /skills가 기록하는 skillOverrides 설정은 2.1.129에서 수정됐다. 그 이전 버전에서는 user/project 설정의 skillOverrides가 적용되지 않아(상태를 읽는 내부 함수가 항상 on을 반환하는 스텁이었다) /skills에서 상태를 바꿔도 모델 컨텍스트에서 스킬 설명이 빠지지 않았다. 아래에서 설명하는 토큰 절약 효과는 2.1.129 이상에서만 실제로 나타난다.


1. /skills의 4가지 옵션#

먼저 /skills 메뉴에서 각 스킬에 줄 수 있는 4가지 상태를 정리한다.

옵션 컨텍스트 로드 / 메뉴 표시 Claude 자동 호출 사용자 수동 호출
on ✅ 이름 + 설명 전체
name-only ✅ 이름만 ⚠️ 감지율 ↓
user-only ❌ 로드 안 됨
off ❌ 로드 안 됨

핵심은 '컨텍스트 로드' 열이다. onname-only만 컨텍스트에 올라가고, user-onlyoff는 매 세션에서 Claude의 시야에 들어오지 않는다. 토큰만 놓고 보면 user-onlyoff는 똑같이 "공짜"인 셈이다.

그런데도 굳이 이 둘을 구분하는 이유가 있다. 그 이유를 이해하려면, 먼저 안 쓰는 스킬이 실제로 얼마나 무거운지부터 봐야 한다.


2. 실측: 65개 스킬은 얼마나 무거운가#

직접 측정해 봤다. ~/.claude/skills/ 아래 65개 스킬의 SKILL.md 프론트매터에서 namedescription만 추출해 글자 수를 합산한 결과다.

총 스킬 수    : 65개
총 글자 수    : 28,980자
추정 토큰     : 7,245 ~ 8,280 토큰
스킬 1개 평균 : 446자 (~127 토큰)

가장 무거운 5개와 가장 가벼운 5개는 이렇다.

[ 무거운 스킬 ]
  ai-readiness-cartography : 1,068자 (~305 토큰)
  plan-tune                :   781자 (~223 토큰)
  office-hours             :   773자 (~221 토큰)
  design-html              :   736자 (~210 토큰)
  plan-devex-review        :   712자 (~203 토큰)

[ 가벼운 스킬 ]
  to-prd        : 166자 (~47 토큰)
  write-a-skill : 171자 (~49 토큰)
  zoom-out      : 204자 (~58 토큰)
  tdd           : 214자 (~61 토큰)
  triage        : 228자 (~65 토큰)

토큰 수치는 글자 수를 바탕으로 환산한 추정치라 정확한 값은 아니지만, 대략 세션이 시작될 때마다 약 7,500~8,300토큰이 스킬 설명만으로 소모되는 것으로 보인다. 그것도 대부분 쓰지도 않는 스킬을 위해서다.

만약 65개 중 자주 쓰는 3개만 on으로 두고 나머지 62개를 전부 user-only로 바꾼다고 가정해 보자.

on으로 둔 3개의 토큰량 : 약 3 × 127 ≈ 380 토큰
절약량                : 약 7,100 ~ 7,900 토큰 (세션당)

세션당 약 7,500토큰, 100세션이면 70만 토큰 규모다. 어디까지나 추정 기반의 어림값이지만, 무시할 수치는 아닌 듯하다.

한 가지 덧붙이면, 스킬 설명이 무한정 컨텍스트에 쌓이는 것은 아니다. Claude Code에는 스킬 목록에 쓸 수 있는 예산(skillListingBudgetFraction)이 있고, 기본값은 모델 컨텍스트 윈도우의 1%다. Opus 4.7의 1M 윈도우라면 약 1만 토큰에 해당한다. 위에서 측정한 65개의 description 합계(약 7,245~8,280토큰)는 이 예산 안에 들어오므로 65개가 전부 로드된다. 만약 예산을 넘으면 사용 빈도가 가장 낮은 스킬의 설명부터 잘려나가며, /doctor로 초과 여부를 확인할 수 있다.


3. "어차피 세션 시작 때 한 번만 로드되는 것 아닌가?"#

여기서 자연스러운 의심이 든다. "스킬 목록은 세션 시작 때 한 번 로드되고 끝 아닌가? 그럼 토큰을 한 번만 쓰는 거니까 그렇게 큰 비용은 아니지 않나?"

결론부터 말하면 아니다. 정확히 말하면 컨텍스트는 "한 번 점유"되지만, API 전송은 "매 턴 반복"된다. 비용 모델을 제대로 이해하려면 세 가지 관점을 분리해서 봐야 한다.

관점 A — 컨텍스트 윈도우 점유 (논리적 관점)#

세션 시작 시 1회 주입되고, 끝까지 유지된다.

시점 동작
세션 시작 on 스킬들의 이름 + 설명이 시스템 프롬프트의 스킬 목록(skill listing)으로 1회 주입
이후 모든 턴 그 스킬 목록이 롤링 컨텍스트에 그대로 남음
스킬 파일 수정 ~/.claude/skills/ 등의 스킬을 편집·추가·삭제하면 재시작 없이 현재 세션에 반영됨 (live change detection)

Opus 4.7의 1M(약 100만) 토큰 컨텍스트 윈도우를 기준으로 보면 8k 토큰은 전체의 약 **0.8%**다. 비율로는 작아 보이지만, 큰 코드베이스를 본격적으로 다루기 시작하면 1M도 의외로 빠듯해진다. description으로 점유한 8k는 그만큼 작업용 컨텍스트가 줄어든 것이고, 그 8k를 비워두면 나중에 스킬 본문이나 코드를 더 담을 여유가 생긴다.

관점 B — API 전송 (물리적 관점)#

매 턴마다 그 8k가 다시 전송된다. Claude Code(및 Anthropic API)는 stateless라서, API 호출마다 전체 컨텍스트를 처음부터 다시 보낸다. 한 세션에서 10개의 메시지를 주고받았다면 이렇게 된다.

Turn 1  : system reminder(8k 설명 포함) + 사용자 메시지 1
Turn 2  : system reminder(8k 또 포함) + 메시지 1 + 응답 1 + 메시지 2
  ...
Turn 10 : 같은 8k 설명이 또 포함되어 전송

즉, 8k 토큰이 와이어를 10번 탄다. 누적 전송량은 80k 토큰이다. 컨텍스트 윈도우를 8k씩 10번 잡아먹는 것이 아니라, 8k 슬롯 하나가 처음부터 끝까지 점유된 채로 매 턴마다 다시 전송되는 구조다.

관점 C — 청구 비용 (prompt caching 적용)#

여기서 prompt caching이 결정적인 변수다.

비용 종류 기본 입력가 대비
Turn 1 Cache write × 1.25
Turn 2 ~ N Cache read × 0.1 (90% 할인)

Opus 4.7 입력 단가를 $5/MTok으로 잡고, 8k 설명 × 10턴을 계산해 보면 다음과 같다. 이 계산은 API 종량 과금 기준이다 — Pro·Max 같은 구독 요금제에서는 달러가 이렇게 직접 청구되지는 않지만, 토큰을 아끼는 효과 자체는 동일하게 적용된다. 실제 청구액은 캐시 적중률과 세션 패턴에 따라 달라지므로, 아래 수치는 단순화한 모델을 바탕으로 계산한 값으로 봐 주면 된다.

캐싱 없을 때 : 8k × 10턴 × $5/MTok                  = $0.40
캐싱 적용    : (8k × 1.25 + 8k × 9턴 × 0.1) × $5/MTok = 약 $0.086
            → 약 78% 절감

한 줄 정리#

8k 토큰은 점유는 1번, 전송은 10번, 청구는 2.15번 분량이다. (청구 배수 2.15 = 첫 턴 cache write 1.25 + 이후 9턴 cache read 0.1 × 9)

그래서 안 쓰는 62개를 user-only로 빼면 다음 세 가지가 한꺼번에 좋아진다.

  1. 컨텍스트 슬롯이 즉시 비어 다른 작업 컨텍스트를 더 담을 수 있다.
  2. 매 턴 전송량이 줄어 캐시 미스가 났을 때의 비용도 줄어든다.
  3. 컨텍스트 압축 시 잘려나갈 대화가 더 오래 보존된다.

여기에 한 가지를 덧붙이자면, 위에서 측정한 7,2508,280토큰은 description만의 합계다. 스킬을 실제로 호출하면 그 스킬의 SKILL.md 본문(보통 수백수천 토큰)이 추가로 lazy load되어 컨텍스트에 들어온다. 그러니 평소 description 예산을 아껴둘수록, 정작 작업할 때 본문을 로드할 여유 공간이 더 생긴다.

💡 확인 명령어

  • /context — 현재 세션의 컨텍스트 윈도우 점유량을 카테고리별로 표시
  • /skills — 스킬 목록과 각 스킬의 상태(on/name-only/user-only/off)를 보고 바꾸는 메뉴
  • /doctor — 스킬 목록 예산 초과 여부와 설명이 잘린 스킬을 표시

4. 그렇다면 왜 off가 아니라 user-only인가#

이제 핵심 질문이다. "안 쓰는 62개를 그냥 off로 꺼버리면 안 되나? 토큰 절약 효과는 똑같지 않나?"

토큰 절약만 보면 똑같다. 하지만 user-onlyoff보다 나은 이유가 세 가지 있다.

4-1. 컨텍스트가 진짜로 깨끗해진다#

user-onlyoff도 Claude의 스킬 목록에 표시되지 않는다. 세션마다 컨텍스트에 이름과 설명이 로드되지 않는다는 점은 같다.

그런데 이는 단순한 토큰 절약 이상의 의미가 있는 듯하다. Claude는 컨텍스트에 떠 있는 정보를 어느 정도 "고려"하기 마련인데, 65개의 스킬 설명이 떠 있으면 사용자가 그냥 "이 코드 좀 봐줘"라고 했을 때도 /review, /qa, /audit-and-write-readme 같은 스킬을 두고 호출 여부를 저울질하게 되는 것으로 보인다. 일종의 결정 비용이 발생하는 셈이다. 이 부분은 모델 내부 동작에 대한 필자의 해석이라 단정하긴 어렵다.

스킬 목록을 3개로 줄이면 Claude의 주의도 그 3개에 더 집중되고, 응답이 산만해질 여지도 줄어드는 것으로 느껴졌다. 어디까지나 필자의 경험에 따른 것이지만, 토큰 절약과는 별개의 이점이라고 본다.

4-2. 가끔 필요할 때 즉시 부를 수 있다#

off는 끄는 순간 사실상 존재하지 않는 것과 같다. 한 달 만에 /benchmark-models가 다시 필요해지면, /skills 메뉴에 들어가서 일일이 다시 켜야 한다.

user-only는 다르다. / 메뉴에는 그대로 보이고, /benchmark-models라고 직접 입력하면 즉시 실행된다. "평소엔 자고 있다가, 부르면 일어나는" 상태인 셈이다.

4-3. 스킬 체이닝(chaining)이 살아 있다#

이 부분이 가장 중요하다.

Claude Code의 스킬은 종종 다른 스킬을 호출하도록 설계된다. 예를 들어 /shipSKILL.md에는 이런 식의 지시가 들어 있곤 한다.

PR을 만든 뒤 land-and-deploy 스킬을 invoke하라.

이때 /land-and-deployuser-only 상태라면 어떻게 될까. Claude Code 2.1.129 변경 로그에는 user-invocable-only(/skills 메뉴의 user-only)가 "모델에게서만 숨긴다(hides from model only)"라고 명시되어 있다. 즉 제한은 발견(discovery) 단계에만 걸리고, 호출 게이트(invocation gate) 자체는 막지 않는다. 반면 off는 "모델과 / 메뉴 양쪽에서 숨긴다"이고, off로 꺼둔 스킬을 호출하면 Skill <name> is disabled를 반환하며 실제로 막힌다.

그래서 /ship이 활성화되어 컨텍스트에 로드되면 그 안의 "land-and-deploy를 호출하라"는 지시도 함께 로드되고, Claude는 그 이름을 보고 Skill 도구를 호출한다 — 대상이 user-only든 아니든 말이다. user-only는 스킬 목록(listing)에서만 빠질 뿐 호출을 막지는 않기 때문이다. 다만 부모 스킬에 자식 스킬의 이름이 적혀 있어야 한다는 조건이 붙는데, 이는 바로 아래에서 다룬다.

반면 off는 호출 게이트 자체를 막는다. 체이닝이 끊어진다.

off       : 안 쓰는 스킬이 다른 스킬의 의존성일 때 → 워크플로우가 깨진다
user-only : 의존성이어도 안전 → 이름이 명시된 체이닝은 그대로 작동한다

단, 체이닝에는 한 가지 조건이 있다#

체이닝이 작동하려면 부모 스킬이 자식 스킬의 이름을 명시적으로 적어둬야 한다.

체이닝 방식 user-only 자식의 작동 여부
SKILL.md에 "skill-b를 invoke해라"처럼 이름이 박힘 ✅ 작동
"관련된 다른 스킬이 있으면 알아서 써라" 식의 암묵적 체이닝 ❌ Claude가 존재를 모름 → 못 부름

한 가지 짚어둘 점은, 모든 번들이 Skill 도구로 다른 스킬을 직접 호출하는 방식의 체이닝을 쓰지는 않는다는 사실이다. 예를 들어 gstack/ship/land-and-deploy는 "PR 생성 → 머지·배포"로 이어지는 순차적 단계이지 한쪽이 다른 쪽을 invoke하는 구조가 아니며, /plan-eng-review가 테스트 계획을 아티팩트 파일로 남기면 나중에 /qa가 그 파일을 읽어가는 식의 아티팩트 전달 방식을 사용한다. 이런 순차·아티팩트 방식은 user-onlyoff든 영향을 받지 않는다. user-onlyoff의 차이가 실제로 갈리는 지점은, 부모 스킬의 SKILL.md가 자식 스킬 이름을 명시해 Skill 도구로 직접 호출하는 경우다 — 이때 off면 호출이 막히고, user-only면 작동한다.


5. 실전 세팅 가이드#

그러면 65개짜리 글로벌 스킬을 실제로 어떻게 분류하면 좋을지 정리한다.

on으로 둘 것 (3~5개)

  • 매일 쓰는 핵심 스킬. /ship, /qa, /review 같은 것.
  • Claude가 알아서 감지해서 불러주길 원하는 것.

name-only로 둘 것 (2~3개)

  • 자주 쓰진 않지만, Claude가 가끔 자율적으로 떠올려주면 좋은 것.
  • 설명 토큰까지는 아껴도 무방한 것.

user-only로 둘 것 (나머지 55~60개)

  • 가끔 필요하지만 평소엔 컨텍스트에 떠 있을 필요가 없는 것.
  • 다른 스킬의 체이닝 대상이 될 가능성이 있는 것.
  • "부를 때만 와줘"가 적절한 것.

off로 둘 것 (정말 안 쓰는 것만, 0~2개)

  • 완전히 deprecated된 것.
  • 다른 스킬이 절대 호출하지 않는다고 확신할 수 있는 것.

6. 마무리#

GitHub 오픈소스 스킬 번들은 풍족하다. 하지만 그 풍족함의 대가는 컨텍스트 토큰과 산만함이다. 필자의 경우 65개 스킬 중 안 쓰는 62개가 세션마다 약 7,500토큰(추정)을 갉아먹고, 거기에 Claude의 주의력까지 분산시키고 있는 것으로 보였다.

해결책은 의외로 단순하다.

  1. 자주 쓰는 것만 on — Claude가 알아서 호출해야 하는 것
  2. 나머지는 거의 다 user-only — 토큰은 아끼고 주의도 정리하되, 호출은 살려두는 자리
  3. off는 정말 안 쓸 때만 — 체이닝까지 끊어도 되는 것만

user-only는 한마디로 "절약하면서도 살려두는" 자리다. 토큰은 off만큼 아끼면서도, 필요할 때 즉시 부를 수 있고, 다른 스킬의 체이닝도 깨뜨리지 않는다.

오픈소스 번들 사용자가 가장 자주 잘못 쓰는 옵션이 off이고, 가장 적게 쓰는 옵션이 user-only다. 이 둘을 반대로 쓰면 된다.


참고 자료#

  • Claude Code Docs — Extend Claude with skillsskillOverrides의 4가지 상태(on / name-only / user-invocable-only / off) 정의, skillListingBudgetFraction(기본 1%) 예산, 스킬 콘텐츠 수명주기, live change detection
  • Claude Code CHANGELOG — 2.1.129: "skillOverrides setting now works: off hides from model and /, user-invocable-only hides from model only, name-only collapses description". 이 글은 2.1.129 이상을 전제로 한다.
  • Anthropic API — Pricing — Claude Opus 4.7 입력 25/MTok, 5분 cache write 1.25×, cache read(hit) 0.1×
  • gstack — github.com/garrytan/gstack/ship·/qa 등 스킬 워크플로우. 스킬 간 연결은 주로 순차 단계와 아티팩트 파일 전달 방식
  • 측정 방법: ~/.claude/skills/*/SKILL.md의 프론트매터에서 namedescription을 추출해 글자 수를 합산(when_to_use는 제외). 토큰 추정치는 영문 4자/토큰, 한·영 혼합 3.5자/토큰 기준
  • 컨텍스트 윈도우 기준: Claude Opus 4.7 (1M 토큰)
  • 진단 명령어: /context(컨텍스트 점유량), /skills(스킬 목록·상태), /doctor(스킬 목록 예산 초과 여부)

댓글