Phase 08 — Extending: MCP, Skills, Retrieval
Part of Harness engineering.
A harness reaches beyond its built-in tools in three ways. MCP connects outside tool servers. Skills add workflows that load only when needed. Retrieval finds the right code in a large repo. This phase builds the MCP handshake by hand, then uses the official SDK. It then adds a skill index with deferred loading, a repo map, and a search_code tool.
Lessons
- The MCP Protocol: Server and Client — handshake,
tools/list,tools/calland the two error homes over stdio. - The Official MCP SDK — what the decorator does, and a notes server that persists to disk.
- Skills and Deferred Loading — a cheap index in context and bodies or schemas loaded on demand.
- The Repo Map — symbols with line numbers, and chunks cut on structure.
- A search_code Tool — ranked
path:linehits behind one tool.
Where the depth lives
| If you want | Read |
|---|---|
| MCP and standard connectors in product terms | MCP and standard connectors |
| Protocols between agents and tools | Multi-agent and protocols |
| Tool contracts and reliability | Tool contracts and reliability |
| Chunking and ingestion for retrieval | Chunking and ingestion |
| Embeddings and semantic search | Embeddings and semantic search |
| What goes into a context pipeline | The anatomy of a context pipeline |
Test yourself
- A client sends
tools/listbeforenotifications/initialized. What should a careful server do? <details><summary>Answer</summary>It may refuse, because the handshake is not finished. The spec tells clients not to send requests other than pings beforeinitializeis answered. It does not say how a server must react. The lesson’s server returns a JSON-RPC error. The client must sendinitialize, read the reply, then send theinitializednotification. (<a href=“./01-mcp-protocol-server-client/docs/en.md”>Lesson 1</a>)</details> - A tool divides by zero. Is that a JSON-RPC error or a tool result? Why does it matter?
<details><summary>Answer</summary>It is a normal result with
isError: true. The model reads results and can recover. A JSON-RPC error is for protocol faults such as an unknown tool, and many clients do not show it to the model. (<a href=“./01-mcp-protocol-server-client/docs/en.md”>Lesson 1</a>)</details> - Why does a stray
printbreak a stdio MCP server? <details><summary>Answer</summary>The client parses every stdout line as a protocol message. The server must write only valid messages to stdout and send logs to stderr. (<a href=“./01-mcp-protocol-server-client/docs/en.md”>Lesson 1</a>)</details> - What does an SDK tool decorator derive from your function, and what must you still write well?
<details><summary>Answer</summary>It derives the
inputSchemafrom type hints and the description from the docstring. You still write the name, hints and docstring, because the model reads them to pick and call the tool. (<a href=“./02-official-mcp-sdk/docs/en.md”>Lesson 2</a>)</details> - When does a memory MCP server keep notes across restarts? <details><summary>Answer</summary>Only when it writes them somewhere durable, such as a file. A Python list lives and dies with the process. (<a href=“./02-official-mcp-sdk/docs/en.md”>Lesson 2</a>)</details>
- What is always in context for a skill, and what loads later? Why does the description matter so much? <details><summary>Answer</summary>The name and description are always in context. The body loads when the skill is used. The description is all the model sees when it decides, so it must name concrete cases. (<a href=“./03-skills-and-deferred-loading/docs/en.md”>Lesson 3</a>)</details>
- Why must a chunker handle decorators and nested definitions?
<details><summary>Answer</summary>A chunk that drops its decorators is not the real definition, and a flat walk loses the parent of a method. Qualified names such as
Session.openkeep the parent. (<a href=“./04-repo-map/docs/en.md”>Lesson 4</a>)</details> - Why should
search_codereturnpath:linehits and not file contents, and what should it do when nothing matches? <details><summary>Answer</summary>Hits keep the answer small, and the agent reads the lines it needs. With no match the tool must return an empty result, so the agent does not follow a weak “closest” hit. (<a href=“./05-search-code-tool/docs/en.md”>Lesson 5</a>)</details>
