Skip to content
Get Started

Getting Started

Self-Host Mirobody

Run the Mirobody engine on your own infrastructure: what you get, the three stages, how the data flows, and how to extend it.

Run Mirobody on your own machine, server, or cloud instance. The engine is open source under Apache 2.0 — a Python package (3.12+) usable as a library, plus an HTTP server, a background worker, PostgreSQL with pgvector, and Redis when you want the full capability. The source is at thetahealth/mirobody.

For what Mirobody is and the problem it solves, start at Introduction to Mirobody. This page is about running it yourself.

The code layout, the contribution areas and this documentation all follow the same three stages — C · S · A, where the A is both Answers and the agent that produces them.

StageWhat it meansWhere in the package
CollectTake data in from device providers, uploaded documents and on-device batchesmirobody/pulse/
StandardizeResolve readings to canonical codes (LOINC · SNOMED CT · RxNorm), normalize units, store as FHIR R4mirobody/indicator/
AnswersAn agent reads the original documents through a virtual filesystem and answers with charts and citations. The same standardized series also drives the derived uses: scheduled insights, a drafted report, or the alerts you build on topmirobody/agent/

The same measurement is written differently by every source that produces it, with its own units and reference ranges — differences that are enough to stop one person’s own history from being compared against itself. That is the layer Mirobody occupies: an indicator name is resolved before the reading is stored, rather than kept as the string it arrived as. 血红蛋白, ヘモグロビン and hemoglobin all resolve to LOINC 718-7; LDL-C and 低密度脂蛋白胆固醇 both resolve to LOINC 13457-7. Units are normalized to UCUM in the same pass, so 毫摩尔每升 and mmol/L are recorded as one unit. The result is that reports from different devices, laboratories and languages can be placed on a single time series.

Resolution runs locally against vocabularies shipped inside the package — no key, no configuration, and no network connection:

Terminal window
pip install mirobody
mirobody resolve "LDL cholesterol" "血红蛋白" "ヘモグロビン"
from mirobody.engine import resolve
resolve("血红蛋白").loinc # -> '718-7'

Standardization is installable on its own, so this stage can be adopted without running the rest of the services. The resolution rules and the shipped vocabularies are described in Health Indicators; the library API is in The Engine as a Library.

Providers and on-device batches converge on StandardPulseData before anything is written; file extraction writes straight to the store, keeping the report’s own indicator names for semantic search to reconcile. Both routes land in the same indicator table, which is why the agent queries indicators rather than one shape per vendor. The write path, the two tables behind it and the aggregation that follows are described in Data Flow.

There is an agent for each, and the difference is who runs the tool loop.

DeepAgent — you run the engineBaseAgent — an external model calls in
Tool loop runshere, in your deploymentin the LLM provider, against /mcp over HTTP
Forrunning the whole engine yourselfClaude Desktop · Cursor · ChatGPT Apps · any MCP client
Extrasvirtual filesystem, QuickJS, Agent Skills, chartswhatever the MCP tool surface exposes

The engine mints a per-user MCP URL on request — POST /personal/mcp — so one person’s MCP client reaches only their own data. The bundled web client offers it under Settings; your own client can call the endpoint directly. See Agent Types and MCP Integration.

Five configuration keys each point at a set of directories, which the engine scans at startup. Extending it requires no compile step and no entry in any registry.

KeyDefaultWhat goes there
MCP_TOOL_DIRSmirobody/agent/toolsTool modules: a function or a *Service class becomes an MCP tool
MCP_RESOURCE_DIRSmirobody/agent/resourcesMCP UI resources
AGENT_DIRSmirobody/agentAgent implementations
PROVIDER_DIRSmirobody/pulse/providersData providers, one mirobody_<slug>/ package per source
SKILL_DIRSmirobody/agent/skillsAgent Skills: a directory holding one SKILL.md

Add your own directory in config.{env}.yaml and place it first in the list to take precedence over the packaged one. See Adding Custom Tools, Agent Skills and Building a Provider.

Self-hosting is one of two ways to run Mirobody, and each comes with finished surfaces, not only an API:

SurfaceAddressWhat it is
Your own deploymentlocalhost:18080git clone./deploy.sh → sign in. Your data stays on your machine, and the bundled web client is a full app: /data for documents and readings, /ask for the agent, plus Care Circle sharing: a member can let family — or a clinician — ask the AI using their records.
Your MCP endpointlocalhost:18080/mcpFor Claude Desktop / Cursor. Set MCP_PUBLIC_URL for HTTPS and remote clients.
Hosted chatchat.mirobody.aiThe client we operate.
Mirobody Cloudplatform.mirobody.aiKeys, usage, and the health-data API for building on top; see the Cloud tab.
WeChat miniprogramsearch mirobody in WeChatChina only, Chinese interface. Same backend, same records and indicators as the hosted chat client.

Run it

Follow the Quickstart: clone, ./deploy.sh, sign in.

Configure it

Add an LLM key and an embedding key in config.{env}.yaml; see Configuration. They are two different keys, and the second one is why indicators stay at 0 when it is missing.

Understand it

Read The Engine as a Library for the install layers, then the Architecture Overview.

Extend it

Add a tool with Adding Custom Tools, or a data source with Building a Provider.

Contributions are organized around the same three stages. The lowest-barrier kind is making an unresolved indicator name resolve: check it with mirobody resolve "<term>", add a mapping to resolver_overrides.tsv, and add a case to test_engine_coverage.py.