The embedded MCP server (/mcp/messages, powered by spring-ai-starter-mcp-server-webmvc) silently drops all search parameters when translating MCP tool calls into FHIR REST search requests. This causes patient-scoped queries to return unfiltered, server-wide results — a serious data isolation issue when handling PHI.
Environment:
hapi-fhir-jpaserver-starter Docker image (latest as of Aug 2026)
Spring AI MCP dependency: spring-ai-starter-mcp-server-webmvc:1.1.0-M1
MCP client: mcp-remote@latest via Claude Desktop
Database: H2 (default) / PostgreSQL (also tested)
Steps to reproduce:
- Start hapi-fhir-jpaserver-starter with default MCP config
- Connect via mcp-remote in Claude Desktop:
{
"mcpServers": {
"hapi": {
"command": "npx",
"args": ["-y", "mcp-remote@latest", "http://localhost:8080/mcp/messages"]
}
}
}
- Create 2+ Patient resources with associated Conditions
- Use the MCP search-fhir-resources tool to search Conditions scoped to one patient:
resourceType: "Condition", query: "patient=Patient/"
- Observe HAPI access log
Expected behavior:
HAPI access log shows the search parameters and returns only resources matching the patient filter:
Operation[search-type Condition] Params[?patient=Patient%2F<id>&_count=100]
Actual behavior:
HAPI access log shows empty parameters — every search parameter is silently dropped:
Operation[search-type Condition] UA[] Params[] ResponseEncoding[JSON]
All Condition resources across all patients are returned regardless of the patient filter.
Proof that HAPI's REST API is not the issue:
A direct curl to the same HAPI instance with the same parameters works correctly:
curl "http://localhost:8080/fhir/Condition?patient=Patient%2F<id>&_count=100"
Access log confirms parameters are received and filtering works:
Operation[search-type Condition] UA[curl/8.7.1] Params[?_count=100&patient=Patient%2F<id>]
Additional observation — MCP protocol version mismatch:
The HAPI log also shows:
Client requested unsupported protocol version: 2025-11-25, so the server will suggest the 2025-06-18 version instead
This version negotiation fallback may be contributing to the parameter loss, as structured tool-call arguments could be dropped or malformed during the protocol downgrade.
Impact:
This is a PHI data isolation failure. Queries intended for a single patient silently return data for every patient on the server, with no error or warning. Any MCP-based client (Claude Desktop, Cursor, etc.) using the built-in MCP endpoint will unknowingly receive cross-patient data.
The embedded MCP server (/mcp/messages, powered by spring-ai-starter-mcp-server-webmvc) silently drops all search parameters when translating MCP tool calls into FHIR REST search requests. This causes patient-scoped queries to return unfiltered, server-wide results — a serious data isolation issue when handling PHI.
Environment:
hapi-fhir-jpaserver-starter Docker image (latest as of Aug 2026)
Spring AI MCP dependency: spring-ai-starter-mcp-server-webmvc:1.1.0-M1
MCP client: mcp-remote@latest via Claude Desktop
Database: H2 (default) / PostgreSQL (also tested)
Steps to reproduce:
resourceType: "Condition", query: "patient=Patient/"
Expected behavior:
HAPI access log shows the search parameters and returns only resources matching the patient filter:
Operation[search-type Condition] Params[?patient=Patient%2F<id>&_count=100]Actual behavior:
HAPI access log shows empty parameters — every search parameter is silently dropped:
Operation[search-type Condition] UA[] Params[] ResponseEncoding[JSON]All Condition resources across all patients are returned regardless of the patient filter.
Proof that HAPI's REST API is not the issue:
A direct curl to the same HAPI instance with the same parameters works correctly:
curl "http://localhost:8080/fhir/Condition?patient=Patient%2F<id>&_count=100"Access log confirms parameters are received and filtering works:
Operation[search-type Condition] UA[curl/8.7.1] Params[?_count=100&patient=Patient%2F<id>]Additional observation — MCP protocol version mismatch:
The HAPI log also shows:
Client requested unsupported protocol version: 2025-11-25, so the server will suggest the 2025-06-18 version insteadThis version negotiation fallback may be contributing to the parameter loss, as structured tool-call arguments could be dropped or malformed during the protocol downgrade.
Impact:
This is a PHI data isolation failure. Queries intended for a single patient silently return data for every patient on the server, with no error or warning. Any MCP-based client (Claude Desktop, Cursor, etc.) using the built-in MCP endpoint will unknowingly receive cross-patient data.