boc-valet-mcp
README.md
# šØš¦ Bank of Canada Valet MCP Server
[](https://www.python.org/downloads/)
[](https://modelcontextprotocol.io)
[](LICENSE)
[](https://github.com/Chatusvi-Karnati/boc-valet-mcp/actions)
An [MCP](https://modelcontextprotocol.io) server that gives LLM agents (Claude, and any other MCP-compatible client) live access to Canadian economic and financial data through the **[Bank of Canada Valet API](https://www.bankofcanada.ca/valet/docs)** ā exchange rates, interest rates, inflation series, and thousands more.
The Valet API is **free and requires no API key**, so this server runs out of the box.
> Ask *"What's the latest USD/CAD exchange rate?"* or *"Chart CORRA over the last month"* and the agent pulls the numbers straight from the source.
---
## Why this exists
Large language models don't know today's exchange rate ā their training data is frozen in the past. MCP closes that gap by letting a model call live tools. This server is a small, focused, production-shaped example of that pattern: clean tool design, input validation, actionable errors, and tests.
## Features
- **5 well-scoped tools** covering discovery ā metadata ā data retrieval
- **No API key** ā the Valet API is public
- **Dual output** ā human-readable Markdown or structured JSON, per call
- **Search + pagination** over the large series/group catalogue
- **Multi-series comparison** ā pull several series side by side in one call
- **Agent-friendly errors** ā every failure explains what to try next
- **Typed & validated** ā Pydantic `Field` constraints on every parameter
- **Tested** ā offline unit tests, no network needed for CI
## Tools
| Tool | What it does |
|------|--------------|
| `boc_list_series` | Search / list the available data series (start here) |
| `boc_list_groups` | Search / list curated groups of related series |
| `boc_get_series_info` | Fetch metadata (label, description) for one series |
| `boc_get_observations` | **Core:** get data points for one or more series, by date range or most-recent |
| `boc_get_group_observations` | Get every series in a group in a single call |
## Architecture
```
src/boc_valet_mcp/
āāā server.py # MCP tool definitions (the interface agents see)
āāā client.py # Async httpx client + centralized, actionable errors
āāā formatting.py # Markdown / JSON rendering (shared by every tool)
```
The separation keeps each layer testable: tools stay thin, HTTP concerns live in one place, and presentation logic is unit-tested offline against representative payloads.
## Quickstart
```bash
git clone https://github.com/Chatusvi-Karnati/boc-valet-mcp.git
cd boc-valet-mcp
python -m venv .venv && source .venv/bin/activate # Windows: .venv\Scripts\activate
pip install -e .
```
Run it directly (it speaks MCP over stdio):
```bash
boc-valet-mcp
```
### Inspect it interactively
The MCP Inspector is the fastest way to click through the tools:
```bash
npx @modelcontextprotocol/inspector boc-valet-mcp
```
### Use it with Claude Desktop
Add this to your `claude_desktop_config.json` (see [`examples/`](examples/claude_desktop_config.json)):
```json
{
"mcpServers": {
"bank-of-canada": {
"command": "boc-valet-mcp"
}
}
}
```
Restart Claude Desktop and ask it something like *"Compare the USD/CAD and EUR/CAD rates over the past week."*
## Example
Calling `boc_get_observations` with `series_names="FXUSDCAD"`, `recent=1`:
```
**Series:**
- `FXUSDCAD` ā US dollar to Canadian dollar daily exchange rate
| Date | FXUSDCAD |
|------------|----------|
| 2024-06-03 | 1.3654 |
_1 observation(s)._
```
## Development
```bash
pip install -e ".[dev]"
pytest # run the test suite
ruff check . # lint
```
## How it was built
Designed and built following Anthropic's MCP server best practices ā comprehensive tool coverage, `readOnly`/`idempotent` annotations, Pydantic-validated inputs, and error messages written for an agent audience. Developed with an AI-assisted workflow using Claude Code.
## License
MIT ā see [LICENSE](LICENSE).
## Acknowledgements
Data is provided by the [Bank of Canada Valet API](https://www.bankofcanada.ca/valet/docs). This project is not affiliated with or endorsed by the Bank of Canada. Please review the Bank of Canada's [terms of use](https://www.bankofcanada.ca/terms/) for the data.
TDQS
A4.2/5.0
Scored across 5 tools
Disambiguation5/5
Each tool has a clear, distinct purpose: listing series, listing groups, getting series metadata, getting observations for series, and getting observations for groups. No overlap.
Naming Consistency5/5
All tools follow a consistent 'boc_verb_noun' pattern (e.g., boc_list_series, boc_get_observations), making it easy to infer functionality.
Tool Count5/5
With 5 tools, the server is focused and each tool earns its place. The count is ideal for a read-only economic data API.
Completeness4/5
Covers discovery and retrieval for both individual series and groups. Missing a dedicated tool for group metadata, but the list tool provides enough context.
Maintenance
ActivitySlowing
ResponsivenessNo issues