#
tokens: 3925/50000 6/6 files
lines: on (toggle) GitHub
raw markdown copy reset
# Directory Structure

```
├── .gitignore
├── .mcp.json
├── .python-version
├── LICENSE
├── main.py
├── pyproject.toml
├── README.md
└── uv.lock
```

# Files

--------------------------------------------------------------------------------
/.python-version:
--------------------------------------------------------------------------------

```
1 | 3.10
2 | 
```

--------------------------------------------------------------------------------
/.mcp.json:
--------------------------------------------------------------------------------

```json
1 | {
2 |   "mcpServers": {
3 |     "zipcode-search": {
4 |       "command": "uv",
5 |       "args": ["run", "python", "main.py"]
6 |     }
7 |   }
8 | }
9 | 
```

--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------

```
  1 | # Byte-compiled / optimized / DLL files
  2 | __pycache__/
  3 | *.py[cod]
  4 | *$py.class
  5 | 
  6 | # C extensions
  7 | *.so
  8 | 
  9 | # Distribution / packaging
 10 | .Python
 11 | build/
 12 | develop-eggs/
 13 | dist/
 14 | downloads/
 15 | eggs/
 16 | .eggs/
 17 | lib/
 18 | lib64/
 19 | parts/
 20 | sdist/
 21 | var/
 22 | wheels/
 23 | pip-wheel-metadata/
 24 | share/python-wheels/
 25 | *.egg-info/
 26 | .installed.cfg
 27 | *.egg
 28 | MANIFEST
 29 | 
 30 | # PyInstaller
 31 | #  Usually these files are written by a python script from a template
 32 | #  before PyInstaller builds the exe, so as to inject date/other infos into it.
 33 | *.manifest
 34 | *.spec
 35 | 
 36 | # Installer logs
 37 | pip-log.txt
 38 | pip-delete-this-directory.txt
 39 | 
 40 | # Unit test / coverage reports
 41 | htmlcov/
 42 | .tox/
 43 | .nox/
 44 | .coverage
 45 | .coverage.*
 46 | .cache
 47 | nosetests.xml
 48 | coverage.xml
 49 | *.cover
 50 | *.py,cover
 51 | .hypothesis/
 52 | .pytest_cache/
 53 | 
 54 | # Translations
 55 | *.mo
 56 | *.pot
 57 | 
 58 | # Django stuff:
 59 | *.log
 60 | local_settings.py
 61 | db.sqlite3
 62 | db.sqlite3-journal
 63 | 
 64 | # Flask stuff:
 65 | instance/
 66 | .webassets-cache
 67 | 
 68 | # Scrapy stuff:
 69 | .scrapy
 70 | 
 71 | # Sphinx documentation
 72 | docs/_build/
 73 | 
 74 | # PyBuilder
 75 | target/
 76 | 
 77 | # Jupyter Notebook
 78 | .ipynb_checkpoints
 79 | 
 80 | # IPython
 81 | profile_default/
 82 | ipython_config.py
 83 | 
 84 | # pyenv
 85 | #.python-version
 86 | 
 87 | # pipenv
 88 | #   According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
 89 | #   However, in case of collaboration, if having platform-specific dependencies or dependencies
 90 | #   having no cross-platform support, pipenv may install dependencies that don't work, or not
 91 | #   install all needed dependencies.
 92 | #Pipfile.lock
 93 | 
 94 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow
 95 | __pypackages__/
 96 | 
 97 | # Celery stuff
 98 | celerybeat-schedule
 99 | celerybeat.pid
100 | 
101 | # SageMath parsed files
102 | *.sage.py
103 | 
104 | # Environments
105 | .env
106 | .venv
107 | env/
108 | venv/
109 | ENV/
110 | env.bak/
111 | venv.bak/
112 | 
113 | # Spyder project settings
114 | .spyderproject
115 | .spyproject
116 | 
117 | # Rope project settings
118 | .ropeproject
119 | 
120 | # mkdocs documentation
121 | /site
122 | 
123 | # mypy
124 | .mypy_cache/
125 | .dmypy.json
126 | dmypy.json
127 | 
128 | # Pyre type checker
129 | .pyre/
130 | 
131 | # IDE
132 | .vscode/
133 | .idea/
134 | *.swp
135 | *.swo
136 | 
137 | # macOS
138 | .DS_Store
139 | 
140 | # Windows
141 | Thumbs.db
142 | ehthumbs.db
143 | Desktop.ini
144 | 
145 | # Linux
146 | *~
147 | 
148 | # Keep important MCP files
149 | !.mcp.json
150 | !.python-version
151 | 
```

