MHTL Warehouse MCP Server
# MHTL Warehouse MCP Server
An [MCP](https://modelcontextprotocol.io) server (TypeScript) that lets Claude
query the local DuckDB warehouse in `data/mock.duckdb` — a mock motorcycle-loan
warehouse with DMS (loan servicing) and LOS (loan origination) tables.
Ask Claude things like:
> **"Get the insights of the customer Noy Vongphachanh"**
and it will look the customer up, pull their contracts, delinquency/NPL status,
recent collection notes, and loan applications.
## Tools exposed
| Tool | What it does |
|---|---|
| `list_tables` | List all tables/views with row counts. |
| `describe_table` | Show columns + types for a table. |
| `find_customer` | Search customers by (partial) name or id → returns their `oid`. |
| `customer_insights` | **The headline tool.** Full profile for a customer: identity, contracts, outstanding/overdue balances, NPL flag, recent contact notes, loan applications. |
| `query` | Run an arbitrary **read-only** `SELECT`/`WITH` query. Auto-applies a `LIMIT`; blocks anything that writes. |
The database is opened **read-only**, and the `query` tool rejects any
non-`SELECT` statement and multi-statement input, so nothing can mutate the data.
## Setup
```bash
npm install
npm run build # compiles src/ -> dist/
```
## Connect it to Claude Desktop
1. Build (`npm run build`).
2. Copy `claude_desktop_config.json` from this folder to Claude Desktop's config
location (create the folder/file if it doesn't exist):
- **Windows:** `%APPDATA%\Claude\claude_desktop_config.json`
(`C:\Users\fookl\AppData\Roaming\Claude\claude_desktop_config.json`)
- **macOS:** `~/Library/Application Support/Claude/claude_desktop_config.json`
If you already have other MCP servers configured, merge the `mhtl-warehouse`
entry into your existing `mcpServers` object instead of overwriting the file.
3. Fully quit and reopen Claude Desktop.
4. In a new chat you should see the tools available (plug/tools icon). Try:
*"Get the insights of the customer Noy Vongphachanh."*
## How the data links together
- `dms_customer.oid` (BIGINT) ← `dms_contract.customer` (the numeric id).
- `dms_contract.contractid` ← `dms_contact_note.contract` / `dms_contact_legal.contract`.
- LOS ↔ DMS customers share their **last 5 id digits** 1:1
(`C500123` ↔ `L100123`), used to attach loan applications.
## Configuration
- `WAREHOUSE_DB_PATH` — absolute path to the DuckDB file. If unset, the server
defaults to `../data/mock.duckdb` relative to `dist/`.
## Project layout
```
src/index.ts MCP server + tool definitions
src/db.ts Read-only DuckDB connection + query/normalisation helpers
dist/ Compiled output (run this)
data/ mock.duckdb + parquet warehouse
```
TDQS
Scored across 5 tools
Each tool has a clearly distinct purpose: find_customer for searching customers, customer_insights for consolidated profile, list_tables and describe_table for schema discovery, query for arbitrary SQL. No overlap.
Four tools follow a consistent verb_noun pattern (find_customer, customer_insights, describe_table, list_tables). 'query' deviates as a single verb, but it's a common term and doesn't create confusion.
Five tools is well-scoped for a warehouse MCP server. It provides essential operations (schema discovery, customer lookup, SQL query) without unnecessary bloat.
Covers the main use cases: discovering schema, finding customers, getting insights, and querying. Minor gaps like a dedicated contract search tool, but SQL can cover those needs.