로컬 모델은 도구를 얼마나 제대로 부르나 — 8개 모델, 9,759턴
노트 · 측정
로컬 모델은 도구를 얼마나 제대로 부르나 — 8개 모델, 9,759턴
저장된 실행 9,759턴에서 집계한 모델별 도구 호출: 자체 호출, 없는 도구, 읽지 않음, 근거 없는 숫자, 이름 노출.
2026-10-04
로컬 LLM 커뮤니티의 한 글(2026-06)이 핵심을 짚었습니다. 로컬 모델을 에이전트에 붙였을 때 진짜 문제는 초당 토큰이 아니라 도구 호출이라는 것, 그리고 “호출을 안 함 · 없는 도구를 부름 · 호출이 깨져 글로 새어 나옴 · 결과를 받고도 무시함”을 따로 세는 독립적인 측정이 있어야 서로 같은 얘기를 할 수 있다는 것입니다. veneta 팀이 지난 2주 동안 저장한 실행 파일에는 모델이 부른 도구와 그 결과, 최종 답이 턴마다 그대로 들어 있어서, 모델 없이 세기만 하면 됐습니다.
무엇을 셌나
운영 질문(장애·최적화·양자) 턴만 셌고, 잡담과 데이터 없음 질문은 도구를 부를 일이 없어 뺐습니다. 턴마다 다음을 봅니다.
- 모델 자체 호출 — 하네스가 먼저 읽어 건넨 값(아래 “조건” 참조) 말고, 모델이 스스로 더 부른 도구. 이 가운데
- 없는 도구 — 도구 목록에 없는 이름을 부름(
recallFromMemory,none같은 것). 루프는 오류 결과를 돌려주고 답은 계속됩니다. - 상태 오류 — 실제 도구가 그 시점의 상태 때문에 거절함(예: “열린 인시던트가 없음”). 모델 잘못이 아닌 경우가 대부분이라 참고용입니다.
- 없는 도구 — 도구 목록에 없는 이름을 부름(
- 읽지 않음 — 하네스 포함 아무 도구도 읽지 않고 답함.
- 근거 없는 숫자 — 답에 쓴 숫자 가운데 어떤 도구 결과나 기억 줄에도 없는 것이 있음. “결과를 받고도 쓰지 않거나 잘못 읽은” 축입니다.
- 도구 이름 노출 — 답 본문에 도구 이름이나 호출 구문이 그대로 남음. 호출이 글이 되어 버린 경우입니다.
- 요청 실패 — 모델 서버 요청 자체가 실패한 턴.
결과
| 모델 (서빙) | 턴 | 모델 자체 호출 턴 | 자체 호출 | 없는 도구 | 상태 오류 | 읽지 않음 | 근거 없는 숫자 | 이름 노출 | 요청 실패 |
|---|---|---|---|---|---|---|---|---|---|
| gemma-4-31b (FP8) | 2,874 | 8.7 % | 252 | 0 | 0 | 0.0 % | 0.9 % | 0.8 % | 0 |
| otel-31b (FP8) | 1,442 | 0.9 % | 17 | 0 | 1 | 0.5 % | 4.6 % | 5.5 % | 1 |
| gemma-4-12B (bf16) | 746 | 5.8 % | 51 | 0 | 0 | 0.0 % | 4.3 % | 2.0 % | 0 |
| qwen3.8-27b (FP8) | 710 | 0.0 % | 0 | — | 0 | 0.0 % | 12.0 % | 1.3 % | 0 |
| exaone-4.0.1-32b (bf16) | 632 | 13.4 % | 107 | 0 | 2 | 0.0 % | 17.4 % | 3.2 % | 0 |
| llama-3.3-70b (FP8) | 512 | 95.3 % | 656 | 22 (3.4 %) | 45 | 0.0 % | 1.0 % | 9.8 % | 21 |
| glm-4.7-flash (bf16) | 422 | 20.6 % | 120 | 0 | 3 | 0.0 % | 26.1 % | 3.1 % | 0 |
| mistral-small-3.2-24b (FP8) | 422 | 2.1 % | 12 | 0 | 0 | 0.0 % | 16.4 % | 1.2 % | 0 |
읽는 법
- “읽지 않음”이 모든 모델에서 0에 가까운 것은 모델이 아니라 하네스의 공입니다. veneta는 운영 질문의 첫 걸음으로 도구를 먼저 읽어 결과를 모델에 건넵니다. 이 표는 그 루프 안에서의 비율이지, 모델을 맨몸으로 에이전트에 붙였을 때의 실패율이 아닙니다.
- 자체 호출 비율은 성적이 아니라 성향입니다. 건네받은 값으로 충분하면 더 부르지 않는 모델(gemma 8.7 %, qwen 0 %)과, 거의 매 턴 더 부르는 모델(llama 95 %)이 있습니다. 더 부른다고 답이 좋아지지는 않았습니다.
- 없는 도구를 부른 것은 한 모델뿐입니다. llama-3.3-70b가 자기 호출 656건 중 22건(3.4 %)에서
none,recall,recallLastAction,recallFromMemory같은 이름을 불렀습니다. 기억을 “도구로” 부르려는 시도가 대부분인데, 기억은 호출이 아니라 프롬프트에 이미 들어 있습니다. - 모델을 가장 크게 가르는 축은 호출이 아니라 “결과를 쓰는 것”입니다. 근거 없는 숫자 비율이 0.9 %(gemma-4-31b)에서 26.1 %(glm-4.7-flash)까지 벌어집니다. 같은 도구 결과를 받고도 숫자를 지어내거나 잘못 읽는 빈도가 모델마다 다르고, 이것이 veneta 팀이 답을 검사로 묶어 두는 이유입니다.
- 이름 노출은 호출 형식이 모델의 “말투”와 안 맞을 때 생깁니다. llama 9.8 %, otel 5.5 %가 높고, 나머지는 1~3 %입니다. vLLM의 모델별 파서가 1차로 막고, veneta의 검사가 남은 것을 잡아 바꿔 씁니다.
조건
- 장비 1대(DGX Spark GB10), vLLM, 모델별 서빙: gemma-4-31b FP8-Dynamic·파서 gemma4 / otel-31b FP8·gemma4 / gemma-4-12B bf16·gemma4 / qwen3.8-27b FP8·hermes, 사고 끔 / exaone-4.0.1-32b bf16·hermes, 사고 끔 / llama-3.3-70b FP8-dynamic·llama3_json / glm-4.7-flash bf16·glm47, 사고 끔 / mistral-small-3.2-24b FP8·mistral.
- 턴은 2026-09-22 ~ 10-04의 세 캠페인(운영 14문항, veneta-bench 12문항(기억 능력 벤치마크)과 그 확장 세트, 레이어 비교 실행)에서 왔고, 모델마다 섞인 비율이 다릅니다(실행 파일에 세트별 턴 수가 있음). 그 사이 루프도 바뀌었습니다(9-27부터 코드 기반 검사가 Critic 판정에 앞섬). 그래서 이 비율은 “그 기간 veneta의 루프가 돌려준 최종 답”의 비율이고, 검사는 오늘 코드로 다시 매겼습니다.
- 턴마다 모델 호출은 한두 번(초안, 필요하면 재작성)이고, 깊은 다단계 에이전트 루프가 아닙니다. 그래서 “턴이 깊어질수록 형식이 깨진다”는 현상은 이 표에 없습니다.
- 모델의 지능 순위가 아닙니다. 같은 루프에서 도구를 어떻게 다루었는지의 기록입니다.
다음
콘솔에 이 네 축을 실시간으로 보여 주는 칸(이 세션의 도구 수용률)을 붙이고, 공개 벤치마크의 답변을 쓰는 LLM(writer) 행(클라우드 모델 포함)에도 같은 수를 셉니다. 세는 스크립트(npm run eval:tools)와 실행 파일은 v0.1과 함께 공개하니, 같은 루프를 자기 모델로 돌린 분은 같은 표를 뽑을 수 있습니다.
