# Awesome Life - Full Contents for AI Ingestion > This document contains the full text of the 15 most recent articles from Awesome Life for efficient ingestion by AI search engines and agents. --- ## [AI 에이전트가 같은 기준으로 분석하게 하려면 — 카카오 추천팀의 3층 컨텍스트 설계](https://butteryoon.github.io/kakao-tech/llm-agent/2026/10/29/kakao-ai-analysis-context-design.html) - **Published Date**: 2026-10-29 - **Author**: James Yoon - **Tags**: kakao-tech, llm-agent, data-analysis, context-engineering, claude-md, agent-case - **Description**: 카카오톡 숏폼 추천팀이 AI 에이전트 분석 환경을 개인별 지침 문서(CLAUDE.md)에서 팀 공통 지식베이스로 옮긴 기록. Data Catalog(What), Analyst Persona(How), Task Context(Why) 세 컨텍스트로 데이터 암묵지를 문서화하고, Git 저장소와 Jira를 연결해 누가 분석하든 같은 로그·같은 집계 규칙·같은 검증 절차에서 출발하게 만든 구조를 정리한다. ### Content:
카카오 추천팀은 추천 지표 분석을 AI 에이전트에게 맡긴다. 에이전트는 미리 정리해 둔 지침 문서(CLAUDE.md)를 읽고 SQL을 작성해 기존 Hadoop 환경에서 실행한 뒤, 집계 결과를 리포트로 만든다. 그런데 개발자 A와 B가 같은 추천 지표를 각자의 에이전트로 분석했더니 ‘재생수’가 서로 다르게 나왔다. A는 영상 플레이어의 수집 로그를, B는 앱의 수집 로그를 썼기 때문이다. 둘 다 틀린 데이터는 아니었다. 다만 어느 로그를 어떤 기준으로 써야 하는지가 사람 머릿속에만 있었다.
카카오 기술 블로그에 10월 28일 올라온 「팀이 신뢰할 수 있는 AI 분석 환경 만들기: 추천팀의 컨텍스트 설계」는 이 문제를 풀려고 개인별 지침 문서를 팀 공통 지식베이스로 옮기고 컨텍스트를 세 층으로 나눈 과정을 다룬다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 카카오 추천팀은 분석 자동화의 기반을 개인별 CLAUDE.md에서 팀 공통
AI Data Workspace로 옮겼다. 컨텍스트는 Data Catalog(What: 데이터 암묵지와 집계 규칙), Analyst Persona(How: 분석 절차·해석 원칙·리포트 문체), Task Context(Why: Jira 이슈로 받는 과제 브리핑) 세 층으로 나눴다. 앞의 둘은 Git 저장소에 두고 마지막 하나는 Jira에 둔 채 연결 도구(Skill)로 읽힌다. 이제 누가 분석하든 같은 로그, 같은 집계 규칙, 같은 검증 절차에서 출발한다. 사람의 일은 반복 추출과 정합성 확인에서 문제 정의와 판단 쪽으로 옮겨 갔다.
원문 필자는 지난 글에서 데이터 엔지니어와 분석가만 알던 로그 접근 방법과 분석 기준을 AI로 조회하는 사례를 소개했다. 이 환경을 팀 전체가 함께 쓰자 한계가 세 가지 드러났다.
"원인을 살펴보니 개발자A는 영상 플레이어의 수집 로그를, 개발자B는 앱의 수집 로그를 사용하고 있었습니다. 두 수집기는 영상 소비를 서로 다른 기준으로 기록합니다."
그러다 보니 리포트 수치를 사람이 다시 맞춰 보고 분석이 적절했는지 재확인해야 했다. 팀은 개인 지침 문서에 지식을 쌓는 대신, 팀이 함께 관리하는 지식베이스와 과제 맥락으로 방식을 바꿨다.
에이전트가 분석 전에 읽는 정보를 세 가지 질문으로 나눴다.
| 구분 | 역할 | 답해야 할 질문 | 두는 곳 |
|---|---|---|---|
| 1. Data Catalog | What — 데이터 암묵지 해소 | 무엇을 어떤 기준으로 집계하는가? (데이터의 의미, 로그 선택 기준, 집계 규칙, 주의사항) | Git data_sources/<db>/<table>.md |
| 2. Analyst Persona | How — 분석 방법 가이드 | 어떻게 비교·검증하고 결과를 전달하는가? (분석 절차, 해석 원칙, 리포트 구성과 문체) | Git .claude/references/, commands/, skills/ |
| 3. Task Context | Why — 분석 배경 브리핑 | 왜 분석하며, 어디까지 확인했고, 다음에 무엇을 판단해야 하는가? (목적, 가설, 진행 경과, 검증 결과, 후속 질문) | Jira 이슈·댓글 (연결 도구로 읽음) |
세 층으로 나눈 까닭은 정보마다 재사용 범위와 갱신 이유가 다르기 때문이다. 지표 정의는 여러 분석이 함께 쓰고 비교·검증 방법도 과제에 맞춰 되풀이해 적용한다. 특정 실험에서 무엇을 확인했고 다음에 무엇을 판단할지는 과제가 진행되면서 계속 바뀐다.
"이렇게 나눈 이유는 정보를 재사용하는 범위와 갱신하는 이유가 다르기 때문입니다. 지표 정의는 여러 분석에서 함께 사용하고, 비교·검증 방법도 과제에 맞게 반복해서 적용합니다. 반면 특정 실험에서 무엇을 확인했고 다음에 무엇을 판단할지는 그 과제가 진행되면서 바뀝니다."
원문이 공개한 AI Data Workspace의 구성은 다음과 같다. Data Catalog와 Analyst Persona를 관리하고 분석에 쓴 SQL·결과·근거·리포트를 함께 보관한다.
AI Data Workspace
├── CLAUDE.md # 진입점. 읽을 순서와 금지 사항만 적는다
├── data_sources/
│ └── <db>/<table>.md # [What] Data Catalog. 테이블 하나에 문서 하나
├── .claude/
│ ├── references/
│ │ └── analyst-persona.md # [How] Analyst Persona. 분석 절차·해석 원칙
│ ├── commands/ # [How] 정형 분석 Command. weekly-metric · ab-test · add-data-source
│ └── skills/
│ ├── html-report/ # [How] 리포트 외형·차트
│ └── pangyo-analyst-voice/ # [How] 리포트 문장의 문체
└── analyses/
└── <category>/<date>_<topic>/ # 분석 산출물. README · queries/ · results/ · report.html
(Jira 이슈 · 댓글) # [Why] Task Context. 저장소 밖에서 연결 도구로 읽는다
CLAUDE.md에는 읽을 순서와 금지 사항만 적는다. 실제 지식은 data_sources/와 .claude/ 아래에 흩어 두고 과제 맥락은 저장소 밖 Jira에 남긴다. 에이전트는 Jira 연결 도구(Skill)로 이 맥락을 브리핑받는다.
Data Catalog는 로그 테이블의 스키마 바깥에 있던 팀의 사용 기준을 문서로 옮긴 것이다. 팀은 Google Cloud가 데이터와 시스템 주변 지식을 Markdown 문서로 표현하자며 내놓은 Open Knowledge Format(OKF) 가이드에서 착안했다.
data_sources/<db>/<table>.md)플레이어 로그와 앱 로그 중 무엇을 쓸지, cold 사용자를 ‘최근 N일 동안 유효재생이 없는 사용자’로 볼지는 스키마에 없는 팀의 논리적 정의다. 원천 데이터 구조는 손대지 않고 그 위에 조직이 합의한 지표와 해석 규칙을 얹는다는 점에서, 원문은 이 카탈로그를 semantic layer에 가깝다고 설명한다.
원문의 재생 로그 카탈로그 예시는 다음과 같다(일부 생략).
# play_log
사용자-콘텐츠 시청 로그. 주간 지표·A/B 테스트·전후 비교의 기본 데이터 소스.
집계·파생 지표·필터 규칙의 정의는 이 문서가 기준.
- 테이블 타입: EXTERNAL (Parquet)
- 파티션: date_id(YYYY-MM-DD) + hour_id(HH). 복합 파티션 → 반드시 필터
- 보유 기간: 2025-11 ~ (2026-07-16 실측)
## 컬럼 정보
| 컬럼 | 타입 | 주의사항 |
|---|---|---|
| user_id | string | 원본 식별자. 보고용 산출물에 노출 금지 |
| watch_length | double | 시청 시간, 단위 = 초. `>= y` 로 y초 재생 판정 |
| watch_percentage | double | 1.0 초과 가능 → cap 필수 |
| valid_view | boolean | 유효재생(x초 이상). 서비스 공식 기준 필드 |
| valid_view_flag | boolean | 스키마엔 있으나 미사용 → 아래 절 |
| action_name | string | 분석은 `play_end` 만 |
| reco_type | string | `reco` 가 추천 성능 집계의 기본 모수. 그 외 값은 제외 |
## 집계 규칙
| 지표 | 수식 |
|---|---|
| VVR(유효재생률) | valid_views / total_views |
| y초 재생률 | SUM(watch_length >= y) / total_views |
| 인당 재생수 | total_views / COUNT(DISTINCT user_id) |
## 데이터에서 확인한 사실
- valid_view_flag 는 전 행 false (2026-06-10 확인) → 유효재생 판정은 valid_view 를 쓴다
맨 처음의 재생수 문제는 이 문서 첫 줄에서 풀린다. 카탈로그가 이 로그를 ‘주간 지표·A/B 테스트·전후 비교의 기본 데이터 소스’로 못 박고 CLAUDE.md는 분석을 시작할 때 카탈로그부터 읽게 한다. 그래서 A와 B가 같은 요청을 하면 에이전트는 같은 로그에서 출발한다. 다른 목적에 쓰는 로그는 해당 테이블 문서 첫 줄에 용도가 적혀 있으니, 어느 로그를 고를지도 문서에 남는다.
"재생 로그 카탈로그가 ‘주간 지표·A/B 테스트·전후 비교의 기본 데이터 소스’라고 못 박고, CLAUDE.md가 분석을 시작할 때 카탈로그부터 읽게 하므로, 개발자 A와 B가 같은 요청을 하면 에이전트는 같은 로그에서 출발합니다."
분석 패턴은 과거 분석 사례에서 원칙을 뽑아 만든 지침 analyst-persona.md로 통일했다.
눈여겨볼 대목은 분석 패턴은 쓰되 과거 분석 히스토리는 참고하지 않는다는 원칙이다. 과제마다 목표와 성공 지표가 다르기 때문이다. 어떤 과제는 시청시간을, 다른 과제는 소비한 영상 수를 주요 지표로 삼는다. ‘시청시간이 늘었으니 좋은 변화’라는 과거 결론을 그대로 가져오면 그때의 목표가 지금의 판단 기준이 돼 버린다.
Task Context는 과제의 맥락을 에이전트에게 브리핑하는 층이다. 과제가 진행되는 Jira 이슈를 에이전트가 직접 읽는다.
원문은 실제 과제 하나를 따라가며 세 컨텍스트가 함께 쓰이는 모습을 보여 준다. 수치와 식별 정보를 뺀 가상 사례로 재구성한 것이다.
추천 모델에 영상 임베딩(영상 내용을 숫자 벡터로 표현한 값)을 새 입력 피처로 넣었을 때 추천 성능이 나아지는지 확인하는 과제였다. 온라인 A/B 실험이 시작된 뒤, 같은 Jira 이슈에 질문 두 개가 댓글로 달렸다. 지금까지의 결과로 볼 때 실험을 계속할 가치가 있는지, 조정이 필요한지였다.
| 분석에 필요한 맥락 | Jira에서 확인한 기록 |
|---|---|
| 왜 시작했는가? | 영상 임베딩 피처 추가에 따른 추천 성능 비교 |
| 지금 어떤 단계인가? | 온라인 A/B 실험 진행 중 |
| 지금 답할 질문은 무엇인가? | 실험의 지속·조정 여부 |
에이전트는 다음 순서로 움직였다.
중간 결론은 “관측한 범위에서 손해는 확인되지 않았지만, 이득도 확정하지 못했다”였다. 에이전트는 관측 기간을 늘린 뒤 미리 정한 규칙으로 판정하자고 제안했고 아직 답하지 못한 질문도 따로 적었다. 사람이 검토한 분석 결과는 에이전트가 Jira 댓글로 과제에 남긴다.
"중간 분석의 결론은 “관측한 범위에서 손해는 확인되지 않았지만, 이득도 확정하지 못했다” 였습니다. 에이전트는 관측 기간을 늘린 뒤 미리 정한 규칙으로 판정하자고 제안했고, 아직 답하지 못한 질문도 따로 적었습니다."
[중간점검] 판정 아님
① 계속할 가치: 관측 범위에서 손해 신호 없음. 이득은 미확정
② 조정 필요: 설계 유지. 관측 기간 연장 권장
근거: 완전 관측일만 사용 · 실험 전 기간으로 편차 보정 · 함정 점검 5항목 이상 없음
다음 질문: 연장 관측 후 같은 규칙으로 재판정. 아직 답하지 못한 항목은 README에 정리
판정 규칙(안): 주요 지표 차이가 합의 기준 이상 · 보조 지표 손해 없음 → 롤아웃 검토 (기준값은 팀 합의)
후속 분석은 규칙을 그대로 둔 채 관측 기간만 늘려 진행했다. 이슈 댓글에서 “이득 미확정, 같은 규칙으로 추가 관찰”이라는 현재 상태를 브리핑받아 출발했고 마지막 분석에서 규칙상 ‘실험로직 적용’ 조건을 충족했다. 실제 적용 여부는 기대 효과와 전환에 드는 운영·학습 비용을 견줘 사람이 따로 판단했다.
| 구분 | 과거 | 현재 |
|---|---|---|
| 개발자·기획자 | 분석이 필요하면 분석가에게 요청 | 공통 기준을 바탕으로 자기 실험 결과를 직접 분석하고, 간단한 분석은 직접 수행해 의사결정에 활용 |
| 분석 담당자 | 동료 분석 결과의 정합성 검증, 가설 설정부터 결과 해석까지 폭넓게 관여 | 동료의 분석 결과를 읽고 의사결정에 집중, 측정 방식과 성공 기준 수립 |
| AI 에이전트 | 개인별 지침 문서를 읽고 사람마다 다른 기준으로 분석 | 팀의 Data Catalog와 Analyst Persona, 과제 브리핑을 읽고 같은 기준으로 분석 |
"사람의 노력은 반복되는 추출과 기본적인 정합성 확인에서 문제 정의와 판단으로 집중되었습니다."
원문은 팀 분석 자동화에 적용하려면 세 컨텍스트를 어떻게 구성할지부터 생각해 보라고 권한다. 원문 구조를 바탕으로 바로 가져다 쓸 수 있는 지점을 정리하면 이렇다.
같은 카카오 기술 블로그에서 데이터 분석 에이전트의 시스템 프롬프트·도구 명세서·메시지 배열 설계를 다룬 글은 카카오 테크 — 데이터 분석 에이전트를 만들며 배운 컨텍스트 설계에 정리해 두었다. 그 글이 에이전트 한 개의 컨텍스트 설계를 다룬다면, 이 글은 여러 사람이 같은 에이전트 환경을 공유할 때 무엇을 표준화해야 하는지를 다룬다.
MCP 서버 하나 만드는 건 어렵지 않다. 막히는 곳은 그 서버를 사내 인증 뒤에 붙일 때다. 브라우저 콜백을 받고 토큰을 캐시하고 만료되면 갱신하는 코드를 팀마다 따로 짠다. LY Corporation 기술 블로그에 10월 26일 올라온 「Flava MCP Hub가 걸어온 길: AI 시대를 위한 배관 공사」는 이 반복 작업을 플랫폼이 떠맡게 만든 기록이다. 지금은 MCP 서버 650개 이상이 이 플랫폼 위에서 돈다. 사내에 MCP를 퍼뜨리려는 팀이라면 인증을 어디서 처리할지, Gateway를 직접 만들지를 정할 때 참고할 대목이 많다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: Flava MCP Hub는 사내 프라이빗 클라우드 Flava 위에 올린 전사 MCP 플랫폼으로, 카탈로그·런타임·Gateway를 한곳에서 제공한다. 요청 경로를 Connection(Connector)·Proxy(Gateway)·Authorization·Monitoring 네 층으로 나눴다. 사내 IAM이 DCR·CIMD를 지원하지 않아 생긴 Protocol Gap은 클라이언트 쪽 stdio 프록시인 Connector가 OIDC·토큰 캐시·갱신·Bearer 주입을 대신 맡는 방식으로 풀었다. 인증 준비 시간은 약 1주일(내부 추정)에서 5분으로 줄었다. 처음 쓰던 Rust 오픈소스 Gateway는 ES512 키가 섞인 JWKS 로딩 실패, CORS보다 앞서 도는 인증 미들웨어, 잦은 OOM 때문에 Go로 새로 만든 자체 Gateway로 바꿨다. 다음 과제는 OpenAPI to MCP, Internal Auth, MCP 최신 스펙 대응, CLI·skill 확장, ID-JAG 다섯 가지다.
사내에서 MCP를 쓰는 팀이 늘자 원문이 꼽는 문제 네 가지가 드러났다.
Flava MCP Hub는 이 문제들을 카탈로그(사내 MCP 서버 목록), 런타임(생성·배포·사용), Gateway(권한·접근 제어·인증 흐름) 세 역할로 받는다. 카탈로그에서 서버를 골라 1분 안에 연결하고 새 서버는 인증을 갖춘 채로 5분 안에 배포한다는 것이 원문이 밝힌 숫자다.
"현재 플랫폼 위에서 동작하는 MCP 서버는 650개 이상, 사용하는 팀은 200팀 이상이며, 누적 도구 호출 수는 1,150만 건을 넘었습니다."
요청은 클라이언트에서 출발해 Connector와 Gateway를 지나 MCP 서버에 닿는다. 원문은 이 경로를 네 층으로 나누고 층마다 책임을 따로 뒀다.
| 층 | 하는 일 | 핵심 컴포넌트 |
|---|---|---|
| 1층 Connection | 클라이언트 요청을 처음 받고 사내 인증의 복잡함을 감춘다 | MCP Connector (stdio 연결, OIDC 흐름·토큰 캐시·자동 갱신·Bearer 헤더 주입) |
| 2층 Proxy | 어떤 정책으로 어느 서버에 보낼지 정하고, CORS·헤더 변환·전송 프로토콜을 공통 규약으로 맞춘다 | MCP Gateway |
| 3층 Authorization | 토큰을 먼저 검사하고 사내 여러 인증 방식을 한곳에서 검증한다 | Gateway의 OAuth/OIDC 미들웨어 |
| 4층 Monitoring | 전 구간의 도구 호출·인증 결과·지연 시간을 모은다 | 모니터링 층 |
이렇게 나누면 MCP 서버를 만드는 팀은 프로토콜 처리도 인증 코드도 쓰지 않는다. Gateway가 검증된 요청만 통과시키기 때문이다. 클라이언트 쪽은 설정 한 줄로 Connector에 붙는다.
MCP 표준은 클라이언트가 처음 만나는 서버에도 바로 연결할 수 있어야 한다는 전제에서 출발한다. 그래서 DCR(dynamic client registration)이나 CIMD(client ID metadata document) 같은 방식을 쓴다. LY의 사내 인증 시스템은 IAM 기반이라 클라이언트가 미리 등록돼 있어야 하고 토큰도 사내 시스템에서 받아야 한다. 표준을 따르면 사내 인증을 못 쓰고 사내 인증에 맞추면 표준에서 벗어난다. 이 틈을 각 팀이 메우려면 결국 같은 인증 로직을 팀마다 다시 짜야 했다.
해법은 끊어진 두 지점 사이에 Connector를 끼우는 것이었다.
"클라이언트 입장에서 Connector는 표준 stdio MCP 서버처럼 보입니다. 클라이언트는 기존 stdio MCP 표준에 맞춰 연결하기만 하면 됩니다."
사내 OIDC, 브라우저 콜백, 토큰 캐시, 자동 갱신, Bearer 헤더 주입은 전부 Connector 안에서 끝난다. 요청은 Connector를 지날 때 이미 인증된 상태가 되고 클라이언트는 사내 인증이 있는지조차 몰라도 된다. 효과는 준비 시간에서 바로 보였다.
"내부 추정으로는 이 과정에 대략 1주일 정도가 필요했습니다. 지금은 Connector가 인증 처리를 맡기 때문에 MCP 서버 개발팀은 MCP 서버 로직에만 집중하면 됩니다. 나머지는 Flava MCP Hub가 담당하므로 같은 작업을 5분 안에 마칠 수 있습니다."
처음에는 개발 기간이 약 2개월로 빠듯해 검증된 오픈소스 Gateway를 들였다. 공통 문제를 다시 풀 필요가 없었으니 초기에는 맞는 선택이었다. 운영이 길어지면서 한계가 셋 보였다. 팀에는 Go에 익숙한 사람이 많았는데 그 오픈소스는 Rust 기반이라 장애가 나면 분석과 디버깅이 어려웠다. 프로젝트 로드맵이 사내 요구를 운영에 필요한 속도로 반영해 주지 않았다. 사내 인증용 변경을 upstream PR로 올리거나 fork에서 따로 관리해야 하는 부담도 있었다.
당시 쓰던 버전과 환경에서 실제로 부딪힌 문제는 이랬다.
"사내 인증 시스템이 제공하는 JWKS(JSON Web Key Set)에는 ES512 알고리즘을 사용하는 키가 포함돼 있었습니다. 당시 사용하던 버전은 이 값을 파싱하지 못했고, 실제 토큰 검증에 해당 키를 사용하지 않더라도 JWKS를 로딩하는 단계에서 실패했습니다."
Go로 다시 만든 자체 Gateway는 구조를 사내 요구에 맞춰 새로 설계했고 핵심 동작을 직접 제어한다. 팀에 익숙한 언어와 도구로 장애를 분석할 수 있게 됐다. upstream이나 fork에 기대지 않으니 패치 주기도 짧아졌다. 원문은 판단 기준도 함께 남겼다. 오픈소스는 빨리 시작하기에 좋지만 프로젝트 방향과 운영 요구가 계속 벌어지면 fork와 패치로 따라가는 방식이 오히려 부담을 키운다는 것이다. LLM으로 코드를 분석하고 고칠 수 있게 되면서 직접 개발하거나 이관하는 부담이 예전보다 줄었다는 점도 Go 재작성 과정에서 확인했다고 적었다.
처음 기대한 건 중복 제거와 표준화였다. 운영해 보니 다른 가치가 하나 더 있었다. 모든 도구 호출이 Hub를 거치니 어떤 도구가 실제로 많이 쓰이는지, 어느 팀의 MCP 서버가 다른 팀에서도 재사용되는지가 데이터로 쌓였다. 지금은 어떤 기능을 먼저 공식 지원할지, 어떤 MCP 템플릿을 만들지를 이 트래픽 데이터로 정한다. 연결을 쉽게 하려고 만든 구조가 전사 AI 도구 사용을 들여다보는 관측 지점이 된 셈이다.
원문이 밝힌 준비 중인 방향은 다섯 가지다.
"2026-07-28 버전에서는 요청마다 프로토콜 버전을 선언하는 방식과 server/discover를 통한 서버 정보 조회가 도입됐습니다."
로봇 정책을 학습시키려면 그 전에 할 일이 많다. 코스를 설계하고 3D 에셋을 만들고 시뮬레이션 환경을 조립해야 학습을 시작할 수 있다. NVIDIA 기술 블로그가 10월 23일 공개한 「AI 에이전트로 Microduck 로봇에게 시뮬레이션에서 걷기 가르치기」는 이 준비 과정의 상당 부분을 에이전트에게 맡긴 튜토리얼이다. 로봇을 다루지 않더라도 계획 에이전트가 실행 에이전트에게 일을 넘기는 방식, 그리고 산출물에 무엇을 담는지는 에이전트 파이프라인을 짜는 사람이 눈여겨볼 만하다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 예제 로봇은 Pollen Robotics의 작은 2족 보행 오리 로봇 Microduck이다. RTX Spark에서 도는 Hermes 에이전트와 Nemotron 3.5 Bolt가 프롬프트를 6단계 계획으로 바꾸고 결과물을 인계 패키지로 묶어 Astra에게 넘긴다. Astra는 FreeCAD·Blender를 프로그래밍 방식으로 돌려 USD 에셋을 만들고 무료 공개 라이브러리 SimReady Central Library(OpenUSD 에셋 2,000개 이상)도 함께 쓴다. 정책은 클라우드의 Isaac Lab에서 RTX PRO 6000 Blackwell 한 장, 병렬 환경 4,096개로 적응 학습하고 RTX Spark의 Isaac Sim에서 롤아웃으로 검증한다. sim-to-real 대비는 BAM 서보 모델과 도메인 랜덤화로 하며 실제 하드웨어 배포 절차는 원문 범위 밖이다.
원문 워크플로는 로컬과 클라우드를 오간다.
"NVIDIA RTX Spark는 AI를 활용한 계획 수립과 정책 검증을 위한 로컬 개발 허브 역할을 합니다. 클라우드에서는 NVIDIA Isaac Lab을 사용해 강화 학습으로 로봇 정책을 학습합니다."
| 단계 | 누가 / 무엇으로 | 산출물 |
|---|---|---|
| 1. 장애물 코스 계획 | Hermes + Nemotron 3.5 Bolt (RTX Spark) | 프로젝트 계획, 컨셉 이미지, 에셋 목록, 인계 패키지 |
| 2. 시뮬레이션 에셋 제작 | Astra → FreeCAD, Blender | 편집 가능한 모델 + USD 에셋 |
| 3. 환경 조립 | Astra, Isaac Sim + Newton | 로봇·코스·센서가 들어간 학습 환경 |
| 4. 정책 학습 | Isaac Lab (클라우드) | 경사로·장애물 통과 정책 |
| 5. 정책 검증 | Isaac Sim (RTX Spark) | 완주·넘어짐·충돌·정지 기록, 롤아웃 영상 |
| 6. 실제 로봇 준비 | BAM 서보 모델, 도메인 랜덤화 | sim-to-real 격차를 줄인 시뮬레이션 설정 |
먼저 코스 구성과 Microduck이 배울 동작을 프롬프트로 쓴다. 원문이 예시로 든 프롬프트는 단계마다 무엇을 남겨야 하는지까지 지정한다. 일부를 옮기면 이렇다.
항법과 보행 과제를 포함한 Microduck 시뮬레이션 장애물 코스를 구축하고 테스트하라.
사실적인 컨셉 이미지를 만들고, Astra가 이를 구축하고 테스트하게 하라.
워크플로
준비에는 Hermes와 Nemotron 3.5 Bolt를, 에셋 제작과 시뮬레이션에는 Astra를 사용하라.
1. 조사 및 계획 — Microduck 공식 문서를 검토하여 기능, 제약, 미확인 사항을 요약하라.
2. 컨셉 생성 — 검증된 Microduck 참조 이미지로 사실적인 코스 컨셉을 생성하라.
3. 에셋 식별 — 재사용 가능한 고유 에셋을 추출하고, 반복되는 인스턴스를 묶고, 대표 크롭을 선정하라.
4. 인계 준비 — 계획, 로봇 브리프, 컨셉, 에셋 목록, 크롭, 실행 지침을 패키징하라.
5. 에셋 제작 및 검증 — 시뮬레이션 전에 모든 에셋이 완료되었거나 진행 불가임이 입증되었는지, 사용 가능한 모델이 최소 하나 있는지 확인하라.
6. 조립 및 테스트 — 재현 가능한 지침과 근거를 제공하고, 물리 하드웨어는 조작하지 마라.
Hermes와 Nemotron은 Microduck 저장소와 문서를 훑어 로봇이 할 수 있는 동작과 추가로 확인할 점을 정리한다. 이어 로컬 이미지 생성 모델로 코스 컨셉 이미지를 만들고 이미지를 분석해 재사용할 에셋 목록을 뽑는다. 에셋마다 식별자와 외형 설명을 달고 해당 부분을 잘라 참조로 붙인다. 이미지 밖으로 잘렸거나 다른 물체에 가려진 부분도 기록해 둔다. 그래야 다음 단계에서 이미지로 확인한 정보와 추정할 부분을 구분할 수 있다.
"Hermes는 이러한 결과물을 하나의 인계 패키지로 묶습니다. 전체 프로젝트 계획, Microduck 조사 내용과 출처 링크, 컨셉 이미지, 에셋 목록, 크롭한 참조 이미지, 다음 단계의 지침이 포함됩니다."
패키지가 갖춰지면 Hermes가 Astra에게 작업을 자동으로 위임한다.
큰 컨셉 이미지에서 잘라 낸 크롭은 작고 흐릿하다. Astra는 클라우드 이미지 편집으로 객체를 분리해 선명한 참조 이미지를 만들고 이것을 원본 크롭과 비교해 실루엣·비율·색상이 유지됐는지 확인한다. 원본 크롭은 컨셉 이미지에 실제로 보였던 내용의 기록으로 남긴다.
"이미지로 확정할 수 없는 치수와 가려진 면은 모델링 가정으로 기록합니다. Astra가 FreeCAD에 지시하여 기본 형상과 편집 가능한 CAD 구조를 만든 다음, Blender로 세밀한 형상과 머티리얼을 추가합니다. 두 애플리케이션은 모두 프로그래밍 방식 실행을 통해 로컬에서 실행됩니다."
결과물은 편집 가능한 모델과 내보낸 USD 에셋 두 벌로 저장되고 검토용 미리보기와 출력 점검 결과가 함께 나온다. 새로 만들 필요가 없는 물체는 SimReady Central Library에서 가져온다. 시뮬레이션에 바로 쓸 수 있는 OpenUSD 에셋 2,000개 이상을 무료로 공개한 라이브러리다.
Astra는 준비된 에셋으로 Isaac Sim에서 코스를 조립한다. Isaac Sim은 Omniverse 라이브러리의 렌더링과 센서 시뮬레이션을 맡고 Newton은 이동과 균형을 포함한 Microduck의 물리 동작을 모델링한다. 로봇 구조는 링크(연결된 물체), 조인트(물체 사이의 상대 운동 제약), 액추에이터(구동)로 정의하는데 원문은 이 구성도 에이전트가 거들 수 있다고 적었다. 이렇게 하면 움직이는 로봇, 상호작용할 코스, 그 결과를 피드백으로 돌려주는 시뮬레이션이 한 환경에 갖춰진다.
Isaac Lab에서는 과제마다 관측, 행동, 보상을 정의하고 API로 구현한다. 오픈소스 GPU 가속 물리 엔진 Newton이 그 행동에 따라 로봇이 지면·환경과 어떻게 상호작용하는지 계산한다. 루프는 “시뮬레이션 관측값 → 정책 행동 → 시뮬레이션 동작 → 갱신된 관측값”이다.
이번 과제의 장애물은 경사로와 고르지 않은 지면이다. 출발점은 Astra가 만든 에셋과 Isaac Lab의 Microduck 예제 환경이다. 이 환경에서 사전 학습한 보행 정책에 머리 카메라의 깊이 정보와 로봇 상태 관측을 더해 경사로와 장애물을 통과하도록 추가 학습했다.
"이 적응 학습에는 NVIDIA RTX PRO 6000 Blackwell Workstation Edition GPU에서 병렬 환경 4,096개를 사용했습니다."
원문은 예제 환경 링크를 develop 브랜치로 걸었지만 지금 IsaacLab 저장소에는 그 브랜치가 없다. 위 링크는 같은 경로가 있는 main 브랜치로 바꿨다(flat_env_cfg.py, rough_env_cfg.py, agents/, mdp/가 들어 있다).
학습한 정책은 RTX Spark로 가져와 Isaac Sim에서 돌린다. 학습 중에는 정책이 계속 바뀌지만 평가 때는 고른 정책 하나를 실행해 어디서 성공하고 어디를 보완해야 하는지 본다. 기록할 항목은 코스 완주 여부, 넘어짐, 충돌, 진행이 멈추는 상황이다. 이 기록을 롤아웃 영상과 함께 보면서 환경이나 학습 설정을 고친다.
RTX Spark에 Isaac Sim을 설치할 때는 Windows x86 바이너리를 받으면 된다. 원문에 따르면 Arm의 Windows x86 에뮬레이션으로 바로 실행된다.
원문은 하드웨어 배포 세부 절차를 다루지 않는다. 대신 그 전에 시뮬레이션을 실제 로봇에 가깝게 맞추는 두 가지를 소개한다.
"Isaac Lab은 서보 응답을 모델링하는 Better Actuator Models(BAM)를 지원합니다. 명령 지연, 기계적 백래시(구동계의 미세한 유격), 모터가 공유 배터리에서 전력을 끌어 쓸 때 생기는 전압 강하를 모델링합니다."
BAM 설정을 Microduck 실측값에 맞추면 sim-to-real 격차가 줄어든다. 그래도 센서, 지면 접촉, 제어 타이밍은 실제와 다를 수 있어서 도메인 랜덤화로 물리 파라미터와 관측 노이즈를 현실적인 범위에서 흔들어 정책이 그 차이에 익숙해지게 한다. 원문에는 Isaac Lab에서 학습한 보행 정책으로 실제 Microduck이 걷는 영상도 실렸다.
| 리소스 | 용도 |
|---|---|
| Microduck 저장소 | 로봇 문서·하드웨어 |
| Isaac Lab Microduck 예제 환경 | 학습 환경 출발점 |
| Hugging Face Microduck sim-to-real 튜토리얼 | 실습 가이드 |
| 네이티브 BAM 서보 Microduck 보행 데모 | 데모 |
| Isaac Lab 문서 (v3.0.0-EA) · Isaac Lab Learning Path | 강화 학습·모방 학습 프레임워크 |
| Isaac Sim 문서 | 로봇·환경 시뮬레이션 |
| SimReady Central Library | 공개 OpenUSD 에셋 |
| Omniverse 라이브러리 | 렌더링·시뮬레이션 통합 |
Hermes 에이전트가 배치 작업으로 수집한 RAG·AI 에이전트 분야 주간 논문 보고서(arXiv cs.IR/cs.CL/cs.MA/cs.AI/cs.LG, 2026-10-18~25)에서 일곱 편을 골랐다. 고른 기준은 하나다. 읽고 나서 내 파이프라인에서 오늘 바꿀 게 있는가. 일곱 편 모두 초록에 코드나 데이터 링크가 있고 그중 여섯 편은 작성 시점에 저장소가 실제로 열린다.
TL;DR: ① 영어 코퍼스에서 dense와 late-interaction을 따로 돌리고 있다면, 인덱스 하나로 합치는 179M 모델이 나왔다. ② 좁은 기술 도메인에서는 상용 API 임베딩이 BM25에 크게 밀릴 수 있고 작은 개발 컬렉션에서 고른 설정은 코퍼스가 커지면 뒤집힌다. ③ 다중 사실 질문에서는 “관련 청크 하나”가 아니라 “필요한 청크 전부”를 가져왔는지 재야 한다. ④ 반복 검색·쿼리 재작성·리랭킹을 붙이면 정확도는 그대로인데 “모른다”고 답하는 비율이 떨어진다. ⑤ LLM 심판은 같은 설정을 다시 돌리기만 해도 판정이 21.2% 바뀐다. ⑥ 자기 개선 에이전트에는 스스로 고칠 수 없는 핵심을 코드로 박아 둔다.
수집과 서지 대조는 보고서 단계에서 끝났다. arXiv API로 받은 후보 475편 가운데 코드·모델 공개나 수치 근거가 있는 65편이 남았고 선정분은 초록 페이지의 citation_title과 맞춰 봤다. 아래 일곱 편을 고른 것과 “무엇을 바꿀 것인가”는 초록을 직접 읽고 판단했다.
dense bi-encoder와 late-interaction(ColBERT 계열) 검색기는 서로 다른 질문에서 틀린다. 벡터 하나는 글이 무엇에 관한 것인지를 잡고 토큰 단위 매칭은 정확한 개체와 구절을 잡는다. 그래서 둘을 같이 쓰려면 모델 둘, 인덱스 둘에 점수 융합 단계까지 붙여야 했다.
"Using both today means two models, two indexes and a score-fusion step."
UIBK-Embedding-v1은 179M 파라미터 영어 인코더 하나로 두 표현을 한 번에 뽑는다. dense 임베딩을 토큰 벡터 목록에 벡터 세 개로 끼워 넣고 1차원 태그로 두 종류가 서로 매칭되지 않게 막는다. 그러면 평범한 MaxSim이 곧 “토큰 MaxSim + 가중 dense 코사인”이 된다. 기존 late-interaction 인덱스에 손대지 않고 그대로 올라가며 저자들은 PLAID로 확인했다. BEIR nDCG@10은 59.79로, 같은 체급 최강인 LateOn보다 2.57점 높고 15개 데이터셋 전부에서 앞섰다.
바꿀 것: 영어 문서에 dense와 late-interaction을 따로 돌리고 융합하고 있다면, 이 모델로 PLAID 인덱스 하나를 만들어 기존 융합 결과와 나란히 비교해 본다. 인덱스와 융합 코드가 하나씩 줄어든다. 다만 영어 인코더다. 한국어 코퍼스라면 이 모델 자체보다 “dense 벡터를 토큰 벡터 목록에 끼워 넣는다”는 구조를 참고하는 정도가 맞다.
FormBench는 배합 특허 문서에서 화학 정보를 정밀하게 찾는 검색 벤치마크다. 질의 55,352개에 약 100만 패시지짜리 코퍼스 두 벌을 붙였는데, C0은 방해 문서를 무작위로 뽑았고 C1은 구조가 비슷한 문서를 방해 문서로 넣었다.
결과가 극단적이다. 구조가 비슷한 방해 문서가 섞인 C1에서 OpenAI-3-large는 0.009(C0에서는 0.213)를 받았다. BM25는 C1 0.375, C0 0.467로 버텼고 이 벤치마크 트리플렛으로 추가 학습(TAPT)한 Qwen3-Embed만 BM25를 넘었다(C1 0.4085, C0 0.4835). 저자들은 API 실패의 원인을 도메인 안에서 임베딩 공간이 한데 뭉쳐 버리는 현상(within-domain geometric collapse)으로 짚었다. 그런데 분류와 군집화에서는 API가 TAPT 변형보다도 나았다. 군집화를 잘한다고 정밀 검색까지 잘하는 건 아니다.
바꿀 것: 특허·사양서처럼 용어가 비슷한 문서가 빽빽한 코퍼스에서 API 임베딩만 쓰고 있다면, BM25 단독 결과를 같은 질의에 한 번 돌려 비교한다. 비교 세트를 만들 때는 무작위 방해 문서 말고 구조가 비슷한 문서를 섞어야 이 차이가 드러난다.
olivettigroup/formbench 저장소는 작성 시점(10/25)에 404이고 HF 데이터셋 vinven7/FormBench도 로그인 없이는 열리지 않는다(401). 당장은 설계만 참고할 수 있다생의학 RAG를 대상으로 한 통제 실험이다. 정답 문서는 그대로 두고 검색 컬렉션만 점점 키우면서 초록·평문 전문·계층형 전문 세 가지 표현을 비교했다. 결론은 둘이다. 작은 컬렉션에서 보이던 성능 패턴이 컬렉션이 커지면 일관되게 유지되지 않았고 리랭킹이 도움이 되는지도 코퍼스와 검색 설정에 따라 달랐다. 계층형 표현은 대부분의 종단 비교에서 평문 전문과 같거나 나았는데, 인덱싱 단위는 67% 적었고 저장 공간은 44~56% 덜 들었다.
바꿀 것: 청킹·리랭커 설정을 몇천 건짜리 개발 컬렉션에서 골랐다면, 정답 문서는 고정하고 운영 규모에 가깝게 컬렉션을 불린 뒤 다시 비교한다. 전문을 인덱싱하고 있다면 계층형 표현을 후보에 올린다. 생의학 도메인에서 나온 결과라 다른 도메인에서도 같은 방향일지는 직접 확인해야 한다.
이 논문은 답과 함께 줄 단위 인용을 내게 하는 evidence-based generation(EBG)을 정의하고 정답 여부와 근거를 한꺼번에 채점하는 Ans+Evid 지표를 만들었다. 프런티어 모델 열 개와 오픈 웨이트 모델 세 개를 돌려 보니, 긴 컨텍스트 모델은 피하는데 RAG만 걸리는 한계가 둘 나왔다.
"similarity retrieval surfaces any relevant chunk far more reliably than all required chunks for multi-fact queries, and chunking destroys document meta-information needed to resolve identity-bearing queries."
하나는 유사도 검색이 관련 청크를 하나쯤 가져오는 데는 강하지만 다중 사실 질문에 필요한 청크 전부를 가져오는 데는 훨씬 약하다는 것이다. 다른 하나는 청킹이 문서 메타정보를 날려서 “어느 문서·누구의 것이냐”를 가려야 하는 질문을 풀지 못한다는 것이다. 답만 채점하면 이런 실패는 보이지 않는다. 바늘이 둘인 설정에서 인용이 빠지는 경우가 그렇고 컨텍스트가 모델의 사전 지식과 충돌할 때 Ans와 Ans+Evid 사이 격차가 벌어지는 경우도 그렇다.
바꿀 것: 검색 평가가 hit@k처럼 “관련 청크가 하나라도 들어왔나”만 보고 있다면, 다중 사실 질문에는 필요한 청크가 전부 들어왔는지를 따로 센다. 청크마다 출처 문서 제목 같은 식별 정보가 남아 있는지도 확인한다. 답변 평가에는 인용을 요구하고 답과 근거를 같이 채점한다.
DeclineCraft는 답할 수 없는 질문을 일부러 만든다. 코퍼스 기준일 이후에 추가된 마인크래프트 기능을 묻는 식이다. 27개 LLM을 놓고 답이 없는 질문에서 “모른다”고 인정한 비율(CAR), 답할 수 있는 질문에 시도한 비율, 정확도를 쟀다.
단발 검색을 붙이면 검색이 없을 때보다 CAR이 40개 구성 중 38개에서 유의하게 올랐다. 여기까지는 예상대로다. 문제는 그다음이다. 모델이 컨텍스트를 스스로 판단해 검색을 최대 두 번 더 요청하는 반복 RAG는 단발 RAG보다 CAR을 40개 중 30개에서 유의하게 떨어뜨렸다. 정확도는 그사이 거의 움직이지 않았다.
"Iterative RAG, in which the model self-assesses its context and can request up to two further retrieval rounds, significantly lowers CAR versus single-shot RAG in 30 of 40 configurations (mean 46.4%), with little change in Answer Accuracy (68.5% to 69.3%)."
하이브리드(dense+sparse) 검색에 쿼리 재작성과 리랭킹을 더했을 때도 시험한 12개 모델 전부에서 CAR이 떨어졌다. 검색 없이 같은 가중치에서 thinking을 켜면 13개 중 8개 모델에서 CAR이 평균 14%p 내려갔고 응답이 “불확실하다”에서 “질문의 전제가 틀렸다”로 바뀌었다. 모델 크기와 출시 시점은 정확도와는 상관이 있었지만 CAR과는 유의한 관계가 없었다.
바꿀 것: 반복 검색·쿼리 재작성·리랭킹을 붙이거나 thinking을 켜는 변경은 정확도만 보고 통과시키지 않는다. 회귀 세트에 답이 없는 질문 묶음을 넣고 “모른다”고 답한 비율을 별도 지표로 기록한다. 이번 결과대로라면 정확도는 그대로인데 이 지표만 떨어진다. 더 큰 모델로 바꾼다고 이 문제가 풀린다고 기대하지도 않는다.
Arena-Hard v2.0 프롬프트 500개에 대해 두 모델의 답을 고정해 두고 GPT-4.1 심판을 기준·출력 형식·과제 프레이밍 조합 여덟 가지로 돌렸다. 각 설정은 버전을 고정한 모델에 온도 0으로 그대로 한 번 더 돌렸다.
"Rerunning the default setup moves the aggregate score by about one point but changes the win/tie/loss outcome on 21.2% of prompts."
기본 설정을 다시 돌리면 집계 점수는 1점 남짓 움직이는데, 프롬프트별 승·무·패는 21.2%가 바뀐다. 지시문을 바꾸면 더 흔들린다. 추론 없이 판정만 내게 하고 다른 지시도 몇 개 뺀 설정에서는, 같은 설정을 다시 돌렸을 때의 평균보다 판정이 28.2%p 더 많은 프롬프트에서 바뀌었고 집계 점수는 4.09점 떨어졌다. 반대로 정확성을 우선하도록 기준을 바꾼 설정에서는 판정이 6.7%p 더 많이 바뀌었는데도 집계 점수는 거의 그대로였다.
바꿀 것: LLM 심판의 개별 판정을 회귀 게이트나 선호 라벨로 쓰고 있다면, 같은 설정을 최소 두 번 돌리고 프롬프트 단위 일치율을 집계 점수와 함께 기록한다. 저자들이 내린 권고도 이것이다. 일치율이 낮은 설정이라면 개별 판정 하나로 어떤 응답을 떨어뜨리는 게이트는 다시 생각해야 한다.
Steward는 실시간 웹 데이터로 투자하는 9개 역할의 멀티 에이전트 시스템이다. 투자 자체보다 볼 만한 건 자기 개선의 경계를 어떻게 그었나다. 매일 밤 코드가 모든 거래와 예측을 채점해 메모리에 쓴다. 분기마다 reflector가 프롬프트 개선안을 내면, 결정적(deterministic) 게이트가 이를 되돌릴 수 있게 적용하고 기록된 입력을 재생해 검증한다. 주문 계산, 리스크 규칙, 규율 담당 에이전트의 프롬프트로 이루어진 “불변 핵심”은 어떤 자기 수정도 건드릴 수 없게 타입 시스템으로 막아 두었다.
5개월 실운영(거래일 102일, LLM 호출 1,632회) 동안 섹터 낙폭 24.6%를 손실 0.3%로 막았다. 기록된 입력을 재생한 실험에서는 주입된 지시를 하나도 따르지 않았다.
바꿀 것: 에이전트가 자기 프롬프트나 메모리를 고치는 구조라면, 자기 수정이 닿지 않을 영역(리스크 규칙, 감시 역할 프롬프트)을 목록으로 정하고 프롬프트가 아니라 코드로 막는다. 학습된 변경은 바로 반영하지 말고 되돌릴 수 있는 게이트를 거치게 한다. 반영 전에는 지난 입력을 재생해서 확인한다.
일곱 편에서 하나만 뽑자면 “집계 숫자가 그대로라고 안심하지 마라”다. 반복 RAG는 정확도를 지키면서 “모른다”를 줄였고 LLM 심판은 집계 점수를 지키면서 판정 다섯 개 중 하나를 바꿨다. 당장 할 수 있는 건 셋이다.
하나. RAG 회귀 세트에 답이 없는 질문 묶음을 넣고 “모른다” 비율을 따로 센다. 검색 단계를 늘리는 변경이 이 숫자를 조용히 깎는다.
둘. LLM 심판 설정을 그대로 한 번 더 돌려 프롬프트 단위 일치율을 본다. 비용은 한 번 돌리는 값이고 개별 판정을 얼마나 믿어도 되는지가 바로 나온다.
셋. 다중 사실 질문에서 필요한 청크가 전부 들어왔는지 센다. hit@k만 보고 있었다면 여기서 새는 게 보일 것이다.
임베딩 교체와 코퍼스 규모 재평가는 인덱스를 다시 만들어야 해서 시간이 든다. 위 셋을 먼저 하고 영어 코퍼스에서 인덱스 두 개를 운영 중이라면 UIBK-Embedding 비교부터 붙인다.
Vundle로 굴러가던 .vimrc를 Neovim 0.12의 내장 플러그인 관리자 vim.pack으로 옮겼다. 설정 파일을 그대로 베껴 넣으면 시작부터 오류가 난다 — 없어진 옵션이 있고, 이사 간 저장소 주소가 남아 있고, 제어문자인 줄 알았던 글자가 그냥 글자인 경우도 있다. 여기에 터미널과 Neovide(GUI)에서 Nerd Font를 쓰면서 한글만 다른 글꼴로 떨어뜨리는 설정까지 붙였다. 이 글은 그 과정에서 실제로 걸린 것만 정리한다. (이 글은 Windows PC에서 수행한 설정 작업 기록을 Claude가 정리해 발행했다.)
TL;DR: Neovim 0.12에는 플러그인 관리자가 내장돼 있다(
vim.pack). Vundle 설정을 옮길 때'pastetoggle'·:behave·cscopetag는 Neovim에 아예 없어 시작 오류를 내고,init.lua와init.vim을 같이 두면 E5422가 난다. Neovide에는GuiFont명령이 없다(그건 nvim-qt 전용) —guifont옵션을 쓴다. 한글 폴백은 크기를 마지막 항목에만 쓰고 DirectWrite 패밀리 이름을 써야 한다. 틀린 이름은 오류 없이 조용히 무시된다.
플러그인이 열댓 개뿐인 구성이라 관리자를 하나 더 얹을 이유가 없었다. 후보들의 상태를 보면 선택이 쉬워진다 (GitHub API 조회, 2026-10-25 기준).
| 관리자 | ★ | 기본 브랜치 마지막 커밋 |
|---|---|---|
| vim-plug | 35,781 | 2026-10-15 |
| Vundle.vim | 23,909 | 2024-07-30 |
| lazy.nvim | 21,672 | 2025-12-17 |
Vundle은 2년 넘게 멈춰 있다. 옮길 거라면 굳이 다른 외부 관리자로 갈아타기보다 0.12에 들어온 vim.pack이 낫다고 봤다. add/del/get/update로 끝나고, 락파일과 설치 경로를 Neovim이 관리한다.
설정을 옮기며 실제로 걸린 여섯 가지다. 순서대로 밟으면 시작 오류 없이 넘어간다.
① 없어진 옵션부터 걷어낸다. 'pastetoggle', :behave, cscopetag/cscopetagorder, :cscope/:lcscope/:scscope는 Neovim에 존재하지 않는다. 공식 문서 vim_diff.txt의 “Vim에는 있지만 Neovim에는 없는 것” 목록에 올라 있다. 'pastetoggle'은 붙임 처리가 자동이라 없앴고, cscope 계열은 통째로 빠졌다. 그대로 옮기면 첫 실행에서 오류가 쏟아진다.
vim_diff.txt)"- *'pastetoggle'* *'pt'* Just Paste It.™ |paste| is handled automatically when"
② mswin.vim을 부르고 있었다면 경로를 확인한다. $VIMRUNTIME/mswin.vim이 아니라 scripts/mswin.vim이고, 이 파일이 이미 selection 같은 mswin 동작을 설정한다. :behave mswin을 따로 부를 필요가 없다.
③ 제어문자인 줄 알았던 것이 글자였을 수 있다. F7/F8에 창 이동을 걸어 둔 매핑의 ^W가 제어문자 0x17이 아니라 캐럿(^)과 대문자 W 두 글자였다. grep -P '\x17'로 확인하면 바로 드러난다. 처음부터 동작하지 않았는데 눈치채지 못한 채 그대로 들고 다닌 셈이다(이 .vimrc는 2020-02-07 이후 손대지 않은 파일이다). 옮기기 전에 한 번 훑어볼 값어치가 있다.
④ 가드 변수를 설정값으로 착각하지 않는다. let g:tabular_loaded = 1이 들어 있었는데, 이건 Tabular 플러그인의 “이미 로드됨” 가드다. 즉 Tabular가 한 번도 켜지지 않고 있었다. 지우니 :Tabularize가 생겼다. *_loaded 꼴 변수는 켜는 스위치가 아니라 끄는 자물쇠인 경우가 많다.
⑤ init.lua와 init.vim을 함께 두면 안 된다. 둘 다 있으면 E5422: Conflicting configs로 멈춘다. 옮기는 동안 참고하려면 init.vim.bak처럼 확장자를 바꿔 둔다.
⑥ 저장소 주소를 현재 것으로 고친다. 오래된 설정에는 이사 간 주소가 남아 있다.
scrooloose/nerdtree → preservim/nerdtree
majutsushi/tagbar → preservim/tagbar
plasticboy/vim-markdown → preservim/vim-markdown
vim-scripts/* 미러를 쓰고 있었다면 원본 저장소(preservim/nerdcommenter, jlanzarotta/bufexplorer)로 바꾸는 편이 낫다.
한 가지 확인이 더 필요한 지점도 남겼다. vim.pack.add가 호출 시점에 플러그인을 로드한다고 보고, 플러그인이 읽는 g: 변수를 add 앞에 두는 구조로 작성했다. Vundle은 vimrc를 다 읽은 뒤 로드해서 순서 감각이 다르다. 이 부분은 문서로 한 번 더 확인하는 것을 권한다.
GUI로 Neovide를 붙이면서 가장 오래 헤맨 지점이다. 예전 ginit.vim에는 nvim-qt 시절에 쓰던 설정이 이렇게 남아 있었다.
if exists(':GuiFont')
GuiFont! D2Coding:h12:l
endif
" GuiTabline 0 / GuiPopupmenu 0 / GuiScrollBar 1 도 같은 모양으로 가드가 씌워져 있었다
nnoremap <silent><RightMouse> :call GuiShowContextMenu()<CR>
inoremap <silent><RightMouse> <Esc>:call GuiShowContextMenu()<CR>
vnoremap <silent><RightMouse> :call GuiShowContextMenu()<CR>gv
이 설정이 Neovide에서는 통째로 무용지물이다. GuiFont·GuiTabline·GuiPopupmenu·GuiScrollBar는 nvim-qt 전용 명령이고 Neovide에는 없다. 실제로 exists(':GuiFont')을 물어보면 0이 돌아온다.
다행인 점과 아닌 점이 갈린다. 네 블록은 모두 if exists(...) 가드가 씌워져 있어 조용히 건너뛰어진다 — 오류는 안 나지만 글꼴도 안 바뀐다(가드가 없었다면 E492가 났을 것이다). 반면 우클릭 매핑 세 줄에는 가드가 없다. 매핑 자체는 시작할 때 그대로 걸리는데 GuiShowContextMenu 함수가 Neovide에 없다(exists('*GuiShowContextMenu')이 0). 우클릭하면 E117(알 수 없는 함수)이 나게 된다 — 매핑과 함수 부재는 확인했고, 실제로 눌러 보는 시험까지는 하지 않았다.
Neovide는 평범한 guifont 옵션을 쓴다.
set guifont=MesloLGM\ Nerd\ Font,Paperlogy\ 4:h12
글꼴 이름에 공백이 있으면 \ 로 이스케이프한다. nvim-qt의 GuiFont!도 같은 규칙이라 GuiFont! MesloLGM\ Nerd\ Font:h12처럼 써야 하는데, 어느 쪽이든 Neovide에서는 GuiFont 자체가 없으므로 이 줄을 고쳐 봐야 소용이 없다.
읽는 순서도 알아 둘 만하다. Neovide는 ginit.vim을 읽되 init.lua보다 먼저 읽는다(:scriptnames에서 ginit.vim이 1번, init.lua가 4번). 같은 옵션을 init.lua에서 다시 정하면 그쪽이 이긴다.
영문·숫자·아이콘은 Nerd Font로, 한글만 다른 글꼴로 떨어뜨리고 싶었다. Meslo에 한글 글리프가 없으니 폴백이 필요하다. 규칙이 까다롭다.
규칙 1 — 크기는 마지막 항목에만 쓴다. 폴백은 쉼표로 잇는 목록이고 :h12는 끝에 한 번만 붙인다. 항목마다 쓰면 로그에 Failed to parse guifont: Invalid size가 찍히고 목록 전체가 무효가 되어 기본 글꼴로 돌아간다.
규칙 2 — DirectWrite 패밀리 이름을 써야 한다. 레지스트리나 GDI 기준 이름이 아니다. 페이퍼로지의 경우 Paperlogy 4 Regular로는 못 찾고 Paperlogy 4가 맞다. 이 글꼴은 굵기마다 패밀리가 따로라 Paperlogy 1~9로 나뉜다(4=Regular/Bold, 5=Medium/Bold).
규칙 3 — 틀린 이름은 오류 없이 무시된다. 주 글꼴을 못 찾으면 Font can't be updated 오류라도 나지만, 폴백 항목을 못 찾으면 조용히 넘어간다. 설정은 멀쩡해 보이는데 한글만 그대로인 상태가 된다. 첫 시도가 정확히 이 경우였다.
규칙 4 — 이름은 이렇게 확인한다. Windows PowerShell 5.1에서,
Add-Type -AssemblyName PresentationCore
[System.Windows.Media.Fonts]::SystemFontFamilies | ForEach-Object { $_.FamilyNames.Values }
한글이 든 .ps1을 만들 거라면 BOM 포함 UTF-8로 저장해야 5.1이 제대로 읽는다.
확인은 neovide --log로 파싱된 글꼴 목록을 직접 보는 게 가장 빠르다. 적용 전후로 창을 캡처해 픽셀 차이를 재 보면 영문 줄은 사실상 변화가 없고(평균 1.5) 한글 줄만 크게 바뀐다(59~64).
Windows Terminal은 설정에서 같은 조합을 넣는다.
"face": "MesloLGM Nerd Font, Paperlogy 4"
profiles.defaults와 명시 프로필 두 곳 모두 넣어야 한다. airline의 파워라인 기호를 쓰려면 init.lua에 vim.g.airline_powerline_fonts = 1을 둔다.
한계도 적어 둔다. 격자(그리드) 기반 렌더링이 한글을 2칸으로 잡는데 Paperlogy는 비례 글꼴이라 자간이 넓어 보인다. 획이 굵고 둥글어지는 효과는 있지만 전후 차이가 극적이지는 않다. 고정폭 한글 글꼴을 쓰면 정렬은 깔끔해지는 대신 글꼴 선택지가 줄어든다.
편집 화면에서 마크다운을 그대로 렌더링하려고 후보를 추렸다 (2026-10-25 조회).
| 플러그인 | ★ | 기본 브랜치 마지막 커밋 |
|---|---|---|
| markdown-preview.nvim | 8,021 | 2023-10-17 |
| render-markdown.nvim | 5,190 | 2026-10-10 |
| markview.nvim | 3,667 | 2026-10-18 |
| live-preview.nvim | 443 | 2026-10-22 |
인기만 보면 markdown-preview.nvim이지만 코드가 3년째 멈춰 있다. 편집 화면 안에서 렌더링하는 쪽으로 render-markdown.nvim을 골랐다.
여기서 환경 제약이 하나 걸렸다. 이 노트북에는 C 컴파일러가 없다. 트리시터 파서를 새로 빌드할 수 없다는 뜻이다. 다행히 markdown·markdown_inline 파서는 Neovim 0.12에 내장돼 있어 핵심 기능은 그대로 돌아간다. 컴파일이 필요한 html·latex·yaml 기능만 끄면 된다.
require('render-markdown').setup({
html = { enabled = false },
latex = { enabled = false },
yaml = { enabled = false },
})
이렇게 하니 :checkhealth 경고가 8개에서 1개로 줄었다(남은 하나는 아이콘 제공 플러그인 안내). 기존 vim-markdown과 함께 써도 충돌 목록에 없다. :RenderMarkdown toggle, buf_toggle, preview로 켜고 끈다.
디렉터리 북마크가 두 벌로 따로 논다는 걸 이번에 알았다.
| 명령 | 저장 위치 | |
|---|---|---|
| NERDTree | :Bookmark, 트리에서 B |
~/.NERDTreeBookmarks |
| CtrlP | :CtrlPBookmarkDir, :CtrlPBookmarkDirAdd |
~/.cache/ctrlp/bkd/cache.txt (이름\t경로) |
서로 보이지 않는다. NERDTree 북마크 표는 기본으로 숨겨져 있기도 하다(g:NERDTreeShowBookmarks=0).
쓰기 편하게 F9/F10에 CtrlP 북마크를 걸고, 작업 디렉터리가 바뀌면 열려 있는 NERDTree만 따라가게 했다. 닫혀 있는데 새로 열지는 않는다.
vim.api.nvim_create_autocmd('DirChanged', {
pattern = '*',
callback = function()
local ok, open = pcall(vim.fn.eval, 'exists("g:NERDTree") && g:NERDTree.IsOpen()')
if not (ok and open == 1) then return end
local win = vim.api.nvim_get_current_win()
vim.cmd('NERDTreeCWD')
if vim.api.nvim_win_is_valid(win) then vim.api.nvim_set_current_win(win) end
end,
})
두 함정이 있다. NERDTree는 존재하지 않는 경로가 섞인 북마크 파일을 읽으면 파일을 다시 써서 그 항목을 지운다 — CtrlP 쪽에서 옮겨 올 때 없는 폴더를 먼저 걸러야 한다. 그리고 :CtrlPBookmarkDirAdd는 -n=?로 정의돼 디렉터리 인자 하나는 선택적으로 받지만 북마크 이름은 인자로 받지 못한다 — 이름은 늘 input() 프롬프트로 묻는다. 자동화 스크립트에서 부르면 그 지점에서 입력 대기로 멈춘다.
설정을 실제 환경에 바로 덮지 않고, XDG_CONFIG_HOME·XDG_DATA_HOME을 임시 폴더로 지정한 격리 환경에서 먼저 설치·시작했다. 이식 과정의 오류를 여기서 다 털고 실제 설정에 옮겼다. 수년 묵은 설정을 건드릴 때 특히 값어치가 있다.
GUI 쪽 상태를 확인할 때는 헤드리스 nvim에서 RPC로 붙어 조회했다.
local ch = vim.fn.sockconnect('pipe', '<Neovide 서버 주소>', { rpc = true })
-- exists(':GuiFont'), &guifont, :scriptnames 등을 조회
참고로 0.12에서 nvim --server <주소> --remote-expr는 값을 돌려주지 않고 TUI 클라이언트로 붙어 버렸다.
헤드리스 자동 시험에서 두 가지가 더 걸렸다. VimEnter 자동 명령 안의 :edit는 filetype 감지가 되지 않는다 — 파일을 인자로 열어야 한다. 그리고 세션의 첫 RenderMarkdown disable이 반영되지 않는 현상을 봤는데, 원인은 확정하지 못했다. 화면 갱신이 없는 환경 탓일 수 있다는 정도까지만 적어 둔다.
vim_diff.txt — Vim과 다른 점당근마켓 커뮤니티홈팀이 LLM 주제 분류 모델을 Gemini에서 OpenAI GPT-5.6으로 교체한 직후, 단가는 20% 내렸는데 요청당 비용은 3.2배가 뛰었다. 에러 한 줄 없었다. 원인은 프롬프트 캐시 히트율이 85.8%에서 2.3%로 무너진 것. GPT-5.5까지는 2,048토큰 간격 자동 구분점이었으나 GPT-5.6부터는 가장 최근 메시지 끝에만 구분점을 찍는 방식으로 바뀌었기 때문이다. 이 글은 세 제공사(OpenAI, Anthropic, Google)의 캐시 동작 차이를 비교하고, 프로덕션에서 즉시 적용 가능한 명시적 브레이크포인트 설정법과 진단 방법을 정리한다.
(이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 모델 교체 시 단가표만 보지 말고 프롬프트 캐시 규칙을 반드시 확인하라. GPT-5.6+는 자동 구분점이 ‘최근 메시지 끝’ 하나로 고정돼 있어 고정 프롬프트+가변 입력이면 캐시가 매번 새로 저장만 된다(쓰기 할증 1.25배). 해결은
prompt_cache_breakpoint로 고정부 끝에 명시적 구분점을 찍고prompt_cache_options.mode: explicit로 자동 구분점 끄기. Anthropic은cache_control: {type: ephemeral}를 system/message 블록에, Gemini는 explicit cachedContent로 선업로드. 캐시 히트율은 토큰 기준으로 하루 이상 운영 트래픽에서 측정해야 한다.
당근마켓은 커뮤니티 피드 글의 주제 분류에 LLM을 사용한다. 요청 구조는 고정된 지시문(카테고리 목록·규칙·예시) + 가변 입력(글 본문) 형태다. 2026년 8월 Gemini에서 GPT-5.6으로 모델을 바꾸자:
"교체 전후의 응답을 나란히 놓으면 달라진 곳은 사용량 정보 안의 캐시 필드 하나뿐이었어요. 캐시가 깨져도 에러는 나지 않아요. 비용만 늘어요."
원인은 GPT-5.6부터 자동 캐시 구분점(breakpoint) 위치가 ‘마지막 메시지 끝’ 하나로 변경됐기 때문이다. 기존 2,048토큰 간격 구분점에서는 긴 고정 지시문 안에 여러 구분점이 생겨 고정부가 재사용됐으나, 이제는 ‘지시문+글A’ 전체가 한 덩어리로 저장돼 ‘지시문+글B’와 매칭되지 않는다.
LLM은 입력 전체를 prefill 단계에서 읽으며 K(Key)와 V(Value) 벡터를 생성해 KV 캐시에 쌓는다. 프롬프트 캐시는 이 KV 캐시의 앞부분을 요청 간에 재사용하는 기능이다.
"프롬프트 캐시는 응답 캐시가 아니에요. 응답 캐시는 같은 질문에 저장해 둔 답을 그대로 돌려줘요. 프롬프트 캐시는 입력을 읽는 계산만 재사용하고 출력은 매번 새로 만들어요."
중요: 토큰 하나만 달라도(K에 위치 정보 포함) 그 뒤 K/V는 모두 달라진다. 시각·요청 ID·JSON 키 순서·도구 목록 순서·출력 스키마·reasoning effort 설정 등이 앞부분을 흔든다.
| 항목 | OpenAI (GPT-5.6+) | Anthropic (Claude Opus 5.5 등) | Google Gemini |
|---|---|---|---|
| 기본 활성화 | 자동 켜짐 | 수동 활성화 (cache_control) |
자동 켜짐 (implicit) |
| 자동 구분점 | 최근 메시지 끝 1개만 | 마지막 블록 끝 1개 (요청 바깥) | 비공개/문서 미명시 |
| 명시적 구분점 | prompt_cache_breakpoint + mode: explicit |
cache_control: {type: ephemeral} 블록 내 (최대 4개) |
explicit cachedContent 선업로드 (별도 저장료) |
| 최소 길이 | 1,024 토큰 | 모델별 상이 (512~4,096) | 2,048~6,144 토큰 |
| 유지 시간 | 30분 (고정, ttl: "30m") |
5분 기본, 1시간 선택 가능 (쓰기 2배) | implicit ~24시간, explicit 60분 기본 |
| 쓰기 할증 | 1.25배 (GPT-5.6+) | 1.25배(5분), 2배(1시간) | implicit 무료, explicit 저장료 별도 |
| 히트 확인 필드 | usage.input_tokens_details.cached_tokens |
usage.cache_read_input_tokens |
usageMetadata.cachedContentTokenCount |
| 진단 기능 | prompt_cache_options.comparison_response_id |
diagnostics 파라미터 |
없음 |
"그런데 GPT-5.6에서 자동 구분점의 위치가 바뀌었어요. GPT-5.5 : 2,048토큰 간격으로 찍어요. GPT-5.6 이후 : 가장 최근 메시지의 끝에 하나 찍어요. GPT-6 계열도 같아요."
GPT-5.6 이후 모델에서 고정 프롬프트+가변 입력 패턴을 쓰려면 자동 구분점을 끄고 고정부 끝에 명시적 구분점을 찍어야 한다.
{
"model": "gpt-6.1-sol",
"prompt_cache_options": { "mode": "explicit" },
"input": [
{
"role": "developer",
"content": [
{
"type": "input_text",
"text": "(매번 같은 지시문, 규칙, 예시)",
"prompt_cache_breakpoint": { "mode": "explicit" }
}
]
},
{ "role": "user", "content": "(요청마다 바뀌는 입력)" }
]
}
prompt_cache_options.mode: explicit → 자동 구분점 비활성화 (매번 바뀌는 입력에 쓰기 할증 방지)prompt_cache_breakpoint 붙은 블록까지가 한 덩어리로 저장 → 입력이 바뀌어도 지시문 덩어리 재사용당근마켓은 사내 LLM 플랫폼 템플릿 첫 변수 앞에 구분점을 찍도록 수정해 히트율 95% 회복, 요청당 비용 약 1/5로 감소.
"고친 뒤 주제 분류의 히트율은 95% 안팎으로 올랐고, 요청당 비용은 약 5분의 1로 줄었어요."
cache_control 블록 내 직접 지정Anthropic은 캐시가 기본 비활성화라 요청에 cache_control을 붙여야 한다. 고정 지시문+가변 입력 패턴에서는 system 블록 끝에 찍는 것이 정석이다.
{
"model": "claude-opus-5-5",
"max_tokens": 1024,
"system": [
{
"type": "text",
"text": "(매번 같은 지시문, 규칙, 예시)",
"cache_control": { "type": "ephemeral" }
}
],
"messages": [
{ "role": "user", "content": "(요청마다 바뀌는 입력)" }
]
}
ttl: "1h"로 1시간 연장 가능 (쓰기 할증 2배, 요청 간격 5분~1시간 사이일 때만 유리)diagnostics 파라미터로 tools_changed 등 미스 사유 확인 가능Gemini implicit 캐시는 기본 켜짐이나 “캐시에서 읽었을 때”만 할인이라고 문서에 명시돼 읽힘 보장 없다. 구분점 위치 제어 불가.
# 1) 고정부 미리 올리기 (cachedContent 생성)
POST https://LOCATION-aiplatform.googleapis.com/v1/projects/PROJECT_ID/locations/LOCATION/cachedContents
{
"model": "projects/PROJECT_ID/locations/LOCATION/publishers/google/models/gemini-3.5-flash",
"contents": [{ "role": "user", "parts": [{ "text": "(매번 같은 지시문, 규칙, 예시)" }] }],
"ttl": "3600s"
}
# 2) 요청에서는 캐시 이름만 부르기
POST https://LOCATION-aiplatform.googleapis.com/v1/projects/PROJECT_ID/locations/LOCATION/publishers/google/models/gemini-3.5-flash:generateContent
{
"cachedContent": "projects/PROJECT_NUMBER/locations/LOCATION/cachedContents/CACHE_ID",
"contents": [{ "role": "user", "parts": [{ "text": "(요청마다 바뀌는 입력)" }] }]
}
응답의 캐시 필드로 토큰 기준 히트율을 측정해야 한다(요청 기준은 후하게 나옴).
// OpenAI Responses API
"usage": {
"input_tokens": 5000,
"input_tokens_details": {
"cached_tokens": 4800, // 캐시에서 읽음
"cache_write_tokens": 0 // 새로 저장 (쓰기 할증)
}
}
// Anthropic
"usage": {
"input_tokens": 200,
"cache_read_input_tokens": 4800, // 캐시에서 읽음
"cache_creation_input_tokens": 0 // 새로 저장 (쓰기 할증)
}
// Gemini
"usageMetadata": {
"promptTokenCount": 5000,
"cachedContentTokenCount": 4800
}
진단 순서 (캐시 의심 시 위부터 순차 확인):
comparison_response_id, Anthropic diagnostics)"캐시가 의심되면 위에서부터 차례로 확인하고 해당하는 단계에서 오른쪽에 적은 대로 고쳐요."
쓰기 할증 1.25배 모델에서 고정부 토큰 기준 평균 비용 배율:
0.1 × h + 1.25 × (1 − h)
h ≈ 22% 미만이면 캐시 없는 것보다 비싸진다(읽기 0.05배 모델도 ≈ 21%). 당근마켓 사례는 h=2.3% → 1.22배로 캐시 없음(1.0)보다 비쌌다.
모델 교체는 코드 한 줄 변경이 아니라 운영 조건 변경이다. 배포 전후로 다음 지표를 운영 트래픽에서 하루 이상 측정해야 한다:
"응답이 맞게 나오는지에 더해 요청당 비용, 응답 시간, 캐시 히트율을 교체 전과 나란히 비교하세요. 이 비교는 몇 건으로는 할 수 없어요. 캐시는 앞선 요청이 데워 둬야 읽히고 요청이 얼마나 자주 오느냐에 따라 달라져서, 몇 건만 보내 보면 실제와 다른 숫자가 나와요."
당근마켓도 배포 다음 날 히트율만 봤다면 닷새가 아니라 하루 만에 알아챘을 것이다. 지금은 구분점을 플랫폼이 자동으로 찍게 하고, 개발자는 “바뀌는 부분은 템플릿 끝에 둔다” 규칙만 지키게 했다.
캐시 규칙은 모델 버전마다 바뀌니 적용 전 최신 문서로 재확인 필요.
--- ## [Nemotron 3.5 Super VL·Bolt 공개 — 데이터센터부터 엣지까지 아우르는 개방형 에이전트 모델군](https://butteryoon.github.io/nvidia/llm-model/2026/10/23/nemotron-3-5-super-vl-bolt.html) - **Published Date**: 2026-10-23 - **Author**: James Yoon - **Tags**: nvidia, nemotron, llm-model, llm, open-model, agent, multimodal - **Description**: NVIDIA가 120B 파라미터 멀티모달 Super VL과 엣지용 74B/4B Bolt 모델을 오픈 가중치로 공개했다. Hugging Face·Ollama·vLLM에서 바로 내려받아 로컬·클라우드 어디서든 에이전트 워크로드에 쓸 수 있다. ### Content:NVIDIA 한국 블로그에 10월 22일 올라온 「데이터센터부터 데스크톱까지 개방되다: 최고 효율의 Super VL 및 Bolt 모델로 Nemotron 제품군을 넓히는 NVIDIA」를 읽고 정리했다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: NVIDIA가 Nemotron 3.5 제품군에 120B 파라미터 멀티모달 Super VL과 엣지·로컬용 Bolt 74B-A9B(24GB), Bolt E4B(4GB)를 추가로 공개했다. 세 모델 모두 오픈 가중치로 Hugging Face에서 즉시 내려받을 수 있고, llama.cpp·Ollama·LM Studio·Unsloth·vLLM을 지원한다. Super VL은 프런티어급 지능을 1/5 크기로 구현해 대량 에이전트 워크플로우에, Bolt 계열은 RTX/DGX Spark·Jetson 같은 온디바이스 환경에 최적화됐다. NeMo·NIM·공개 데이터셋으로 포스트트레이닝·커스터마이징 파이프라인도 함께 제공돼, 조직이 자체 데이터·보안 요건에 맞춰 모델을 직접 손보고 배포할 수 있다.
NVIDIA가 멀티모달 에이전트 작업에 최적화된 120B Super VL과 온디바이스 배포용 74B/4B Bolt 모델을 오픈 가중치로 즉시 사용 가능하게 공개했으며, NeMo·NIM·공개 데이터셋으로 커스터마이징·운영 파이프라인까지 함께 제공한다.
"Nemotron 3.5 Super VL은 대량 에이전틱 워크플로우를 위해 동급 최고 수준의 프런티어급 지능을 제공합니다. 동급에서 가장 빠른 오픈 에이전틱 모델로 그다음으로 빠른 모델보다 5배 빠른데요."
| 모델 | 파라미터 | 양자화 | 타깃 메모리 | 타깃 하드웨어 | 공개일 | |——|———-|——–|————-|—————|——–| | Bolt 74B-A9B 24GB | 74B (A9B MoE) | 네이티브 2비트 | 24GB | RTX/DGX Spark, DGX Station, RTX PRO, GeForce RTX PC | 즉시 (10/16 출시) | | Bolt E4B 4GB | 원문 미공개 | - | 4GB | GeForce RTX, Jetson, RTX/DGX Spark | 2026-10-23 |
"Super VL과 Bolt 74B-A9B 24GB는 지금 바로 쓸 수 있고, Bolt E4B는 10월 23일 공개됩니다. 이들 세 가지 오픈 모델은 대규모 엔터프라이즈 서버부터 엣지 기기와 로컬 하드웨어까지 에이전트 배포의 전 영역을 아우릅니다."
"NVIDIA NeMo와 Python 기반 파이프라인, 공개 데이터셋이 맞춤 구성을 뒷받침합니다. NVIDIA Dynamo에서 이 모델을 구동하면 지연 시간을 85% 낮추면서 최대 8배 많은 사용자에게 서비스할 수 있습니다."
원문은 Super VL을 NVIDIA 최대 리즈닝 모델의 약 1/5 크기로 그에 견줄 만한 프런티어급 지능이라고 표현한다. 속도 쪽 주장은 두 가지다 — 동급에서 가장 빠른 오픈 에이전틱 모델이며 그다음으로 빠른 모델보다 5배 빠르고, 차트 설명에서는 동급 대비 최대 5배 높은 처리량을 든다.
다만 원문은 Artificial Analysis Intelligence Index 차트를 싣기만 하고 점수를 본문에 적지 않았다. 어떤 모델과 몇 점 차이인지는 이 글에서 확인할 수 없다. 숫자로 비교하려면 지표 사이트나 영어 기술 블로그를 따로 봐야 한다.
Bolt 74B-A9B 24GB는 네이티브 2비트 양자화로 24GB 메모리에 올라간다. 원문이 든 타깃은 GeForce RTX PC, DGX Spark, DGX Station, RTX PRO 워크스테이션, 그리고 10월 16일 나온 RTX Spark 노트북이다.
의미는 분명하다 — 클라우드 API 없이 로컬에서 에이전트 워크플로를 끝내는 쪽을 겨냥한다. 프라이버시·지연 시간·비용 때문에 로컬을 원하던 수요다. llama.cpp·Ollama·LM Studio·Unsloth·vLLM 지원이 공개 시점부터 갖춰진 것도 진입 장벽을 낮춘다. 다만 원문에 특정 지포스 모델명이나 VRAM 조합은 나오지 않으므로, 손에 있는 장비에서 실제로 돌지는 직접 확인해야 한다.
가중치가 닫힌 모델은 공급자의 정책과 데이터 소재지 제약을 따라야 한다. Nemotron 3.5 제품군은 개방형 가중치·공개 데이터셋·학습 레시피·NeMo 파이프라인·NIM 패키징을 모두 제공해 조직이 자체 인프라·자체 데이터·자체 보안 정책 아래 모델을 직접 손보고 배포할 수 있게 한다. 원문 표현대로 “통제권은 두 방향으로 작동한다”: 배포 위치 자유 + 모델 직접 수정 자유.
토스 DataOps 팀이 앱 로그 정의 업무를 AI 스킬로 자동화한 과정을 공유했다. 비개발자인 DataOps Manager(DOM)가 수동으로 진행하던 로그 명세 작성·검증·등록 전 과정을 스킬·CLI·플랫폼이 분업하는 구조로 재설계했고, 개인 도구에서 시작해 팀 전체가 쓰는 표준 도구로 발전시켰다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 토스는 로그 정의 업무에 AI 스킬을 도입해 ‘규칙 확인→맥락 조회→명세 제안→CLI 검증→플랫폼 등록’ 전 과정을 자동화했다. 스킬은 판단을 안내하고,
lctl이 형식 규칙을 실시간 검사하며, 로그센터가 위반 명세를 차단한다. 도메인 맥락이 규칙보다 품질을 좌우함을 발견해, 앞으로는 도메인 지식을 지식 베이스로 축적해 스킬이 직접 참조하도록 할 계획이다.
토스 앱에서 발생하는 사용자 행동 로그는 서비스 품질 분석의 기초 데이터다. 로그가 처음부터 정확하고 일관되게 정의되지 않으면 분석 결과도 믿을 수 없다. 이를 위해 토스는 DataOps Manager(DOM) 직군을 두고, 로그 명세를 한곳에서 관리하는 로그센터 플랫폼을 운영한다.
원문이 드는 로그 정의의 네 조건은 이렇다.
"로그를 정의할 때에는 로그를 정해진 형식에 따라서, 도메인 안의 맥락을 이어서, 분석에 필요한 것만 남기면서, 정책과 안전을 지켜서 정의해야 해요."
문제는 규칙은 문서(‘앱로그 백과사전’)에 정리돼 있지만, 도메인 맥락은 담당 DOM의 머릿속에만 있다는 점이다. 기존 명세 검색은 가능하지만, 맥락까지 고려해 일관되게 정의하려면 개인의 경험과 기억에 의존할 수밖에 없었다.
한 DOM이 자신의 경험을 담아 만든 개인용 스킬에서 시작해, 누가 어떤 도메인에서 작업하든 쓸 수 있는 팀 표준 스킬로 확장했다. 이 스킬은 로그 명세를 ‘대신 찍어내는 생성기’가 아니다. 다음 순서로 판단을 안내한다.
"새 로그를 만들기 전에 '앱로그 백과사전'의 표준을 확인하고 도메인의 기존 로그 명세를 끝까지 조회해 재사용할 수 있는지 먼저 살피고, 실제 반영은 사람이 확정한 뒤에만 실행해요."
스킬 실행 흐름
lctl로 형식 규칙 검사 통과 시 로그센터 반영| 계층 | 도구 | 역할 |
|---|---|---|
| 판단·안내 | 로그 정의 스킬 | 맥락에 따른 판단 안내, 불확실한 부분은 사람에게 질문, 작업별 필요 문서만 찾아 읽도록 내비게이션 제공 |
| 형식 검증 | lctl (로그센터 CLI) |
로그 이름 형식 등 기계 판정 가능 규칙을 저장 전 실시간 검사, 규칙 변경 시 스킬 수정 없이 최신 기준 자동 적용 |
| 강제·거부 | 로그센터 | 규칙 위반 명세의 발행 거절, 최종 게이트키퍼 |
"로그 이름 형식처럼 기계가 판정할 수 있는 규칙은 `lctl`이 저장 전에 검사하고, 로그센터는 규칙에 맞지 않는 명세의 발행을 거절해요. 형식 규칙은 스킬에 적어두지 않고 실행할 때마다 `lctl`에 묻기 때문에, 규칙이 바뀌어도 스킬은 늘 최신 기준을 따를 수 있어요."
핵심 설계 원칙: 형식 규칙은 스킬에 하드코딩하지 않고, 실행 시점마다 lctl에 위임한다. 이렇게 하면 규칙이 바뀌어도 스킬을 고칠 필요가 없다.
처음엔 규칙과 절차를 한 문서에 담았으나, 문서가 길어질수록 AI가 중요한 규칙을 놓쳤다. 프론트엔드 개발자 기술 검토를 거쳐 작업별로 문서를 분할하고, 스킬에는 ‘해당 작업에 필요한 문서만 찾아가는 안내’만 남겼다. 이제 AI는 매번 긴 문서를 읽지 않고, 현재 작업에 필요한 조각만 읽는다.
기존에는 업무 도구 개선 시 실사용자가 기획 과정에 맥락을 전달하고, 플랫폼 조직이 개발했다. 이번에는 업무를 가장 잘 아는 DOM이 AI를 활용해 직접 스킬을 만들었고, 플랫폼 조직(로그 프로덕트팀)은 검토 후 lctl에 통합·배포만 맡았다.
"이번 기회로 일하는 방식도 달라졌어요. 기존에는 업무 도구를 개선할 때, 실사용자로서 필요한 기능과 업무 맥락을 기획 과정에 전달했어요. 하지만 이번에는 그 맥락을 가장 잘 아는 저희가 AI를 활용해 필요한 도구를 직접 만들었어요."
각자 맡은 도메인의 기정의 로그 명세를 정답지로 두고, 같은 화면을 스킬로 다시 정의해 비교하는 평가를 반복했다. 평가할수록 분명해진 사실: 정의의 품질을 좌우하는 건 규칙이 아니라 도메인의 맥락이다.
평가에서 걸린 문제와 그에 대한 처방이 구체적이다.
| 발견한 문제 | 적용한 해결 |
|---|---|
| 기존 로그를 찾기 어렵다 | 카테고리 기반 추론 |
| 도메인마다 이름이 제각각이다 | 유사 이름 검사 |
| 도메인 지식이 관리되지 않는다 | 표준 도메인 입력 방식 + 맥락 추가 |
앞으로는 도메인별 로그 이름·파라미터 의미·그렇게 정한 이유를 지식 베이스로 축적해, 스킬이 로그 정의 전에 이를 먼저 읽게 할 계획이다. 이를 통해 복잡한 유저 플로우 로그도 더 정확하고 일관되게 정의할 수 있을 것으로 기대한다.
이 사례는 에이전트/스킬 기반 자동화를 개발 환경에 도입할 때 참고할 만한 패턴을 보여준다.
lctl CLI / 로그센터 플랫폼 (사내 도구, 공개 저장소 없음)카카오가 자체 언어모델 Kanana-2 LLM의 가중치와 구조를 그대로 물려받아 학습한 비전 인코더 Kanana-2-vision-encoder를 공개했다. GenLIP(생성적 언어-이미지 사전학습) 패러다임으로 다음 토큰 예측 하나만으로 이미지 이해 능력을 끌어올렸고, Sliding Window Attention과 Grouped Query Attention을 결합해 2560×2560 해상도에서 지연 시간 61.8%·메모리 21.8%를 줄였다. 9억·4억·2억·1억 파라미터 4종 라인업 중 Medium(4.26억)과 Tiny(9800만) 가중치는 상업 이용 가능 라이선스로 허깅페이스에 공개됐다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 카카오가 외부 비전 인코더 의존을 벗어나 한국어·한국 문화 이해에 강점을 갖춘 자체 비전 인코더를 개발했다. Kanana-2 LLM 가중치 초기화로 학습 단계 4분의 1 단축(4배 효율), SWA+GQA 구조로 고해상도 지연 시간 61.8%·메모리 21.8% 감소, 프루닝+Full-Vocabulary KL 증류+On-Policy Distillation으로 1억 파라미터 Tiny가 4억 파라미터 경쟁 모델을 앞서는 성능을 냈다. Medium·Tiny 가중치는 상업 가능 라이선스로 공개돼 즉시 사용 가능하다.
카카오는 Google SigLIP2, Meta Perception Encoder 등 공개된 비전 인코더가 있음에도 자체 개발을 택했다. 원문은 세 가지 필연성을 제시한다.
"비전 인코더는 비전 언어모델의 성능에 가장 큰 영향을 주는 모듈입니다. 이를 직접 설계해야 시각 정보를 추출하는 단계부터 성능 개선의 큰 축을 열 수 있습니다."
"기존 비전 인코더는 한국 문화와 한글 인식에서 부족한 모습을 보였기에, 국내 이용 환경에 필요한 시각 이해 능력을 강화하기 위해서는 자체 비전 인코더는 선택이 아닌 필수였습니다."
"카카오는 다양한 서비스를 운영하기에 각 서비스 특성에 맞춘 모델이 요구됩니다. 특히 온디바이스 환경에는 매우 작은 비전 인코더가 들어가야 하는데, 비전 인코더에 대한 자체 기술력이 없다면 모델 개발 자체가 어려워집니다."
첫째, 비전 인코더는 VLM 성능의 핵심 모듈이므로 직접 설계해 성능 개선의 주도권을 쥐어야 했다. 둘째, 한국어 문서·메뉴판·문화재 등 작은 한글과 문화적 맥락을 정확히 읽으려면 한국 특화 이해 능력이 필요했다. 셋째, 서비스별로 Large부터 온디바이스용 Tiny까지 다양한 크기의 인코더 라인업이 요구됐는데, 이는 자체 기술력 없이는 불가능하다.
Kanana-2-vision-encoder 학습의 핵심은 GenLIP(Generative Language-Image Pre-training)이다. 통상적인 대조 학습(CLIP 계열) 대신, 이미지를 보고 자세한 설명을 생성하는 다음 토큰 예측을 목표로 한다.
"GenLIP의 학습 목표는 일반 언어모델과 동일하게 다음 토큰 예측(Next Token Prediction)이지만, 주어진 이미지를 참조하여 이미지에 대한 자세한 설명을 생성하도록 학습합니다."
학습 데이터는 Dense Visual Caption으로 구성했다. 메뉴판 예시에서 “돼지양념 숯불구이 170g은 9,900원입니다”, “오른쪽에는 파란 라벨의 맥주병 그림이 보입니다”처럼 작은 글자·색상·위치 정보까지 정확해야만 맞출 수 있는 토큰을 다수 포함시켰다. 손실 함수는 다음 토큰 예측 하나로 단순하지만, 데이터 설계로 비전 인코더가 세밀한 시각 특징을 뽑아내도록 유도했다.
Unified Transformer를 무작위 초기화 대신 이미 유창한 문장 생성 능력을 가진 Kanana-2 LLM 가중치로 초기화했다. 이미 문장 생성 능력은 갖췄으니, 이미지에서 정보를 정확히 뽑아내는 법만 추가 학습하면 된다.
"비슷한 손실에 도달하는 데 필요한 학습 단계가 약 4분의 1로 줄어, 약 4배의 학습 효율 향상을 확인했습니다."
학습 곡선(원문 그림 3)에서 무작위 초기화 대비 동일한 손실 도달 단계가 1/4로 단축됨을 확인했다. 추가로 Kanana-2 LLM 구조(Sliding Window Attention, Grouped Query Attention)를 상속받아 추론 효율도 크게 개선됐다.
Kanana-2 LLM 구조에서 물려받은 두 핵심 요소로 고해상도 이미지 처리의 병목인 어텐션 연산량을 줄였다.
Full Attention은 토큰 수 N에 대해 O(N²) 연산이 필요하다. 이미지 해상도 4배면 토큰 4배, 연산량 16배다. SWA는 각 토큰이 고정된 윈도우 크기 W 안에서만 주변 토큰을 참조해 O(NW)로 낮춘다.
"SWA 레이어에서는 훨씬 적은 일정 범위(윈도우) 내에서만 살펴보기 때문에 계산량이 전체 토큰 쌍에 비례하는 O(N²)에서 토큰 수와 윈도우 크기의 곱에 비례하는 O(NW)로 줄어듭니다."
SWA 레이어를 주력으로 하되, Full Attention 레이어를 적절히 배치해 전역 정보도 놓치지 않게 설계했다.
Multi-Head Attention에서 헤드마다 별도 Key/Value를 두는 대신, 여러 Query 헤드가 Key/Value를 공유하도록 묶는다. Key/Value Projection 연산과 저장 공간을 줄인다.
"여러 Query 헤드가 Key와 Value를 공유하도록 묶습니다. 그만큼 Key와 Value를 만드는 Projection 연산과 저장 공간을 줄일 수 있습니다."
두 구조 결합으로 2560×2560 해상도 기준 지연 시간 61.8% 감소, 최대 메모리 사용량 21.8% 감소를 달성했다(원문 그림 7). 저해상도에서는 이득이 작으나 고해상도로 갈수록 격차가 벌어진다.
학습은 세 단계로 진행되며, 모든 단계에서 전체 파라미터를 학습하되 이미지 전처리와 해상도를 달리했다.
| 단계 | 전처리 | 해상도 |
|---|---|---|
| Stage 1 | Fixed Resolution (비율 재조정) | 224×224 |
| Stage 2 | Native Resolution (원본 비율 유지) | 최대 640×640 |
| Stage 3 | Native Resolution | 최대 1280×1280 |
초기에는 모델이 이미지를 전혀 모르므로 고정 해상도로 학습 효율을 높이고, 점차 원본 비율·고해상도로 확대해 작은 글자·세부 내용 이해력을 키웠다.
학습 완료된 모델이 생성한 캡션을 무수정으로 공개했다.
"특히 이미지 내에서 매우 작게 보이는 '바다'라는 글자까지 정확하게 읽으며 Kanana-2-vision-encoder의 높은 한국 문화와 한글 이해 능력을 자랑합니다."
한국어 OCR·문서 이해와 시각적 위치 인식(Visual Grounding)에서 강점을 보이는 이유다.
9억 파라미터 Large를 확보한 뒤, 프루닝(Pruning) → 지식 증류(Knowledge Distillation)로 Medium(4.26억), Small(2억), Tiny(9800만) 3종을 파생시켰다.
레이어 수(Depth), 내부 차원(Hidden Dimension), 어텐션 헤드, FFN 네 축으로 진행했다.
"레이어는 제거했을 때 Teacher와의 KL 발산 변화가 가장 작은 레이어부터 덜어냈습니다. 내부 차원은 활성값에 주성분 분석(PCA)을 적용해 주요 방향을 남겼습니다. 어텐션 헤드와 FFN은 활성값 중요도에 따라 선택했으며, 어텐션 헤드 선택 시 GQA 그룹 구조를 유지했습니다."
Cross Entropy는 정답 토큰 하나만 강화하지만, Full-Vocabulary KL 증류는 전체 어휘 분포를 Large의 분포에 맞추도록 학습한다. “연보라색”뿐 아니라 “분홍색”, “흰색” 같은 유사 색상에도 학습 신호가 가므로, 작은 모델이 시각·언어 연관성을 처음부터 익히지 않아도 된다.
"Full-Vocabulary KL은 Large가 학습 데이터에서 이미 이해한 시각적·언어적 연관성을 학습 신호로서 활용하므로, Tiny가 시각적·언어적 연관성을 처음부터 직접 파악하지 않아도 됩니다."
1억 파라미터 Tiny에는 On-Policy Distillation을 추가 적용했다. Tiny가 생성 중인 토큰 위에서 다음 토큰 분포를 Large의 분포에 맞추는 방식이다. 원문 그림 13에서 Tiny가 “9,900원”을 “9,000원”으로 읽으려 할 때, Large는 “9”에 높은 확률을 줬고 이 차이를 학습 신호로 썼다.
"Tiny가 '돼지 양념 숯불구이 (170g)의 가격은 9,'까지 생성한 상태에서, Tiny는 다음 토큰으로 '0'에 가장 높은 확률을 부여합니다. 같은 입력을 Large에 보여주면, Large는 다음 토큰으로 '9'에 가장 높은 확률을 부여합니다."
적용 전 “1585”로 잘못 읽던 연도를 적용 후 “1985”로 정확히 읽는 등(원문 그림 14), 작은 모델의 생성 품질을 크게 끌어올렸다.
같은 언어모델(Kanana-2-1.3b-instruct)과 같은 VLM 구조에서 비전 인코더만 바꿔 같은 조건으로 학습·평가했다. 구글·메타·애플·알리바바의 공개 비전 인코더를 상대로 9개 영역 42개 벤치마크를 돌렸다.
9개 영역 중 8개 영역 1위. 특히 시각적 위치 인식(78.0점)과 한국어 OCR·문서 이해(71.6점)에서 큰 격차로 선두.
9개 영역 중 8개 영역 1위. 시각적 위치 인식(67.8점)에서 압도적 1위, 한국어 OCR·문서 이해(65.6점)에서도 우수. 4억 파라미터 경쟁 모델 4종보다 높은 평균 점수(51.81점)를 기록했다.
원문 그림 17에서 Tiny(9800만, 평균 51.81점)가 4억 파라미터 모델 4종을 모두 상회하고, Medium(4.26억, 평균 55.62점)은 평가 모델 중 최고점을 찍었다.
"Kanana-2-vision-encoder-tiny는 9,800만 파라미터에서 평균 51.81점으로, Medium은 4억 2,600만 파라미터에서 평균 55.62점으로 각각 이번 평가의 비교 대상 중 가장 높은 평균 점수를 기록했습니다."
가장 활용도 높은 Medium(426M)과 Tiny(98M) 가중치를 허깅페이스에 공개했다.
라이선스는 Kanana-open으로 연구·개발·상업적 활용 모두 허용된다. Kanana-2 LLM(1.3b-instruct 등)과 조합해 바로 멀티모달 언어모델을 만들 수 있다.
LLM 가중치 재사용으로 비전 모달리티 진입 장벽 낮추기: 이미 검증된 언어모델 가중치로 초기화하면 비전 인코더 학습 비용을 대폭 줄일 수 있다. GenLIP 패러다임은 별도 대조 학습 파이프라인 없이 기존 언어모델 학습 인프라를 거의 그대로 쓴다.
SWA+GQA는 고해상도 VLM 서빙의 실용적 선택지: 2560² 이상 해상도에서 지연 시간·메모리 모두 큰 폭 개선된다. 온디바이스·에지 배포를 노린다면 Tiny(98M) + SWA+GQA 조합이 강력한 기준선이 된다.
작은 모델 증류는 ‘정답 토큰 하나’가 아닌 ‘전체 분포’로: Full-Vocabulary KL과 On-Policy Distillation은 1억 파라미터급에서도 대형 모델 지식을 효과적으로 전이하는 레시피다. 프루닝 시 GQA 그룹 구조 보존, KL 발산 기반 레이어 선택 등 세부 기법도 재현 가능하다.
한국어·한국 문화 특화 비전 이해가 필요하면 이 가중치가 기준선: 한국어 OCR·문서 이해, 시각적 위치 인식 벤치마크에서 공개 모델 중 최고 성능이다. 국내 서비스용 VLM을 만든다면 Kanana-2-vision-encoder를 백본으로 쓰는 것이 합리적이다.
Hugging Face의 ben burtenshaw, Sergio Paniego, merve가 에이전트 포스트 트레이닝 커리큘럼을 한 페이지로 묶어 공개했다. 포스트 트레이닝은 사전학습 다음에 오는 지도 미세조정, 증류, 강화학습 같은 단계를 가리킨다. 에이전트는 여러 턴에 걸쳐 도구를 부르고 결과를 읽은 뒤 다음 행동을 고르므로, 답 하나가 아니라 턴 전체를 놓고 학습시켜야 한다. 커리큘럼 순서는 Hugging Face 유튜브의 라이브스트림 시리즈 ‘Training Agents’를 따르고 코딩 에이전트 훈련을 공통 예제로 쓴다. 이 글에서는 다섯 단계 각각의 학습 신호, TRL 트레이너, 준비물과 함께 원문이 단계별로 걸어 둔 강의·문서·예제 링크를 정리한다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 커리큘럼은 SFT → 증류 → RL → RL 환경 → 하네스와 확장의 다섯 단계로 짜여 있고, 각 단계가 TRL 트레이너(
SFTTrainer,DistillationTrainer,GRPOTrainer,AsyncGRPOTrainer) 하나씩과 짝을 이룬다. 어느 단계에서 시작할지는 지금 손에 든 것으로 정하면 된다. 에이전트 궤적 데이터셋이 있으면 SFT, 교사 모델이 있으면 증류, 답을 자동으로 채점할 수 있으면 RL, 실제로 쓰는 에이전트 하네스가 있으면 5단계다.
원문 맨 앞의 요약표를 옮겼다.
| 단계 | 모델이 배우는 대상 | TRL 트레이너 | 준비물 |
|---|---|---|---|
| 1. SFT | 더 강한 모델이 만든 에이전트 궤적 | SFTTrainer |
에이전트 궤적 데이터셋 |
| 2. 증류 | 교사의 토큰 또는 확률 | DistillationTrainer |
프롬프트, 교사 모델 |
| 3. RL | 답안마다 매긴 점수 | GRPOTrainer |
프롬프트, 보상 함수 |
| 4. RL 환경 | 환경 안에서 행동한 결과 | GRPOTrainer |
태스크, 환경(OpenEnv) |
| 5. 하네스와 확장 | 실제 에이전트의 전체 실행 | AsyncGRPOTrainer |
태스크, 환경, 에이전트 하네스 |
강의는 Post-training Agents 재생목록에 네 번의 세션과 관련 워크숍 두 편이 들어 있다.
에이전트, 하네스, 스캐폴드 같은 용어부터 맞추고 전체 흐름을 한 번 훑는다.
에이전트 궤적을 그대로 따라 하도록 학습시킨다. 궤적은 에이전트가 태스크를 푸는 과정을 도구 호출과 그 결과까지 빠짐없이 기록한 것으로, 대개 더 강한 모델이 만든다. 비용이 싸고 학습도 안정적이다. 다만 모델이 보는 것은 정답 궤적뿐이고 자기가 시도한 결과는 보지 못해서 문제를 풀다 실수하면 거기서 빠져나오는 법을 모른다. 원문은 이 빈틈을 모델 자신의 출력으로 학습하는 온폴리시 증류와 RL이 메운다고 설명한다.
"The model learns to copy agent traces, recordings of an agent solving a task with every tool call and its result, usually produced by a stronger model. It's cheap and stable."
교사 모델이 학생을 가르친다. 교사가 직접 쓴 데이터로 가르치기도 하고 학생이 생성한 토큰에 교사가 매긴 확률로 가르치기도 한다. 교사는 보통 더 큰 모델이지만 MOPD처럼 전문 모델 여럿을 학생 하나로 합치기도 하고, 자기 증류라면 컨텍스트를 더 얹은 같은 모델이 교사가 된다. 토큰마다 값이 하나씩 붙는 촘촘한 신호라서 RL보다 적은 샘플로 학습된다. 대신 학생은 교사가 아는 범위를 넘지 못하고 온폴리시 증류는 학습 스텝마다 교사를 돌려야 한다.
"The signal is dense, one value per token, so training needs fewer samples than RL. On the other hand, the student is limited by what the teacher knows, and on-policy distillation has to run the teacher at every training step."
모델이 자기 출력에 매겨진 점수로 배운다. 답을 쓰면 보상 함수가 채점하고 학습은 점수가 높은 답이 더 자주 나오게 만든다. 교사는 필요 없고 답을 검사할 방법만 있으면 된다. 이 단계에서 쓰는 알고리즘은 GRPO(Group Relative Policy Optimization)로, 프롬프트 하나에 답을 여러 개 뽑아 모두 채점한 뒤 그룹 평균보다 높은 답의 확률을 올린다. 그룹 안에서 답끼리 비교하니 어느 시도가 나았는지 판단하는 모델을 따로 학습시킬 필요가 없다.
"The algorithm used in this step is GRPO (Group Relative Policy Optimization). For each prompt it samples several answers, scores them all, and raises the probability of the ones that scored above the group average."
신호는 증류보다 약하다. 토큰마다가 아니라 답 전체에 숫자 하나가 붙으므로 모델은 여러 번 시도해야 배운다. 평범한 보상 함수를 쓰면 답 하나가 곧 한 턴이고 채점도 한 번뿐이다. 여러 번 행동하고 행동마다 결과를 보게 하려면 다음 단계의 환경이 필요하다.
보상이 환경 안에서 한 행동에서 나온다. 환경은 상태를 유지하고 도구를 노출하며 여러 턴에 걸쳐 응답한다. 도구를 실행하고 무엇이 바뀌었는지 추적하고 최종 결과를 확인하는 것도 환경 몫인데, 코딩 태스크라면 테스트를 돌려 보는 식이다. 에피소드 하나가 답 하나보다 훨씬 길어서 롤아웃 생성이 학습에서 가장 느린 구간이 된다. 트레이너는 3단계와 같은 GRPOTrainer를 쓰고 환경은 OpenEnv로 붙인다.
"The environment runs the tools, keeps track of what changed and checks the final result, for example by running the tests of a coding task. Each episode is longer than a single answer, so generating rollouts becomes the slowest part of training."
롤아웃 하나하나가 원격 샌드박스 안에서 기존 에이전트 하네스를 통째로 돌린 실행이다. 에이전트가 실제로 쓰는 하네스를 그대로 거쳐 학습하므로, 모델은 나중에 돌아갈 바로 그 환경에서 배운다. 생성과 학습은 서로 다른 GPU에서 돌아서 에피소드가 길어져도 트레이너가 놀지 않는다. 트레이너는 갱신한 가중치를 vLLM으로 다시 보낸다.
"Each rollout is a full agent run through an existing agent harness inside a remote sandbox. Training through the same harness the agent uses in practice means the model learns in the setting where it will run."
원문은 순서대로 따라가는 커리큘럼이지만 이미 에이전트를 운영 중인 팀이라면 요약표의 ‘준비물’ 열을 거꾸로 읽는 편이 빠르다. 지금 가진 것과 각 단계의 대가를 맞대 보면 시작점이 나온다.
AsyncGRPOTrainer + vLLM)이 전제다.구글이 2026년 10월 13일 Gemini 4 Argon을 공개했다. 발표문에는 벤치마크 순위 외에도 구글 내부 팀과 얼리 액세스 파트너가 실제로 Argon을 돌려 얻은 수치가 꽤 들어 있다. 이 글은 그중 에이전트를 직접 만들고 운영하는 사람이 당장 따져 볼 만한 것, 즉 가격과 접근 경로, 토큰 한도, 공개 저장소에 반영된 최적화, 안전 장치의 범위만 추려 정리한다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: Argon은 Gemini API 유료 티어(AI Studio·Android Studio)와 Gemini 플랫폼, Antigravity(AI Ultra 구독자)에서 쓸 수 있다. 도입가는 입력 100만 토큰당 $2, 출력 $10이고 캐시 입력은 95% 할인된다. 2026년 11월 30일 이후에는 $4/$20이 된다. 한도는 입출력 합산 1M 토큰이며 긴 출력은 새 continuation protocol 문서를 따라야 한다. 구글은 Antigravity에서 에이전트 코드 제출이 35% 넘게 늘고 롤백은 3분의 1 가까이 줄었다고 밝혔다. ADK 세션 오버헤드 개선(ADK v2.12.0 포함)과 vLLM의 Gemma 4 E2B 2.85배 가속은 공개 저장소에서 직접 확인할 수 있다.
| 대상 | 접근 경로 |
|---|---|
| 개발자 | Gemini API 유료 티어(AI Studio, Android Studio). Google AI Ultra 구독자는 Antigravity와 AI Studio에서도 사용 |
| 기업 | Gemini for business, Gemini API, Google Antigravity |
| 일반 사용자 | Gemini 앱, 검색 AI Mode (Google AI Ultra·Pro 구독자) |
| 연구자 | Antigravity 최고 사용량 티어 6개월 무료 — 과학자 1만 명 대상, 신청서 접수 중(자격·용량·선발 기준 적용) |
| 보안 방어자 | Fairwind Program 가입 시 사이버 가드레일을 뺀 Argon 제공(순차 온보딩) |
Google Antigravity는 구글 내부 도구가 아니라 공개 서비스다. 다만 Argon은 AI Ultra 구독자에게만 열려 있다.
요금은 도입가 기준 입력 100만 토큰당 $2, 출력 $10이다. 캐시된 입력 토큰은 95% 할인된다. 도입 기간은 2026년 11월 30일까지이고 그 뒤로는 $4/$20이 적용되므로 월 예산은 인상 후 단가로 잡아 두는 편이 안전하다. 긴 시스템 프롬프트나 스킬 문서를 매 턴 다시 넣는 에이전트라면 캐시 할인 폭이 체감 비용을 크게 좌우한다.
"The model launches today at an introductory price of $2 per million input tokens and $10 per million output tokens (with cached input tokens at 95% off)." / "After the introductory period expires on November 30, 2026, the price of $4 per 1M input tokens and $20 per 1M output tokens will apply."
Gemini API에서 Argon의 한도는 입력과 출력을 합쳐 100만 토큰이다. 구글은 이 한도 덕분에 Argon이 복잡한 과학·코딩·에이전트 문제를 “더 오래, 더 깊게” 풀 수 있다고 설명한다. 긴 출력을 받으려면 새로 나온 continuation protocol을 써야 하고 설정 방법은 개발자용 long decode 문서와 기업용 Argon 가이드에 있다. 기존 클라이언트 코드를 그대로 붙이기 전에 이 문서부터 확인해야 한다.
"This is enabled by an industry-leading 1M unified input-output token limit via the Gemini API. Read through our documentation for developers and enterprises to learn about the new continuation protocol and ensure the appropriate setup for your needs."
구글 전체 엔지니어링 수치부터 보면, 최근 몇 주 동안 Antigravity에서 Argon을 쓴 팀들의 에이전트 코드 제출은 35% 넘게 늘었고 코드 롤백은 3분의 1 가까이 줄었다. Argon을 쓴 팀 전반의 수치이고 특정 프로젝트 하나에 한정된 결과가 아니다.
"Argon in Antigravity has helped teams increase agentic code submissions by more than 35% while reducing code rollbacks by nearly a third."
개별 사례는 네 가지다.
ADK 성능 개선: Agent Development Kit 팀은 Argon에게 .agents/skills 룰북과 “기존 앱을 깨뜨리지 않고 프레임워크 오버헤드를 없애라”는 한 문단짜리 목표만 주고 밤새 자율로 돌렸다. 결과는 커밋으로 반영됐다. 커밋 메시지를 보면 InMemorySessionService가 읽을 때마다 세션 전체를 깊은 복사하던 부분을 줄였고 OpenTelemetry·인증·LLM flow 모듈은 처음 쓰일 때 import하도록 미뤘다. 50턴 뒤 첫 모델 요청까지 걸리는 시간이 64ms에서 36ms로, 새 프로세스의 ADK import가 1.22초에서 0.97초로 줄었다. 이 커밋은 ADK v2.12.0(2026-10-13 릴리스)에 들어 있으니 InMemorySessionService로 긴 세션을 돌리는 사람은 버전만 올려도 효과를 본다. 과정은 구글 개발자 블로그의 엔지니어링 글에 따로 정리돼 있다.
"Working autonomously overnight, Argon surfaced optimizations, now live in google/adk-python, that cut in-memory session prep time by 40% in long sessions and sped up cold imports by 21%."
vLLM 서빙 가속: A100 한 장에서 vLLM으로 Gemma 4 E2B를 서빙할 때 엔드투엔드 처리량이 초당 약 37,900토큰에서 108,000토큰 이상으로 2.85배 올랐다. 토큰 일치율은 100%였고 품질 저하는 없었다. 몇 달 걸리던 작업을 며칠 만에 끝냈다고 한다. 어텐션 튜닝부터 speculative decoding까지 손댄 내용은 vLLM 업스트림 PR 목록에서 볼 수 있다.
"Using Argon, we achieved a 2.85x end-to-end inference speedup on an A100 via vLLM (accelerating throughput from ~37,900 to over 108,000 tokens per second on Gemma 4 E2B) with 100% token parity and zero quality drop in just a few days, a process that would usually take months."
구글 내부에서는 Antigravity의 /goal 같은 슬래시 커맨드와 커스텀 스킬을 묶어 멀티 에이전트 루프를 돌린다. 이 방식으로 3D 시각화와 게임, 인터랙티브 애니메이션을 브라우저에서 바로 렌더링되는 바닐라 코드로 프로토타이핑하고 있다. 공개된 데모 몇 가지를 보면 이렇다.
로보틱스 쪽에서는 ERQA(Embodied Reasoning) 벤치마크에서 87%를 기록했다. 사람이 콘홀(cornhole)을 하는 영상을 보고 공간 좌표와 전신 관절 움직임을 계산해 시뮬레이션 코드를 스스로 짰고 이 결과를 Apptronik Apollo 휴머노이드에 옮기자 실제 환경에서 연속 7번 성공했다.
"Using slash commands like /goal and prompting for multi-agent loops with custom skills in Antigravity, Googlers are using Argon to prototype complex 3D visualizations, high-fidelity games, and interactive animations in vanilla code that can be rendered directly in the browser."
과학 분야 사례도 여럿 실렸다. AlphaQubit 디코더 추론 처리량을 두 배 가까이 끌어올렸고 Grad 추측의 반례를 더 넓은 부류로 찾아냈다(arXiv:2610.07304). Gamow Labs 비공개 평가에서는 RareBench 57%, LabBench 52.2%를 기록했다. 다만 에이전트 운영자가 자기 환경에 바로 가져올 내용은 아니어서 여기서는 소개만 한다.
Argon을 프로덕션 에이전트에 붙이려는 사람이라면 아래 세 가지를 구분해서 봐야 한다.
"On coding benchmarks where models have no incentive to hold back, shortcut attempts dropped to just 2% on Gemini 4 Argon, our best performance compared to previous Gemini models." / "We used this monitor across internal deployments, capability evaluations, and reinforcement learning training runs"
프롬프트 인젝션 방어도 수치로 공개됐다. Argon은 Gray Swan 간접 프롬프트 인젝션(IPI) 벤치마크에서 1위를 했고 적응형 공격 15회 기준 공격 성공률이 0.7%였다. 웹페이지나 메일, 코드를 읽는 에이전트에는 의미 있는 숫자다. 다만 벤치마크상 0.7%이지 0%는 아니다. 도구 권한 제한이나 외부 입력 격리 같은 자체 가드레일은 계속 유지해야 한다.
"Through adversarial training and automated red teaming, Argon leads the Gray Swan Indirect Prompt Injection (IPI) benchmark, cutting attack success across 15 adaptive attempts to 0.7%."
자세한 평가 내용은 Gemini 4 Argon 모델 카드에 있다.
InMemorySessionService 오버헤드와 import 시간이 줄어든다.RAG 파이프라인에서 문서를 벡터로 바꾸는 일, LLM 트래픽을 걸러내는 분류기를 돌리는 일은 대부분 작은 인코더가 맡는다. 그런데 지금까지는 분류에 강한 인코더와 검색에 강한 인코더가 따로였다. DMIS Lab이 10월 14일 Hugging Face 블로그에 공개한 UltraBERT는 이 둘을 모델 하나로 합쳤다고 주장한다. 무엇이 공개됐고 내 파이프라인에 어떻게 붙이며 도입 전에 무엇을 따져야 하는지 정리한다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: UltraBERT는 150M·380M 영어 인코더이고 컨텍스트는 32K 토큰이다. 여기에 바로 쓸 수 있는 임베딩 모델 UltraBERT-Embed-150M이 함께 나왔고 셋 다 Apache 2.0이다. 핵심 발견은 마스킹 비율이 낮으면 분류가, 높으면 검색이 좋아진다는 것이다. 그래서 5%와 50% 마스킹을 한 배치에 섞고 비율마다 LM 헤드를 따로 뒀다. 저자 측정으로 Embed-150M은 MTEB(eng, v2) 67.24로 200M 이하 dense 임베딩 모델 중 1위이고 32K 길이까지 패스키 정확도 99%를 유지한다. 다만 영어 전용이라 한국어 문서가 중심인 RAG에는 그대로 쓸 수 없다.
| 모델 | 크기 | 용도 |
|---|---|---|
| UltraBERT-150M | 150M | 사전학습 인코더(분류·NER·QA 파인튜닝용) |
| UltraBERT-380M | 380M | 사전학습 인코더 |
| UltraBERT-Embed-150M | 150M | 바로 쓰는 텍스트 임베딩(768차원) |
세 모델 모두 컨텍스트가 32K 토큰이고 라이선스는 Apache 2.0이다. 모델 카드의 언어 태그는 영어(en) 하나뿐이다.
"We're releasing UltraBERT, a family of English encoders (150M and 380M) with a native 32K context, plus UltraBERT-Embed-150M, a ready-to-use embedding model built on top of it. Everything is Apache 2.0 and lives in the UltraBERT collection."
저자들은 150M·380M·1.3B 인코더를 같은 데이터로 학습시키며 레시피를 다시 따져 봤다. 실험에 쓴 토큰을 모두 합치면 70조 개가 넘는다. 실무에 쓸 만한 발견은 세 가지다.
해법은 단순하다. 한 배치에 5% 마스킹 시퀀스와 50% 마스킹 시퀀스를 4:1로 섞는다. 인코더 본체는 공유하고 LM 헤드는 비율마다 따로 둔다. 헤드를 같이 쓰면 두 체제가 출력층을 서로 다른 모양으로 끌어당겨 다툰다는 것이 저자들의 분석이다. 증류는 앞의 규칙대로 5% 헤드에만 걸고 50% 헤드는 일반 MLM으로 학습한다. 사전학습은 2T 토큰이고 마지막 100B 토큰은 32K 컨텍스트로 학습했다.
아래는 150M 모델로 마스킹 전략을 비교한 결과다.
| 전략(150M) | GLUE | BEIR |
|---|---|---|
| 단일 비율 6% | 89.5 | 43.5 |
| 단일 비율 50% | 87.5 | 45.0 |
| 5~50% 균등 샘플링 | 88.0 | 44.2 |
| 5%+50% 혼합, 헤드 공유 | 88.9 | 44.7 |
| 5%+50% 혼합, 헤드 분리 | 89.4 | 45.1 |
"With decoupled heads, one 150M encoder reaches 89.4 GLUE and 45.1 BEIR, matching the best single-ratio model on classification (89.5 at 6%) and beating the best one on retrieval (45.0 at 50%)."
저자들은 최근 인코더들을 과제마다 같은 그리드 서치로 파인튜닝해 비교했고 두 크기 모두 10개 벤치마크 중 9개에서 1위를 했다고 밝혔다. 자주 비교되는 모델만 추렸다. 검색 점수는 각 백본을 MS MARCO로 똑같이 파인튜닝해 잰 값이므로, 완성된 임베딩 모델의 점수가 아니라 백본 자체의 잠재력으로 읽어야 한다.
| 모델 | 크기 | GLUE | BEIR | RAR-b Code | LongEmbed |
|---|---|---|---|---|---|
| ModernBERT | 149M | 88.4 | 42.6 | 29.6 | 63.2 |
| Ettin Encoder | 149M | 88.9 | 42.4 | 31.8 | 60.1 |
| UltraBERT | 152M | 89.5 | 45.2 | 39.1 | 72.0 |
| ModernBERT | 395M | 90.4 | 45.2 | 34.0 | 63.5 |
| Ettin Encoder | 395M | 90.8 | 45.9 | 38.5 | 64.3 |
| UltraBERT | 380M | 91.0 | 47.7 | 47.0 | 74.9 |
긴 문서를 다루는 사람이라면 패스키 결과를 눈여겨볼 만하다. LongEmbed 패스키 테스트에서 512 토큰 모델은 1K를 넘기면 실패하고 8K 모델은 16K·32K에서 급락한다. UltraBERT는 두 크기 모두 32K까지 모든 길이에서 99%를 유지했다. 문서를 잘게 자르지 않고 통째로 넣어도 된다는 뜻이고 분류나 판정 작업에서도 대화 전체를 한 번에 보고 결정할 수 있다.
"UltraBERT holds 99% at every length up to 32K, at both sizes."
RAG에 바로 붙일 수 있는 쪽은 임베딩 모델이다. UltraBERT-150M을 두 단계 대조 학습으로 만들었는데, 1단계는 약 5억 쌍의 약지도 텍스트·코드 쌍, 2단계는 하드 네거티브를 붙인 570만 개 정제 예제(입력 최대 32K)다. 공개 데이터만 썼고 더 큰 임베딩 모델에서 증류하지도 않았다.
| 모델 | 크기 | MTEB(eng, v2) | MTEB(Code, v1) | LongEmbed |
|---|---|---|---|---|
| UltraBERT-Embed-150M | 151M | 67.24 | 73.30 | 79.30 |
| gte-modernbert-base | 149M | 66.26 | 71.66 | 57.0 |
| bge-base-en-v1.5 | 109M | 65.14 | 50.35 | 33.9 |
| nomic-embed-text-v1.5 | 137M | 62.20 | 47.36 | 30.60 |
"On MTEB(eng, v2) it scores 67.24, the highest of any dense model under 200M parameters."
이미 bge-base-en-v1.5나 nomic-embed-text-v1.5로 영어 문서를 임베딩하고 있다면 같은 크기대에서 교체를 검토해 볼 만하다. 차이가 큰 쪽은 코드 검색과 긴 문서다.
transformers>=5.20부터 기본 지원한다. 그보다 낮은 5.x 버전에서는 trust_remote_code=True를 줘야 한다. 긴 입력에는 FlashAttention 2를 권장하며 SDPA도 동작한다.
pip install -U "transformers>=5.20" "sentence-transformers>=6.0"
임베딩은 sentence-transformers로 붙인다.
from sentence_transformers import SentenceTransformer
model = SentenceTransformer(
"dmis-lab/UltraBERT-Embed-150M",
model_kwargs={"attn_implementation": "flash_attention_2", "dtype": "bfloat16"},
)
queries = ["Win big, click now!"]
labels = ["spam", "promotional", "announcement"]
query_embeddings = model.encode(queries, prompt="Instruct: Labeling spam emails\nQuery: ")
label_embeddings = model.encode(labels, prompt="Label: ")
print(model.similarity(query_embeddings, label_embeddings))
프롬프트 규칙은 지켜야 한다. 쿼리에는 Instruct: {task}\nQuery: 접두어를 붙이고 문서는 그대로 넣는다. prompt_name="query"를 쓰면 기본 검색 지시문이 붙는다. 모델 카드에 따르면 위 예제처럼 레이블 문구에는 Label: 접두어를 붙이고 STS·중복 탐지 같은 대칭 과제에서는 양쪽에 같은 지시문을 붙인다.
백본을 직접 파인튜닝한다면 학습률을 낮게 잡아야 한다. 저자들에 따르면 UltraBERT는 다른 인코더보다 최대 10배 낮은 학습률을 선호한다. MNLI에서는 1e-5(150M)·8e-6(380M)가 가장 좋았는데, 다른 인코더는 보통 3e-5~5e-5를 쓴다. 검색 파인튜닝에서는 5e-5(150M)·3e-5(380M)가 가장 좋았고 다른 인코더는 보통 3e-4~5e-4를 쓴다. 평소 쓰던 하이퍼파라미터를 그대로 가져오면 UltraBERT를 과소평가하게 된다.
"Tip: UltraBERT likes lower learning rates than other encoders, by up to 10×. On MNLI our best values were 1e-5 (150M) and 8e-6 (380M), where most encoders prefer 3e-5 to 5e-5."
from transformers import AutoModelForSequenceClassification
model = AutoModelForSequenceClassification.from_pretrained(
"dmis-lab/UltraBERT-150M", num_labels=2
)
공개 체크포인트에는 인코더와 5%(증류) MLM 헤드가 들어 있다. 블로그 공개 뒤 댓글로 요청이 들어와 50% 헤드도 별도 파일(head_50%.pth)로 추가됐다. 스파스 검색기를 학습하려는 사람에게 필요한 부분이다. 교체 방법은 380M 모델 카드에 있다.
AI에 테스트 케이스를 넘기면 Playwright 코드는 나온다. 진짜 문제는 그다음이다 — 그 테스트가 통과했다고 해서, 내가 검증하려던 것을 검증했다는 뜻은 아니다. LINE Plus의 대만 Giftshop QA 김혜영 님이 이 함정에 걸린 뒤 파이프라인을 다시 짠 기록을 정리한다. AI에게 산출물을 맡기는 모든 작업에 그대로 옮겨 붙는 이야기다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: v1.0은 코드를 잘 만들었지만
.first()한 줄로 엉뚱한 컨테이너를 검증하고도 PASS를 냈다. v2.0은 실행 전 게이트와 기댓값을 일부러 틀리게 바꿔 보는 위양성 검증을 넣어 이를 막았다. 원칙은 하나다 — 구현 방법은 AI가 바꿔도 되지만 합격 기준은 바꿀 수 없다. 결과는 회귀 테스트 98개 → 196개, 자동화 전환율 100%, 구축 기간 약 한 달.
출발은 흔한 기대였다. 이미 사람이 정리해 둔 자동화 테스트 케이스를 AI에 넘기면 Playwright 코드가 알아서 나오고, 몇 번 다듬으면 끝날 것 같았다.
v1.0 파이프라인은 다섯 단계였다. ① 테스트 케이스를 읽어 시나리오·스텝·기대 결과로 구조화 ② 실제 브라우저에서 locator 검증·보정 ③ 코드 생성 ④ 실행 ⑤ 리포팅.
"각 단계는 JSON 파일로 연결해 문제가 생긴 단계만 다시 실행할 수 있도록 했습니다. 규칙으로 처리할 수 있는 작업은 코드로 처리하고, 모호한 판단은 AI에 맡기는 방식이었습니다."
단계 사이를 JSON으로 잇는 설계는 그대로 가져다 쓸 만하다. 실패한 단계만 다시 돌릴 수 있어 전체 재실행 비용이 사라진다.
코드는 빠르게 나왔다. 그런데 리뷰하다 보니 테스트는 통과하는데 엉뚱한 것을 보고 있었다.
유형 1 — 컨테이너가 여러 개인데 확인 없이 첫 번째를 골랐다. 홈 화면에 .announcement_list.is_home 클래스를 쓰는 영역이 둘 있었다. 공지 영역과 광고 계획 영역이 같은 클래스를 공유한 것이다. 원본 의도는 두 번째였는데, 파이프라인은 여러 개를 발견하자 .first()를 붙였다.
// NOTE: Multiple containers found (2), using first
const container = page.locator('.announcement_list.is_home').first();
const items = container.locator('.announcement_item');
"코드는 정상적으로 실행됐고 테스트도 통과했습니다. 문제는 제가 검증하려던 광고 계획(廣告方案) 이 아니라 첫 번째 컨테이너인 공지(通知) 영역을 확인했다는 점입니다."
주석까지 친절하게 남겼다는 게 오히려 무섭다. 어느 쪽이 맞는지에 대한 판단이 .first() 한 줄에 묻혔다.
유형 2 — 여섯 개를 검증해야 하는데 하나만 보고 통과시켰다. 오늘 판매 현황 영역의 6개 항목을 모두 확인하는 테스트였는데, 생성된 코드에는 첫 항목만 남았다.
"6개 중 하나만 확인했지만 테스트는 정상적으로 통과했습니다. 원본 테스트 케이스에 있던 검증 항목이 코드로 바뀌는 과정에서 사라진 것입니다."
두 사례의 공통점은 모호할 때 파이프라인이 멈추지 않았다는 것이다. 어떻게든 실행 가능한 코드를 만들었고, 실행에 성공하면 PASS로 처리했다.
목표를 바꿨다. AI가 테스트를 얼마나 많이 만드는지가 아니라, AI가 만든 결과를 사람이 얼마나 빨리 확인하고 믿을 수 있는지를 기준으로 삼았다.
"v2.0의 원칙은 ‘구현 방법은 AI가 바꿀 수 있지만, 합격 기준은 AI가 바꿀 수 없다’로 정리할 수 있습니다."
역할을 셋으로 쪼갠 표가 이 글의 핵심이다.
| 누가 | 무엇을 |
|---|---|
| AI가 자유롭게 바꾼다 | locator 선택, 코드 구조, 대기 방식 |
| 코드로 고정해 못 바꾼다 | 기대 결과, assertion 존재, test.only·test.fixme·test.skip·waitForTimeout·networkidle 금지 |
| 끝까지 사람이 판단한다 | locator가 맞는 요소인지, 원래 의도를 충분히 확인하는지, 제품 버그인지 |
① 명세 초안 — 기대 결과를 코드까지 추적한다. 테스트 케이스를 바로 코드 생성에 넘기지 않고 구조화된 명세를 먼저 만든다. raw_expected에 원본을 그대로 담고, expected_items로 최소 검증 단위로 쪼개고, assertion에 실제 검증 내용을 정의하고, covers로 둘을 잇는다.
- { id: E2, description: "廣告方案 영역 하위 list 항목이 3개 노출된다" }
- { id: A2, description: "廣告方案 영역 하위 list 항목이 3개다", covers: [E2] }
유형 2처럼 검증이 증발하는 문제를 여기서 잡는다.
② 확인 필요 항목(gap) — 애매하면 추측하지 않고 멈춘다. 결과에 영향을 주는 모호한 지점은 질문으로 남기고, 사람이 답하기 전까지 다음 단계로 가지 않는다. “각 항목 숫자를 특정 값으로 단정해야 하나요, 아니면 존재 여부만 확인해야 하나요?” 같은 질문이다. 이 과정에서 자동화 코드뿐 아니라 원본 테스트 케이스의 오류와 모순도 발견됐다고 한다.
③ 게이트 — 검사를 통과하지 못하면 실행하지 않는다. 코드 생성 후 실행 직전에 돌리는 자동 검사 다섯 개다.
validate-spec 명세 형식·필수 항목 (차단)
verify-assertion-coverage 명세의 검증 항목이 코드에 다 들어갔는지 (차단)
safety-check 위험 패턴 없는지 (차단)
gap-scope-lint 검증 범위가 모호한 항목 잔존 (경고)
expected-decomposition-lint 기대 결과가 빠짐없이 쪼개졌는지 (경고)
safety-check가 막는 패턴 목록이 특히 실용적이다. test.only·test.skip·test.fixme는 실행 결과를 오해하게 만들고, waitForTimeout·networkidle은 테스트를 불안정하게 만든다. 근거를 남긴 예외만 허용한다.
④ 위양성 검증 — 기댓값을 일부러 틀리게 바꿔 본다. 게이트를 통과하고 테스트가 돌았어도, 그 테스트가 실제로 기댓값을 보고 있는지는 별개다. 항목이 3개인지 확인하는 테스트라면 기댓값을 4로 바꿔 본다. 이때 실패해야 정상이다.
"여기서 PASS 는 변경한 테스트가 통과했다는 뜻이 아니라, 기댓값을 변경했을 때 대상 assertion 이 정상적으로 실패해 위양성 검증을 통과했다는 의미입니다."
mutation testing의 아이디어를 assertion 동작 확인에 가져다 쓴 것이다.
⑤ 리뷰 패킷 — 사람이 볼 것만 모아 준다. 실제로 확인된 사실과 AI의 분석을 구분해서 보여 주고, 사람 확인이 필요한 항목을 따로 표시한다. locator가 무엇을 가리켰는지 눈으로 보도록 스크린샷도 남긴다. 유형 1처럼 코드만으로 판단할 수 없는 문제는 게이트로 막는 대신 여기로 넘긴다.
"기존에 수동으로 관리하던 회귀 테스트 케이스는 98개였습니다. ... 최종적으로 회귀 테스트 케이스 수를 98개에서 196개까지 늘렸습니다."
QA 본업을 하면서 코드 생성과 실행은 파이프라인에 맡기고, 시간 날 때 대시보드에서 판단할 부분만 봤다는 대목이 이 수치의 맥락이다.
첫째, 선행 비용이 크다. 명세 구조·게이트·위양성 검증·리뷰 패킷을 직접 설계해야 한다. 짧게 쓰고 버릴 자동화라면 오히려 일이 커진다. 오래 유지할 회귀 테스트였기에 값어치가 있었다.
둘째, 사람 판단은 남는다. locator가 의도한 요소를 가리키는지, assertion이 원래 의도를 충분히 확인하는지는 여전히 사람 몫이다.
셋째, 위양성 검증이 만능이 아니다. 개수·텍스트·URL처럼 기댓값을 명확히 바꿀 수 있는 검증에만 통한다. 단순 노출 검증은 자동으로 확인하기 어려워 사람 리뷰로 넘겼다.
그리고 아직 셀러 센터 한 서비스에서만 검증된 단계다. 다른 서비스로 넓히며 공통 영역을 분리하는 것이 다음 목표라고 한다.
"결국 이 워크플로는 사람을 없애는 자동화가 아닙니다. 사람이 직접 판단해야 할 부분을 줄이고, 어디를 봐야 하는지 분명하게 만드는 자동화에 가깝습니다."
이 글은 E2E 테스트 이야기지만, 구조는 AI에게 산출물을 맡기는 모든 파이프라인에 그대로 적용된다.
test.only·waitForTimeout 같은 목록은 사람이 리뷰로 잡으려 하면 반드시 샌다이번 주 arXiv에서 고른 네 편에는 공통점이 있다. 전부 “평가가 통과했는데 실제로는 틀렸다”는 이야기다. 모델을 더 좋게 만드는 연구가 아니라, 내가 지금 쓰고 있는 평가가 무엇을 못 보고 있는지를 지적하는 연구다. 이 중 둘은 저장소가 공개돼 바로 받아 돌려 볼 수 있다.
TL;DR: ① 에이전트 메모리를 다운스트림 QA로만 재면 메모리 연산 분류 정확도가 20%여도 모른다. ② 가드 벤치마크는 도메인 홀드아웃으로 바꾸면 F1이 0.901에서 0.495로 주저앉는다. ③ 에이전트는 입력이 오염돼도 알아채지 못하고 그대로 흘려보낸다. ④ 컨텍스트 압축에는 목표를 같이 넣어야 한다.
수집과 서지 검증은 주간 서베이 스크립트가 했다(arXiv API로 464편을 받아 코드·모델 공개 또는 수치 근거가 있는 61편만 남기고, 선정분은 초록 페이지의 citation_title과 대조했다). 아래 네 편의 선별과 “무엇을 바꿀 것인가”는 사람이 판단해 썼다.
에이전트 메모리 벤치마크 대부분은 최종 답이 맞았는지로 메모리 품질을 매긴다. 문제는 그 점수에 검색 품질과 생성 품질이 섞여 들어간다는 것이다. 메모리가 깨졌는데 답이 맞아 통과하고(거짓 음성), 메모리는 멀쩡한데 답이 틀려 메모리 탓을 한다(거짓 양성).
"Agent memory benchmarks evaluate whether an agent's responses reflect correct knowledge, measuring downstream question-answering accuracy as a proxy for memory quality."
FEB-30은 사실이 시간에 따라 바뀌는 30개 궤적을 6개 진단 범주·3개 난도로 만들어, 매 수집 단계마다 메모리 저장소를 직접 들여다보게 한다. 문서를 알려진 사실 궤적에서 생성하므로 사람 주석 없이 정답이 확정된다.
숫자가 아프다. 한 대표 메모리 시스템에 적용했더니 직접 측정과 다운스트림 QA 측정이 평균 16%p 벌어졌고, 궤적의 44%가 유의미한 괴리 기준을 넘었다. 결정적으로 메모리 연산(생성·갱신·강화·대체)을 올바르게 분류한 비율이 20%였는데, 이 실패는 다운스트림 평가로는 전혀 보이지 않았다.
바꿀 것 — 메모리를 쓰는 에이전트가 있다면 평가에 “저장소 직접 확인”을 한 줄 추가한다. 수집 단계마다 저장소를 덤프해 두고, 사실이 바뀌었을 때 갱신으로 처리했는지 새 항목으로 쌓았는지를 본다. QA 정확도만 보고 있었다면 그 수치는 메모리에 대해 거의 아무것도 말해 주지 않는다.
amazon-science/feb-30-benchmark 저장소는 작성 시점(10/18)에 아직 404다. 지금은 논문의 설계만 참고할 수 있다도구를 쓰는 에이전트에는 위험한 호출을 막는 가드를 붙인다. 그럼 그 가드는 무엇으로 검증하나.
"AI agents take actions through tools. Some actions are sensitive, so guards that supervise them must themselves be evaluated reliably."
이 논문은 가드 평가 데이터에 라벨을 맞힐 수 있는 지름길 단서가 섞여 있다고 지적한다. 예컨대 LinuxArena에서는 셸 명령의 평균 길이만으로 궤적 라벨이 상당히 예측된다. 가드가 안전성을 판단한 게 아니라 데이터의 버릇을 외운 것일 수 있다는 뜻이다.
평가 방식을 바꾸면 점수가 무너진다. AgentDojo-Traj에서 도메인을 섞어 폴드를 나눴을 때 F1이 0.901이었는데, 도메인 홀드아웃으로 바꾸자 0.495로 떨어졌다. AgentHarm-Traj에서는 가중 방식만 바꿨는데 TS-Guard의 F1이 0.902에서 0.719로 내려갔다(대신 균형 정확도는 올라갔다).
더 직접적인 실험도 있다. 64스텝 통제 실험에서 <INFORMATION> 마커의 표기만 바꿨더니 차단율이 8.33%p 내려갔고, 도구 이름을 의미 없는 별칭으로 바꾸자 11.46%p 올라갔다. 위험한 호출은 모두 계속 차단됐으니, 움직인 것은 거짓 양성 쪽이다. 저자들은 이 구간을 탐색적 결과로 표현한다.
바꿀 것 — 가드 평가 폴드를 도메인 홀드아웃으로 바꾼다. 지금 점수가 섞인 폴드에서 나온 것이라면 그 수치는 실제 배포 상황을 과대평가하고 있을 가능성이 크다. 그리고 프롬프트의 마커 표기나 도구 이름을 바꿔 보는 짝 지은 개입을 한 번 돌려, 가드 판정이 내용이 아니라 표기에 반응하는지 확인한다.
AgentPerturb는 교란의 대상과 유형을 두 축으로 정리하고, APEX-Agents와 Toolathlon에서 프런티어 모델들을 돌렸다.
"Real-world tasks are often complex and noisy, posing substantial challenges for LLM agents. Yet existing evaluations lack a systematic framework for jointly characterizing potential perturbation targets and types."
결론 셋이다. 교란은 일관되게 성능을 떨어뜨리지만 어떤 교란이 가장 아픈지는 환경마다 다르다. 에이전트는 입력이 바뀐 것을 좀처럼 알아채지 못하고, 오염된 정보를 확인 없이 다음 단계로 넘긴다. 그리고 교란 속에서 성공한 실행은 연산을 훨씬 많이 쓴다.
초록에는 하락 폭의 구체적 수치가 없다. 여기서는 그 점을 그대로 둔다.
바꿀 것 — 회귀 세트에 교란 실행을 한 벌 더 붙인다. 깨끗한 입력에서의 성공률만 보고 있다면, 운영에서 처음 만나는 노이즈가 어디를 부수는지 모른 채 배포하는 셈이다. 토큰·시간 사용량도 같이 기록한다 — 성공했는데 비용이 몇 배로 뛴 실행은 성공으로만 세면 안 된다.
긴 세션을 돌리는 에이전트는 컨텍스트를 줄여야 한다. 문제는 무엇을 남길지 정해야 하는 시점에, 앞으로 어떤 질문이 올지 모른다는 것이다.
"Context compression in long-running applications of large language models (LLMs) must preserve goal-relevant information, often before specific downstream questions are known."
GACC-Bench는 7개 컬렉션에서 문서·에이전트 트레이스 281개 컨텍스트를 모아, 같은 목적을 공유하는 질문들을 묶어 상위 목표로 바꿨다. 최종적으로 목표 500개·질문 2,571개이고 전수를 사람이 검토했다. 압축기에는 원문과 목표와 예산만 주고 질문은 숨긴 채, 고정된 리더가 압축 결과만 보고 답하게 한다.
결과는 방향이 분명하다. 최고 성능 압축기도 전체 컨텍스트를 그대로 쓴 경우와 상당한 격차가 남았고, 특히 한 목표에 딸린 질문을 빠짐없이 맞히는 데서 벌어졌다. 목표를 넣어 압축하면 목표 없이 압축할 때보다 일관되게 정확도가 올랐고, 엉뚱한 목표를 넣으면 떨어졌다.
바꿀 것 — 요약·압축 단계에 그 세션의 목표 문장을 같이 넘긴다. 지금 “앞 대화를 요약해라”만 보내고 있다면 한 줄 추가로 개선 여지가 있다. 다만 목표를 잘못 넣으면 오히려 손해라는 것도 같이 확인됐으니, 목표 문장을 자동 생성해 끼워 넣는 구조라면 그 생성부터 점검해야 한다.
네 편을 관통하는 한 문장은 “통과했다는 사실이 맞았다는 뜻은 아니다”이다. 당장 할 수 있는 것은 셋이다.
하나. 메모리를 쓴다면 저장소를 직접 들여다보는 검사를 평가에 넣는다. QA 정확도 뒤에 20%짜리 실패가 숨어 있을 수 있다.
둘. 가드 평가 폴드를 도메인 홀드아웃으로 바꾼다. 한 번만 돌려 보면 지금 점수가 얼마나 낙관적이었는지 바로 나온다. F1이 절반 가까이 빠지는 사례가 이미 보고돼 있다.
셋. 컨텍스트 압축 프롬프트에 목표 문장을 넣는다. 가장 싸고, 방향이 분명하게 확인된 변경이다.
교란 테스트는 회귀 세트를 한 벌 더 돌려야 해서 비용이 든다. 위 셋을 먼저 하고, 에이전트를 외부 입력에 노출하는 단계가 되면 그때 붙이는 편이 낫다.
엔비디아 한국 블로그가 RTX Spark 노트북 출시 주간의 소프트웨어 로드맵(2026-10-14 발행)을 한 편에 모았다. 하드웨어 스펙을 다시 소개하는 글이 아니다. 10월 16일 노트북이 나올 때 어떤 앱과 모델, 도구가 함께 도착하는지가 중심이고 에이전트 앱·모델·보안·개발 도구·게임 소식을 날짜별로 늘어놓는다. 분량은 많지 않지만 로컬 에이전트 스택이 어디로 가는지가 몇 개 키워드에 담겨 있어서 로컬 LLM을 돌리는 개발 환경 기준으로 추려 본다. (이 글의 초안은 설치된 Hermes 에이전트가 작성했고, Claude가 검수 후 발행했다.)
TL;DR: 일정은 10/14 PAIR 정식 출시 → 10/15 Bolt 74B-A9B 24GB 공개 → 10/16 노트북 출시와 DLSS 5 고속 모델 → 10/23 Bolt E4B 4GB와 RTX Remix 1.6 → 11월 Blender DLSS 순이다. 에이전트용 모델 Nemotron 3.5 Bolt 74B-A9B는 전체 74B, 활성 9B인 MoE에 양자화 인식 학습과 2비트 양자화를 적용해 24GB에 담았고 출시 시점부터 llama.cpp·vLLM·Ollama·Unsloth·LM Studio에서 돌아간다. 눈여겨볼 대목은 “로컬 단독”이 아니다. 로컬과 클라우드를 오가는 하이브리드 라우팅(Switchyard·PAIR·HydraFusion)과 OS 수준 에이전트 샌드박싱(MXC·OpenShell)이 기본 조합으로 굳어 가는 흐름이다.
원문 곳곳에 흩어진 날짜를 모으면 아래와 같다. 모두 원문에 적힌 날짜다(원문 발행일 10/14의 “오늘”은 10/14로 옮겼다).
기술적으로 가장 무게가 실린 대목이다. Bolt 74B는 전체 파라미터 74B, 활성 파라미터 9B인 MoE 모델이다. 품질을 지키는 양자화 인식 학습(QAT)과 2비트 양자화로 24GB 안에 담았다. 원문은 “속도와 지능 사이의 최적점”을 노렸다며 널리 쓰이는 대부분의 밀집 모델보다 빠르고 비슷한 메모리를 쓰는 대부분의 MoE 모델보다 똑똑하다고 주장한다. 다만 이를 뒷받침할 벤치마크 수치는 내놓지 않았다.
"이 모델은 74B 파라미터에 활성 파라미터가 9B인 MoE(전문가 혼합) 모델로, 품질을 지켜 주는 고급 양자화 인식 학습 기법과 2비트 양자화를 적용해 24GB 안에 담아냈습니다."
실행 엔진으로는 출시 시점부터 llama.cpp, vLLM, Ollama, Unsloth, LM Studio가 꼽혔고 Hermes와 OpenClaw 같은 에이전트에서도 바로 쓸 수 있다.
"사용자는 출시 시점부터 llama.cpp와 vLLM, Ollama, Unsloth, LM Studio에서 Nemotron 3.5 Bolt 74B를 구동할 수 있습니다. Hermes와 OpenClaw 같은 에이전트에서도 바로 쓸 수 있고요."
학습 데이터와 가중치, 레시피까지 공개한 완전한 오픈 소스라는 점은 다른 Nemotron 모델과 같다.
RTX Spark는 통합 메모리가 최대 128GB이고 AI 연산 성능이 1페타플롭이다. 여기서 활성 9B짜리 MoE를 돌리는 구도이니 9월에 정리한 RTX 로컬 LLM 입문 스택보다 한 단계 큰, “노트북 한 대에 에이전트 전용 대형 MoE”를 올리는 경우가 생겼다.
같은 계열의 소형 모델 Bolt E4B 4GB는 인게임 AI 에이전트용 기술 모음 NVIDIA ACE의 3세대 SLM이다. 자연스러운 대화에 멀티턴 도구 사용, 지시 수행, 애플리케이션 상태 기반 그라운딩을 묶었다. 적은 메모리와 빠른 첫 토큰 생성 시간을 노리고 설계했고 새 대화 모드는 응답을 짧고 음성에 맞게 다듬는다. 리즈닝은 개발자가 필요에 따라 켜고 끌 수 있다.
원문 전체에 깔린 주제는 로컬 단독 실행이 아니다. 마음껏 반복 실험할 수 있는 로컬 모델과 프런티어급 클라우드 모델을 함께 쓰는 라우팅이다.
"오픈 소스 모델 라우터 라이브러리인 NVIDIA Switchyard는 에이전트가 질의를 로컬 LLM과 클라우드 LLM 사이로 똑똑하게 분배하도록 해, 클라우드 사용량은 최소화하면서도 클라우드에서만 돌릴 때와 비슷한 결과를 얻게 해 줍니다."
묶어 보면 라우터 계층(Switchyard·HydraFusion)과 실행 계층(PAIR·llama.cpp·Windows ML)이 갈라지는 모양새다. “로컬 모델 + 클라우드 폴백”이 앱마다 알아서 하던 임시방편에서 플랫폼 기능으로 옮겨 가고 있다.
에이전트가 파일 시스템과 셸을 직접 만지게 되면서 샌드박싱이 두 계층으로 나뉘었다. 운영체제 수준 보안은 MXC(Microsoft Execution Containers)가 맡는다. NVIDIA OpenShell은 에이전트가 MXC를 쉽게 도입하도록 돕고 자격 증명 보호와 보안 모니터링을 얹는다. 원문 기준으로 OpenClaw와 GitHub Copilot은 이미 MXC를 지원하고 Hermes Agent는 이달 안에 세분화된 OpenShell 제어와 MXC를 통합할 예정이다.
"MXC가 운영체제 수준의 보안을 제공하고, OpenShell은 에이전트가 MXC를 더 쉽게 도입하도록 도우면서 자격 증명 보호와 보안 모니터링 같은 고급 기능을 더해 주죠. Hermes Agent는 이달 안에 세분화된 OpenShell 제어와 MXC를 통합할 예정이며, OpenClaw와 GitHub Copilot은 이미 MXC를 지원합니다."
설치 과정도 손봤다. RTX Spark를 처음 켜면 에이전트 앱을 고르고 설치하는 ‘시작하기’ 화면이 뜬다. GitHub Copilot, Hermes Agent, OpenClaw, Perplexity, Pi, WorkBuddy는 RTX Spark에 맞는 로컬 모델과 설정값을 추천하고 몇 번의 클릭으로 구성까지 끝낸다. NVIDIA는 NVIDIA 앱·Broadcast·PAIR·Omniverse·RTX Remix용 MCP와 CUDA-X Skills 라이브러리도 공개했다. 에이전트가 NVIDIA 도구를 직접 다룰 수 있는 접점이 그만큼 늘었다.
RTX Spark는 Windows on Arm 기반이라 개발 도구가 얼마나 준비됐느냐가 관건이었다. 원문이 꼽은 커뮤니티 성과는 다음과 같다.
작업 환경은 두 갈래다. 주요 개발 도구를 한꺼번에 설치해 주는 Windows 개발자 구성(Windows Developer Config)으로 Windows에서 바로 작업하거나 클라우드 배포 때와 같은 패키지를 쓸 수 있는 WSL을 쓰면 된다.
llama.cpp는 디시전 모델(decision model) 지원을 추가했다. 원문은 긴 리즈닝 루프 없이 요청 분류나 다음 행동 선택 같은 판단을 기존 에이전트보다 최대 200배 빠르게 처리한다고 주장한다. llama.cpp는 Windows 네이티브 동반 앱 Llama Windows도 내놓았다. Hugging Face 블로그 안내대로 Windows 11 시스템 트레이에서 실행되고 로컬 모델과 Hugging Face Hub 추천 모델을 클릭 한 번으로 불러온다.
"요청을 분류하는 일부터 다음 행동을 고르는 일까지, 기존 에이전트보다 최대 200배 빠르게 처리할 수 있습니다. 디시전 모델은 이제 RTX Spark와 GeForce RTX GPU의 llama.cpp, Unsloth에서 지원됩니다."
에이전트 주제와 바로 겹치지는 않지만 원문의 절반을 차지하는 부분이라 요점만 남긴다.
읽고 나면 세 가지가 남는다.
첫째, 이번 글의 알맹이는 노트북 발표가 아니라 에이전트 소프트웨어 스택의 표준화다. 모델(Bolt 74B/E4B), 라우터(Switchyard·PAIR), 보안(MXC·OpenShell), 도구 접점(MCP·CUDA-X Skills)이 한 묶음으로 움직인다. 로컬 에이전트를 직접 돌리는 입장이라면 어느 한 조각보다 이 조합 전체를 지켜봐야 한다.
둘째, 하이브리드 라우팅에 기준점이 생겼다. 모든 질의를 로컬에서 처리하는 대신 라우터가 판단해 로컬과 클라우드로 나누는 구도가 Copilot·Perplexity·Hermes에 똑같이 들어온다. DGX Spark 두 대를 Sync Cluster로 묶어 메모리를 늘리는 접근과 이번 소프트웨어 라우팅은 같은 문제를 반대쪽에서 푼다. 하드웨어로 늘릴 것이냐, 라우팅으로 아낄 것이냐의 차이다.
셋째, 따져 볼 부분이 남아 있다. Bolt 74B의 품질 주장과 디시전 모델의 “최대 200배”는 원문이 수치 근거를 대지 않은 벤더 주장이다. llama.cpp나 Ollama에서 직접 돌려 보기 전에는 판단을 미루는 게 맞다.
로컬 LLM 다운로드가 이미 지난해 전체의 5배에 이른다는 통계와, Qwen 3.8-Flash-Next가 몇 달 전 나온 프런티어 클라우드 모델을 따라잡았다는 서술도 원문의 주장일 뿐 출처 링크가 없다. 흐름을 읽는 참고로만 쓰는 편이 안전하다.