--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Zipcode Search MCP Server
  2 | 
  3 | [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
  4 | [![Python 3.10+](https://img.shields.io/badge/python-3.10+-blue.svg)](https://www.python.org/downloads/)
  5 | 
  6 | A Model Context Protocol (MCP) server that provides Japanese postal code to address lookup functionality. This server can be integrated with AI assistants and other MCP clients to enable postal code search capabilities.
  7 | 
  8 | ## Features
  9 | 
 10 | - 🏣 Search Japanese addresses by 7-digit postal codes
 11 | - 🔌 Model Context Protocol (MCP) compatible
 12 | - 🚀 Fast and lightweight implementation
 13 | - 🌐 Uses reliable Zipcloud API as data source
 14 | - 🛡️ Built-in error handling and validation
 15 | 
 16 | ## Tech Stack
 17 | 
 18 | - **Python 3.10+**
 19 | - **MCP (Model Context Protocol)** - AI tool integration protocol
 20 | - **FastMCP** - MCP server framework
 21 | - **httpx** - Modern HTTP client
 22 | - **Zipcloud API** - Japanese postal code data source
 23 | 
 24 | ## Installation
 25 | 
 26 | ### Prerequisites
 27 | 
 28 | - Python 3.10 or higher
 29 | - [uv](https://docs.astral.sh/uv/) (recommended) or pip
 30 | 
 31 | ### Quick Start
 32 | 
 33 | 1. Clone the repository:
 34 | ```bash
 35 | git clone https://github.com/rooking-oss/zipcode-search-mcp.git
 36 | cd zipcode-search-mcp
 37 | ```
 38 | 
 39 | 2. Install dependencies using uv:
 40 | ```bash
 41 | uv sync
 42 | ```
 43 | 
 44 | Or with pip:
 45 | ```bash
 46 | pip install -e .
 47 | ```
 48 | 
 49 | 3. Run the MCP server:
 50 | ```bash
 51 | uv run python main.py
 52 | ```
 53 | 
 54 | ## MCP Client Configuration
 55 | 
 56 | ### Claude Desktop
 57 | 
 58 | Add the following configuration to your `claude_desktop_config.json`:
 59 | 
 60 | ```json
 61 | {
 62 |   "mcpServers": {
 63 |     "zipcode-search": {
 64 |       "command": "uv",
 65 |       "args": ["run", "python", "/path/to/zipcode-search-mcp/main.py"]
 66 |     }
 67 |   }
 68 | }
 69 | ```
 70 | 
 71 | ### Other MCP Clients
 72 | 
 73 | For other MCP clients, refer to the included `.mcp.json` configuration file or use the following connection details:
 74 | 
 75 | - **Server Name**: `zipcode-search`
 76 | - **Command**: `uv run python main.py`
 77 | - **Working Directory**: Project root directory
 78 | 
 79 | ## Available Tools
 80 | 
 81 | ### search_zipcode
 82 | 
 83 | Searches for a Japanese address using a postal code.
 84 | 
 85 | **Parameters:**
 86 | - `zipcode` (string): 7-digit postal code (e.g., "1000001")
 87 | 
 88 | **Returns:**
 89 | - `address` (string): The found address, or "Address not found" if no match
 90 | 
 91 | **Example Usage:**
 92 | 
 93 | In your MCP client (like Claude):
 94 | 
 95 | ```
 96 | What's the address for postal code 1000001?
 97 | ```
 98 | 
 99 | Or directly:
100 | 
101 | ```
102 | Use the search_zipcode tool to find the address for postal code 1600020
103 | ```
104 | 
105 | ## API Reference
106 | 
107 | The server provides one tool through the MCP protocol:
108 | 
109 | | Tool | Description | Input | Output |
110 | |------|-------------|-------|--------|
111 | | `search_zipcode` | Search address by postal code | `zipcode: string` | `{address: string}` |
112 | 
113 | ## Development
114 | 
115 | ### Project Structure
116 | 
117 | ```
118 | zipcode-search-mcp/
119 | ├── main.py              # MCP server implementation
120 | ├── pyproject.toml       # Project configuration and dependencies
121 | ├── uv.lock             # Dependency lock file
122 | ├── .mcp.json           # MCP client configuration
123 | ├── .python-version     # Python version specification
124 | ├── .gitignore          # Git ignore rules
125 | └── README.md           # This file
126 | ```
127 | 
128 | ### Development Setup
129 | 
130 | 1. Clone and install in development mode:
131 | ```bash
132 | git clone https://github.com/rooking-oss/zipcode-search-mcp.git
133 | cd zipcode-search-mcp
134 | uv sync
135 | ```
136 | 
137 | 2. Run tests (if available):
138 | ```bash
139 | uv run pytest
140 | ```
141 | 
142 | 3. Format code:
143 | ```bash
144 | uv run black .
145 | uv run isort .
146 | ```
147 | 
148 | ### Contributing
149 | 
150 | We welcome contributions! Please follow these steps:
151 | 
152 | 1. Fork the repository
153 | 2. Create a feature branch (`git checkout -b feature/amazing-feature`)
154 | 3. Make your changes
155 | 4. Add tests if applicable
156 | 5. Commit your changes (`git commit -m 'Add amazing feature'`)
157 | 6. Push to the branch (`git push origin feature/amazing-feature`)
158 | 7. Open a Pull Request
159 | 
160 | ## Dependencies
161 | 
162 | ### External Services
163 | - [Zipcloud API](https://zipcloud.ibsnet.co.jp/) - Provides postal code to address mapping data
164 | 
165 | ### Python Packages
166 | - `mcp[cli]` - Model Context Protocol implementation
167 | - `httpx` - Async HTTP client for API requests
168 | 
169 | ## Troubleshooting
170 | 
171 | ### Server Won't Start
172 | 
173 | 1. Verify Python version is 3.10+:
174 | ```bash
175 | python --version
176 | ```
177 | 
178 | 2. Ensure dependencies are installed:
179 | ```bash
180 | uv sync
181 | ```
182 | 
183 | 3. Check if the server starts manually:
184 | ```bash
185 | uv run python main.py
186 | ```
187 | 
188 | ### Postal Code Not Found
189 | 
190 | - Ensure the postal code is exactly 7 digits (no hyphens)
191 | - Verify the Zipcloud API is accessible
192 | - Check your internet connection
193 | 
194 | ### MCP Client Connection Issues
195 | 
196 | - Verify the path in your MCP client configuration is correct
197 | - Ensure the server is executable from the specified directory
198 | - Check MCP client logs for detailed error messages
199 | 
200 | ## License
201 | 
202 | This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
203 | 
204 | ## Acknowledgments
205 | 
206 | - [Zipcloud](https://zipcloud.ibsnet.co.jp/) for providing the postal code API
207 | - [Model Context Protocol](https://modelcontextprotocol.io/) for the integration framework
208 | - [FastMCP](https://github.com/jlowin/fastmcp) for the server implementation
209 | 
210 | ## Support
211 | 
212 | If you encounter any issues or have questions:
213 | 
214 | 1. Check the [Issues](https://github.com/rooking-oss/zipcode-search-mcp/issues) page
215 | 2. Create a new issue with detailed information
216 | 3. For general questions, start a [Discussion](https://github.com/rooking-oss/zipcode-search-mcp/discussions)
217 | 
218 | ---
219 | 
220 | **Note**: This service uses the Zipcloud API and is intended for development and educational purposes. For production use, please ensure proper error handling, rate limiting, and compliance with the Zipcloud API terms of service.
221 | 
```

--------------------------------------------------------------------------------
/main.py:
--------------------------------------------------------------------------------

```python
 1 | from mcp.server.fastmcp import FastMCP
 2 | import httpx
 3 | 
 4 | mcp = FastMCP(
 5 |     name="zipcode-search",
 6 |     description="A Model Context Protocol server for Japanese postal code address lookup"
 7 | )
 8 | 
 9 | @mcp.tool()
10 | def search_zipcode(zipcode: str) -> dict:
11 |     """Search for address by Japanese postal code
12 |     
13 |     Args:
14 |         zipcode: 7-digit postal code (e.g., "1000001")
15 |     
16 |     Returns:
17 |         dict: Address information with "address" key
18 |     """
19 |     try:
20 |         with httpx.Client() as client:
21 |             response = client.get(f"https://zipcloud.ibsnet.co.jp/api/search?zipcode={zipcode}")
22 |             response.raise_for_status()
23 |             data = response.json()
24 |             
25 |         if data.get("results"):
26 |             result = data["results"][0]
27 |             address = f"{result['address1']}{result['address2']}{result['address3']}"
28 |             return {"address": address}
29 |         
30 |         return {"address": "Address not found"}
31 |     
32 |     except Exception as e:
33 |         return {"address": f"Error occurred: {str(e)}"}
34 | 
35 | if __name__ == "__main__":
36 |     mcp.run()
37 | 
```

--------------------------------------------------------------------------------
/pyproject.toml:
--------------------------------------------------------------------------------

```toml
 1 | [project]
 2 | name = "zipcode-search-mcp"
 3 | version = "0.1.0"
 4 | description = "A Model Context Protocol (MCP) server for Japanese postal code address lookup"
 5 | readme = "README.md"
 6 | requires-python = ">=3.10"
 7 | license = {text = "MIT"}
 8 | authors = [
 9 |     {name = "RookingOSS", email = "[email protected]"}
10 | ]
11 | keywords = ["mcp", "postal-code", "zipcode", "address", "japan"]
12 | classifiers = [
13 |     "Development Status :: 4 - Beta",
14 |     "Intended Audience :: Developers",
15 |     "License :: OSI Approved :: MIT License",
16 |     "Programming Language :: Python :: 3",
17 |     "Programming Language :: Python :: 3.10",
18 |     "Programming Language :: Python :: 3.11",
19 |     "Programming Language :: Python :: 3.12",
20 |     "Topic :: Software Development :: Libraries :: Python Modules",
21 | ]
22 | dependencies = [
23 |     "httpx>=0.28.1",
24 |     "mcp[cli]>=1.9.3",
25 | ]
26 | 
27 | [project.urls]
28 | Homepage = "https://github.com/rooking-oss/zipcode-search-mcp"
29 | Repository = "https://github.com/rooking-oss/zipcode-search-mcp"
30 | Issues = "https://github.com/rooking-oss/zipcode-search-mcp/issues"
31 | 
32 | [build-system]
33 | requires = ["hatchling"]
34 | build-backend = "hatchling.build"
35 | 
36 | [tool.uv]
37 | dev-dependencies = []
38 | 
```