7월 첫 주. 챕터가 바뀌었다. 지난 반년이 가능성을 다뤘다면, 이번 반년은 만드는 순서를 다룬다. 첫 주에 두 편이 나갔다.
이번 주 Signal
바닥부터 다시 깐다. 「MCP 서버 첫 구현」이 이번 챕터의 첫 칸이다. 노트 네 개를 도구로 내주는 몇십 줄짜리 서버를 만들고, Claude Desktop 설정에 경로 한 줄을 등록한다. 그게 전부다 — 스토어도, 배포도, 심사도 없다. 채팅에 "노트에 저장해줘"라고 적으면 내 노트북의 코드가 실행된다. dart test가 서버를 별도 프로세스로 띄워 왕복과 영속까지 스스로 검사한다.
그리고 그 옆에 45줄이 선다. 「45줄」은 동네 모임 회비를 채팅과 메모장으로 관리하던 사람이 주말 오후에 만든 도구다. 이번엔 시간이 아니라 줄 수를 셌다 — 화면 정의가 몇 줄이고 서버가 몇 줄인지. 만든 시간은 사람마다 다르지만 줄 수는 안 변하기 때문이다.
도구·패키지 메모
mcp_server의 stdio 모드에서 stdout은 JSON-RPC 전용 통로다. 진단 메시지를 print로 한 줄 흘리면 그 줄이 프로토콜 스트림을 깬다. 이번 서버의 오류 출력이 전부 stderr로만 나가는 이유가 그거다. 임베디드에서 "왜 가끔 파싱이 실패하지"의 상당수가 같은 자리에서 나온다.
짧은 생각
첫 서버를 띄우고 나면 대개 같은 착각을 한다 — 이제 프로토콜을 배워야겠구나. 반대다. initialize 핸드셰이크도, tools/list도, stdio 프레이밍도 패키지가 가린다. 남는 일은 도구가 무엇을 뜻하는지 쓰는 것뿐이다. 그 문장을 잘 쓰는 게 코드보다 중요하다. 모델이 도구를 고르는 근거가 그 문장이기 때문이다.
다음 주
화면을 서버에서 받아 그리는 쪽으로 넘어간다. 그리고 "누가 이 버튼을 눌러도 되는가"를 도구 경계에서 막는 편이 이어진다.
makemind.dev 「소식」 — 매주 한 번, 그 주에 무엇이 올라갔고 만들면서 무엇이 걸렸는지.