Skip to content

Pathuri-Deepesh/mcp-toolbox

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

mcp-toolbox

A local Python MCP (Model Context Protocol) server that exposes 63 utility tools to any LLM — plus a standalone CLI agent (chat.py) built on the Anthropic SDK that demonstrates the full agent loop end-to-end.

Built to learn the MCP protocol from the ground up: tool registration, JSON-RPC over stdio, agentic tool-use loops, and the brain/hands separation that makes any tool reusable across any MCP-aware host (Claude Code, Claude Desktop, Cursor, custom clients).


Architecture

                          ┌──────────────────────────┐
   You ── question ──▶    │   chat.py  (orchestrator)│
                          │   - sends msg to LLM     │
                          │   - dispatches tool calls│
                          │   - feeds results back   │
                          │   - loops until end_turn │
                          └────┬───────────────┬─────┘
                               │               │
                  Anthropic API│               │ stdio + JSON-RPC
                               ▼               ▼
                       ┌───────────────┐   ┌────────────────────┐
                       │  Claude (LLM) │   │ mcp_toolbox server │
                       │  picks tool + │   │ 63 tools, executes │
                       │  arguments    │   │ Python or hits APIs│
                       └───────────────┘   └────────┬───────────┘
                                                    │
                                                    ▼
                              ┌────────────────────────────────────┐
                              │ External APIs (DuckDuckGo, Open-   │
                              │ Meteo, frankfurter, CoinGecko, ...)│
                              └────────────────────────────────────┘

The same MCP server can be consumed by chat.py (custom client) or by Claude Code / Claude Desktop / any MCP-aware host via .mcp.json — write the tools once, plug in anywhere.


The 63 tools (10 modules)

Module Tools
search web_search, news_search, image_search, wikipedia_search, wikipedia_summary, fetch_url
knowledge dictionary_lookup, thesaurus, rhymes, random_joke, cat_fact, random_quote, random_useless_fact, country_info
data generate_uuid, generate_password, color_convert, lorem_ipsum, random_choice, coin_flip, dice_roll
math calculator, statistics_summary, random_number, base_convert, prime_check, factorize, unit_convert
finance currency_convert, list_currencies, crypto_price, trending_crypto
network dns_lookup, http_status, expand_url, ip_info, public_ip
time current_time, list_timezones, convert_timezone, date_diff, add_to_date, working_days_between, parse_date
text count_words, regex_match, regex_replace, url_encode, url_decode, base64_encode, base64_decode, hash_text, json_format, slugify, diff_text
weather get_weather, geocode, reverse_geocode
travel search_flights, search_hotels, search_trains, search_car_rental, search_restaurants, airport_info (travel search tools return deterministic mock data — designed to be swapped for real Amadeus / Skyscanner APIs)

Install

git clone https://github.com/Pathuri-Deepesh/mcp-toolbox.git
cd mcp-toolbox
python -m venv .venv
.venv\Scripts\activate           # Windows
# source .venv/bin/activate      # macOS / Linux
pip install -e .
pip install anthropic python-dotenv

Use it — three ways

1. Standalone CLI agent (chat.py)

The custom-built agent that hand-rolls the agentic loop (no LangChain).

echo "ANTHROPIC_API_KEY=sk-ant-..." > .env
python chat.py
[loaded 63 tools from mcp-toolbox] type 'quit' to exit

Question: convert 1000 USD to INR
  -> currency_convert({"amount": 1000, "from_currency": "USD", "to_currency": "INR"})

Response: 1000 USD = ₹92,823 INR (rate from 2026-04-17).

Question: what's the weather in Mumbai?
  -> geocode({"place_name": "Mumbai"})
  -> get_weather({"latitude": 19.07, "longitude": 72.88})

Response: Mumbai is currently 31°C, partly cloudy, with light winds...

The -> lines are real-time tool invocations — proof Claude is selecting tools from the catalog and the MCP server is executing them.

2. Inside Claude Code (or any MCP-aware host)

The bundled .mcp.json is auto-discovered when you launch Claude Code in this directory:

{
  "mcpServers": {
    "toolbox": {
      "command": ".venv/Scripts/python.exe",
      "args": ["-m", "mcp_toolbox"]
    }
  }
}

Then in Claude Code, /mcp should list toolbox · ✔ connected. Chat naturally — Claude picks the right tool from the 63 automatically.

3. MCP Inspector (manual tool exploration)

npx @modelcontextprotocol/inspector .venv/Scripts/python.exe -m mcp_toolbox

Opens a browser UI where you can list tools, invoke them by hand, and inspect the JSON-RPC traffic.


How chat.py works (the agent loop)

The full agentic loop in plain pseudo-code:

load 63 tool schemas from MCP server

repeat:
    user types a question
    append to message history

    repeat:                                     # inner agentic loop
        send message history + tool schemas to Claude
        receive response

        if response is final answer (end_turn):
            print the answer
            break

        if response contains tool_use blocks:
            for each tool_use block:
                call MCP server with tool name + arguments
                collect the result
            append all tool results to message history
            # loop back — let Claude decide the next step

That's the whole agent. ~80 lines of Python in chat.py. LangChain's AgentExecutor does the same thing — this version just doesn't hide it.


Add your own tool

  1. Create a function in src/mcp_toolbox/tools/ (or a new module file).
  2. Decorate it with @mcp.tool() and add a docstring — the LLM uses the docstring to decide when to call it.
  3. Import the new module in src/mcp_toolbox/server.py.

Example:

from ..server import mcp

@mcp.tool()
def reverse_string(text: str) -> str:
    """Reverse a string. Useful for palindrome checks and debugging."""
    return text[::-1]

Restart the host (Claude Code or chat.py) and the new tool appears in the catalog automatically.


Notable engineering decisions

  • python -m mcp_toolbox, not python -m mcp_toolbox.server — the server.py module imports tools.*, and tools.* imports back from ..server. Running server.py directly via -m causes Python to load it twice (as __main__ and as mcp_toolbox.server), so tools register on a different mcp instance than the one main() runs. Routing through __main__.py loads server.py exactly once.
  • chat.py uses client.messages.stream() — adaptive thinking + cache_control on the non-streaming endpoint can return raw SSE strings in some SDK versions. Streaming + .get_final_message() is the canonical fix.
  • sys.stdout.reconfigure(encoding='utf-8') — tool output frequently contains Unicode (currency symbols, language names); the default Windows console codepage (cp1252) can't encode it.

License

MIT — see LICENSE.

About

No description, website, or topics provided.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages