Content
# KETI FLOW MCP
This is an independent MCP server that learns blower/pump operating point data every time the server starts, and allows agents to query optimal control values using the MCP tool.
## Structure
```text
KETI_FLOW_MCP/
├─ src/
│ ├─ train/
│ ├─ mcp_server/
│ └─ utils/
├─ data/
├─ tests/
├─ config/
│ └─ config.json
├─ main.py
├─ pyproject.toml
├─ uv.lock
├─ README.md
└─ .gitignore
```
`src/mcp/` is not used as it may conflict with the package name `mcp` of the Python MCP SDK.
## Installation
```powershell
cd C:\Users\keti\workspace\KETI_FLOW_MCP
uv sync
```
The virtual environment is created in `.venv/`.
## Data
Training data is located under `data/`. This folder contains sensitive data and is not tracked by git.
The default settings use the following files:
```text
data/blower/fan_training.csv
data/pump/pump_training.csv
```
The default CSV columns are as follows:
```csv
Flowrate,Head,Power,Angle,Speed
```
Currently, the MCP tool takes the required flow rate `Flowrate` as input and finds the `Angle` value that minimizes `Power`.
## Configuration
The configuration file is `config/config.json`.
Main items:
- `data.base_dir`: The base directory for training data
- `machines.<name>.data_file`: The CSV path for each device
- `flow_column`: The flow column
- `control_column`: The control value column to optimize
- `target_column`: The target column to minimize or maximize
- `optimization`: `minimize` or `maximize`
- `candidate_count`: The number of real-time search candidates
- `respect_control_flow_range`: Whether to strictly apply the learned flow range for each control value
## Execution
```powershell
uv run python main.py
```
The server performs the following actions in order:
1. Load `config/config.json`
2. Load CSV files from `data/`
3. Learn blower/pump model memory
4. Start MCP stdio server
No model files or LUT files are generated.
## MCP Tools
### `get_optimal_blower_angle`
Input:
```json
{
"required_flow": 500.0
}
```
Response example:
```text
The optimal angle control value at this flow rate is 49. Predicted Power: 2.739 kW
```
Out-of-range response example:
```text
This flow rate is not within the learned data range. Supported range: 500 ~ 900
```
### `get_optimal_pump_control`
Input:
```json
{
"required_flow": 5.0
}
```
## MCP Resources
### `keti-flow://training-status`
Returns the learned model status, data file, number of rows, and flow range for the current server process.
## Codex Registration Example
Register in Codex MCP settings in the following format:
```json
{
"mcpServers": {
"keti-flow": {
"command": "uv",
"args": [
"--directory",
"C:\\Users\\keti\\workspace\\KETI_FLOW_MCP",
"run",
"python",
"main.py"
]
}
}
}
```
## Claude Registration Example
Add the following item to `mcpServers` in the Claude Desktop settings file:
```json
{
"mcpServers": {
"keti-flow": {
"command": "uv",
"args": [
"--directory",
"C:\\Users\\keti\\workspace\\KETI_FLOW_MCP",
"run",
"python",
"main.py"
]
}
}
}
```
## Local Verification
`tests/` is a folder for local verification and is not tracked by git.
Simple smoke verification:
```powershell
uv run python -c "from src.mcp_server.server import build_runtime; r=build_runtime(); print(r.status())"
```
Blower prediction verification:
```powershell
uv run python -c "from src.mcp_server.server import build_runtime, optimal_control_text; r=build_runtime(); print(optimal_control_text(r, 'blower', 500))"
```
## Git Exclusion
The following items are excluded from git:
- `data/`
- `tests/`
- `.venv/`
- Model output files
- Logs and local output files