A hands-on lab for building a terminal-based AI agent from scratch in Go, inspired by You Should Write An Agent by Fly.io.
This project walks you through building a fully functional agentic loop in Go — no frameworks, no magic. Just Go's standard library, the Anthropic API, and a terminal. By the end, you'll have an agent that can hold multi-turn conversations, call tools, and execute real actions on your machine.
- Create a new Go module:
go mod init agent - Add the Anthropic Go SDK as a dependency (or use
net/httpraw) - Store your API key in an environment variable and read it with
os.Getenv - Write a
main.gowith a basic REPL: read a line, print it back
- Define a
Messagestruct withRoleandContentfields - Implement a
callClaude(messages []Message)function that POSTs to the Anthropic/v1/messagesendpoint - Parse the JSON response and extract the assistant's reply text
- Print the reply in the terminal; confirm a single Q&A works end-to-end
- Maintain a
context []Messageslice in memory across loop iterations - Append each user message and each assistant reply to context before the next call
- Add a system message at index 0 to give the agent a persona or instructions
- Verify the agent remembers previous turns in a 5-message conversation
- Define a
Toolstruct matching Anthropic's JSON schema (name,description,input_schema) - Implement at least one concrete tool — e.g.
run_shellthat executes a bash command viaos/exec - Pass the
toolsarray with everycallClaudeinvocation - Detect
tool_useblocks in the response and dispatch to the correct Go function - Append tool results back to context as
tool_resultmessages and loop until no more tool calls
- Add a
--verboseflag that prints each tool call name and args before executing - Implement a token-budget guard: if context length exceeds N turns, summarize old messages
- Persist conversation history to a JSON file so sessions survive restarts
- Go 1.21+
- An Anthropic API key
git clone https://github.com/your-username/agent
cd agent
go mod tidyCreate a .env file:
ANTHROPIC_API_KEY=sk-ant-...
Run the agent:
go run main.goagent/
├── main.go # Entry point and REPL loop
├── llm.go # Anthropic API client
├── tools.go # Tool definitions and handlers
├── history.json # Persisted conversation history (Phase 5)
├── .env # API keys (never commit this)
├── .gitignore
└── go.mod
.env
history.json
agent