occulytics
Occulytics MCP Server
Ein MCP-Server, der einem KI-Assistenten ermöglicht, Portfolio-Fragen für ein Asset-Management-Team eines Healthcare-REIT (Omega Healthcare Investors) zu beantworten, gestützt auf zwei öffentliche Quellen: Omegas SEC-10-K-Einreichungen und die CMS-Datei „Nursing Home Provider Information“.
Das Designziel laut Brief: Der Server muss in der Lage sein, eine Antwort als vollständig, unsicher oder nicht unterstützt – und warum zu kennzeichnen – anstatt eine selbstbewusste Zahl zu liefern, die nichts stützt. Jedes Tool gibt deterministische Daten in einer Hülle zurück, die einen berechneten Status, Hinweise und Herkunft trägt.
Quickstart
Alles läuft offline – die Datenartefakte sind eingecheckt.
npm install
npm run build
npm test # 41 tests: curated-data checksums, domain units, full e2e over MCPProbieren Sie es in einer UI aus (MCP Inspector öffnet sich in Ihrem Browser):
npm run inspectVerbinden Sie sich mit Claude Code: Eine projektspezifische .mcp.json ist enthalten – öffnen Sie dieses Repo in Claude Code nach npm run build, und der occulytics-Server ist verfügbar. Oder registrieren Sie ihn global:
claude mcp add occulytics -- node /absolute/path/to/occulytics-mcp/dist/src/server/index.jsVerbinden Sie sich mit Claude Desktop (claude_desktop_config.json):
{
"mcpServers": {
"occulytics": {
"command": "node",
"args": ["/absolute/path/to/occulytics-mcp/dist/src/server/index.js"]
}
}
}Pre-Demo-Check, dass der kompilierte Server über echtes stdio funktioniert: npm run smoke. Zum Aktualisieren der Daten aus den Live-Quellen: npm run ingest (siehe Datenpipeline).
Related MCP server: Medical Billing MCP
Was Sie fragen können
Die fünf Ziel-Fragen und was der Server tatsächlich tut:
Frage | Antwortpfad | Ehrliches Ergebnis |
Top fünf Betreiber nach % der Investitionen, und wie viele Einrichtungen jeder betreibt? |
| Teilweise aus Design: Omega hat die vollständige Betreibertabelle nach seinem 10-K für das Geschäftsjahr 2020 eingestellt. Sie erhalten die vollständige Rangliste für FY2020 (mit Leasing-/Hypothekenaufschlüsselung – einschließlich der Tatsache, dass Ciena, nicht Consulate, bei Einbeziehung der Hypotheken tatsächlich auf Platz 1 war) und die namentlichen Offenlegungen für FY2025 (Maplewood ≥10%, CommuniCare 7,2%), jeweils datiert, nie vermischt. „Tatsächlich betreibt“ = aktuelle CMS-Kettenzahlen. |
Anteil der Einrichtungen der Top-Betreiber unter dem nationalen Personalbesetzungsdurchschnitt? |
| Pro Betreiber berechnet und serverseitig gegen den nationalen Mittelwert (3,86 gemeldete Pflegekräfte HPRD) gepoolt. Nicht zuordenbare Betreiber werden benannt und ausgeschlossen, nicht stillschweigend fallengelassen. |
Durchschnittliche Sternebewertung des größten Betreibers und Zweijahresrichtung? |
| Nicht unterstützt für Maplewood (größter nach Investitionen): Es betreibt Seniorenwohnanlagen, die keine CMS-zertifizierten Pflegeheime sind – der Server sagt das und warum. Für CommuniCare (größter nach Umsatz): durchschnittlich 3,05 Sterne, verbessert von 2,26 → 3,04 auf einem konstanten Panel mit 117 Einrichtungen (Juli 2024 → Juli 2026). |
Portfolio-Belegung? |
| Ein gekennzeichneter Proxy: Omega legt weder Belegung noch eine Einrichtungsliste offen. Bettgewichtete Belegung über zugeordnete Betreiberketten (83,5 % gegenüber 80,5 % national), mit Abdeckungsrechnung – welchen Anteil des Portfolios der Proxy tatsächlich repräsentiert und wer ausgeschlossen ist (UK-Betreiber, Maplewood, Karten mit geringer Konfidenz). |
Ein-Absatz-Exposure-Briefing zum größten Betreiber? |
| Das Modell schreibt den Absatz; der Server liefert nur deterministische Fakten: ≥10 % der Investitionen, 6,6 %/5,2 %/5,4 % Umsatztrend, die Notiz zur Kündigungsgebühr von 12,5 Mio. $ und die CMS-Abdeckungslücke. |
Architektur
Drei Schichten, eine Abhängigkeitsrichtung, keine Datenbank, kein Laufzeitnetzwerk:
scripts/ingest.ts CMS download → validate → project → data/processed/*.json (committed)
data/curated/*.json Hand-transcribed 10-K facts + operator→CMS map, per-fact citations
│
src/domain/ Pure, deterministic, unit-tested: store, resolve, metrics
│
src/server/ MCP wiring: 9 tools + 1 resource → envelope responses (stdio)data/curated/omega-10k.json— FY2025-Portfoliozusammenfassung + Konzentrationshinweis, FY2020-Betreiberinvestitionstabelle. Jeder Block zitiert seine Einreichung/Sektion.data/curated/operator-map.json— das Rückgrat der Ehrlichkeit: die CMS-Zuordnung jedes Omega-Betreibers mitmethod(chain-exact / legal-name-pattern / curated-alias),confidence(high/medium/low) und Hinweisen; nicht zuordenbare Betreiber tragen den Grund.src/domain/metrics.ts— die gesamte Arithmetik: Ranglisten, Belegung, Benchmark-Vergleiche, Sterne-Trends mit konstantem Panel. Nichts Numerisches bleibt dem Modell überlassen.src/server/tools.ts— dünn: Eingabe validieren (zod), Domäne aufrufen, in Envelope verpacken.
Die Antwort-Hülle
Jedes Tool gibt zurück:
{
"status": "complete" | "partial" | "unsupported", // brief's complete / uncertain / unsupported
"data": { /* deterministic numbers & records, never prose */ },
"caveats": [ /* why partial; staleness; method notes — computed, not decorative */ ],
"provenance": [ { "source", "asOf", "detail", "url" } ],
"cost": { "chars", "estTokens", "basis" } // self-reported payload size, labeled estimate
}status wird aus dem Datenpfad berechnet, nicht hartcodiert: Ein nicht zugeordneter Betreiber ergibt unsupported mit dem aufgezeichneten Grund des Zuordnungseintrags; alles, was die FY2020-Tabelle berührt, ist partial mit dem Veraltungshinweis; der Belegungs-Proxy ist immer partial.
Tool-Übersicht
Tool | Rückgabe | Roh oder aufgelöst? |
| FY2025-Gesamtsummen, Mischung, Geo + namentliche Betreiberkonzentration | aufgelöste Fakten, wie eingereicht |
| Zwei datierte Ranglistenblöcke (FY2020 vollständig / FY2025 namentlich) | aufgelöst; % aus eingereichten Dollar berechnet |
| Name → kanonischer Betreiber + CMS-Zuordnung + Konfidenz + 10-K-Kontext (FY2020-Rang/%, FY2025 offengelegte %) | Metadaten |
| paginierte Einrichtungszeilen + Zusammenfassung der Gesamtpopulation | Rohzeilen + aufgelöste Zusammenfassung |
| Sterne (Mittelwert + Verteilung pro Stern), Personal im Vergleich zum nationalen Durchschnitt, Belegung und 2-Jahres-Trends mit konstantem Panel für alle drei; gepoolter Block für mehrere Betreiber | aufgelöst (alle Arithmetik serverseitig) |
| Einrichtungs-Drilldown nach CCN/Name: aktuelle Kennzahlen, Verlauf pro Snapshot, umgekehrte Omega-Betreiber-Zugehörigkeit | Rohdetails + aufgelöste Zugehörigkeit |
| Proxy-Belegung + 2-Jahres-Trend + Abdeckungsrechnung | aufgelöst, explizit als Proxy gekennzeichnet |
| nationale Personal-/Stern-/Belegungsreferenzen + Methoden | aufgelöst |
| Quellen, Jahrgänge, Zuordnungen, bekannte Lücken (auch Ressource | Metadaten |
Begründung der Granularität: Tools sind fragenförmig, aber zusammensetzbar – deterministische Aggregation (wo LLM-Arithmetik über 100+ Zeilen ein Korrektheitsrisiko darstellt) ist eine Tool-Verantwortung; narrative Synthese ist Sache des Modells. Jedes Tool, das Betreiber entgegennimmt, akzeptiert Freitext und löst intern auf, sodass ein Client nie ein zweistufiges Protokoll benötigt; eine fehlgeschlagene Auflösung ist eine unsupported Antwort (mit Kandidaten und dem bekannten Universum), kein Fehler.
Quellenübergreifende Fragen (10-K-Teil ↔ CMS-Teil) sind erstklassig: Die Betreiberidentität ist der Join-Schlüssel, round-trip verifiziert (jeder Name in der 10-K-Rangliste löst sich in jedem CMS-gestützten Tool auf – e2e-getestet), und jeder aufgelöste Betreiberblock enthält seinen 10-K-Kontext (omegaContext: FY2020-Rang und % des Portfolios, FY2025 offengelegte Konzentration), sodass Fragen wie „Wie gut ist unser größter Betreiber?“ ohne zweiten Aufruf aufgelöst werden.
Wichtige Entscheidungen & Abwägungen
1. Zwei Jahrgänge, nie vermischt. Die entscheidende Forschungserkenntnis: Omegas 10-Ks nach FY2020 enthalten keine Tabelle mit Investitionen pro Betreiber – die FY2025-Einreichung nennt nur Maplewood (≥10 % der Investitionen) und CommuniCare (7,2 %). Eine aktuelle „Top Five“ ist daher aus den genannten Quellen nicht vollständig belegbar, und der Server sagt genau das: Ranglisten kommen als zwei separat datierte Blöcke, und der Status ist partial mit dem Grund. Abwägung: weniger befriedigend als eine saubere Liste; gewählt, weil eine vermischte Liste numerisch inkohärent wäre (2020-Dollar gegenüber 2025-Prozentsätzen auf unterschiedlichen Nennern).
2. Handübertragene SEC-Fakten, maschinell erfasste CMS-Daten. Die Omega-Fakten sind ~30 Zahlen in zwei Tabellen in zwei unterschiedlich formatierten Einreichungen. Ein generischer 10-K-Parser hat in diesem Umfang den schlimmsten möglichen Fehlermodus für dieses Briefing – stillschweigend falsche Extraktion. Stattdessen: kuratierte JSON mit Zitaten pro Fakt, geschützt durch Prüfsummentests (jede summierbare Spalte muss die eigenen Zwischensummen und Summen der Einreichung reproduzieren – ein Tippfehler lässt den Build fehlschlagen). Die CMS-Seite (14.693 Zeilen × 3 monatliche Jahrgänge) ist vollständig automatisiert mit Validierung, weil dort der Umfang die Automatisierung zur sichereren Option macht. Abwägung: Das Aktualisieren für einen neuen 10-K ist eine manuelle Bearbeitung; akzeptiert für ein jährlich eingereichtes Dokument.
3. Der Betreiber→CMS-Join ist ein kuratiertes, mit Konfidenz markiertes Artefakt. Keiner der Datensätze verweist auf den anderen. Der Join (10-K-Betreibername → CMS-Kette) ist die riskanteste Inferenz im System, also ist er Daten, nicht Code: Jede Zuordnung hält fest, wie sie erstellt wurde und wie sehr man ihr vertrauen kann, und nicht zuordenbare Betreiber halten fest, warum (Maplewood: Seniorenwohnen, außerhalb von CMS; Healthcare Homes: UK). Zuordnungen mit geringer Konfidenz (Agemo → Signature) werden standardmäßig aus gepoolten Aggregaten ausgeschlossen und bei Einbeziehung sichtbar gemacht. Abwägung: Skaliert nicht auf Hunderte von REITs; korrekt für die ~11 namentlich genannten Betreiber eines REITs, und der Mechanismus (Methode/Konfidenz/Hinweis pro Zuordnung) ist das, was skalieren würde.
4. Kettenkennzahlen sind Obermengen und sagen das. Omegas Portfolio auf Einrichtungsebene ist nicht öffentlich (verifiziert: Schedule III aggregiert nach Bundesstaat). CMS-Kennzahlen beschreiben daher den gesamten Betrieb eines Betreibers, nicht nur Omegas Gebäude – jede betroffene Antwort trägt diesen Hinweis, und der Belegungs-Proxy berichtet, welchen Anteil des (FY2020-)Portfolios seine Abdeckung repräsentiert (~40 %). Abwägung: Eine Rekonstruktion auf Einrichtungsebene aus der CMS-Eigentümerdatei war möglich, ist aber mehrtägige Fuzzy-Matching-Arbeit; der ehrliche Proxy mit Abdeckungsrechnung ist die Antwort in vier Stunden. Diese Rekonstruktion ist der natürliche nächste Schritt.
5. Methodik ist Teil der Antwort. Sterne-Trend = konstantes Panel (Einrichtungen, die in beiden Endpunkt-Snapshots bewertet wurden), mit Panelgröße, Ausschlüssen und der bekannten Verzerrung (Kettenmitgliedschaft nur aktuell) in der Antwort. Personal-Benchmark = berichtete gesamte Pflegekräfte-HPRD, Einrichtungsmittelwert (was die Frage verlangt, unbereinigt; fallmix-bereinigt existiert und wird vermerkt). Belegung = durchschnittliche Bewohner/Tag ÷ zertifizierte Betten, was die operative Belegung unterschätzt (zertifiziert > in Betrieb befindliche Betten). Alles in den Payloads angegeben, nicht nur hier.
6. In-Memory-JSON, keine Datenbank, Artefakte eingecheckt. 15.000 Zeilen laden in Millisekunden; eine DB fügt operative Angriffsfläche hinzu, ohne dass ein Abfragebedarf besteht. Eingecheckte Artefakte (~6 MB) bedeuten, dass Installieren → Bauen → Demo ohne Netzwerk funktioniert — die Live-Demo kann nicht durch einen CMS-Ausfall oder eine geänderte Download-URL kaputtgehen. Kosten: Das Repo trägt Daten; die Ingestion leitet sie jederzeit aus den Quellen neu ab.
7. Begrenzte Ausgaben. Einrichtungslisten sind paginiert (Standard 25) mit einem immer vollständigen Zusammenfassungsblock und Gesamtzahl — eine Kette mit 185 Einrichtungen überflutet nie den Client-Kontext.
Tests
tests/curated.test.ts— Transkriptions-Prüfsummen gegen die eigenen Summen der Einreichungen.tests/metrics.test.ts,tests/resolve.test.ts— Domäneneinheiten auf Fixtures (exakte Werte).tests/e2e.test.ts— ein echter MCP-Client über einen In-Memory-Transport gegen die echten Daten: ein Test pro Demo-Frage, einschließlich der nicht unterstützten Pfade.npm run smoke— der kompilierte Server über echtes stdio aus einem fremden Arbeitsverzeichnis.
Effizienz & Token-Kosten
npm run cost misst, was ein LLM-Client pro Demo-Frage an Kontext zahlt (Tool-Ergebnistext + einmalige Tool-Schemas), vollständig offline. Token-Zahlen sind Schätzungen (Zeichen ÷ 4; echte Tokenizer weichen ±20 % ab) — der Wert liegt in den relativen Kosten und der Regressionsverfolgung.
Aktuelle Messungen (eingecheckte Artefakte):
Frage | Aufrufe | Geschätzte Tokens |
Q1 Top-5 + Einrichtungszahlen | 2 | ~4,1k |
Q2 Personal unter Landesdurchschnitt | 1 | ~3,0k |
Q3 größter Betreiber Sterne + Trend | 2 | ~1,9k |
Q4 Portfolio-Belegung | 1 | ~1,0k |
Q5 Exposure-Briefing | 2 | ~1,4k |
Fünf-Fragen-Sitzung | 8 | ~11,4k (+ ~3,2k einmalige Schemas) |
Jede Antwort stempelt außerdem ihren eigenen cost-Block ({chars, estTokens, basis}), sodass der Assistent angeben kann, was eine Antwort an Kontext gekostet hat — als Schätzung gekennzeichnet, weil die echte Tokenisierung clientseitig erfolgt und der Server sie nie sieht (in Claude Code bleiben /cost und /context die Grundwahrheit auf Sitzungsebene).
Zwei bewusste Optimierungen halten das schlank (eine Reduktion um 31 % gegenüber der naiven Version, gemessen): Der modellgerichtete Textspiegel ist kompaktes JSON (allein der Pretty-Print-Leerraum war ~26 % des Payloads), und wiederholte Methodik-Strings stehen einmal pro Antwort in den Umschlag-Hinweisen statt auf jedem Trend-Block. Einrichtungslisten sind paginiert; Zusammenfassungen sind immer vollständig populationsbezogen. Der Kostenstempel selbst fügt ~21 Tokens pro Antwort hinzu — gemessen und den Mehraufwand für die Sichtbarkeit wert.
Datenpipeline
npm run ingest lädt data/processed/ herunter und baut es neu auf:
Löst die aktuelle Provider-Information-CSV-URL aus der CMS-PDC-Metastore-API auf (die Datei-URL ändert sich monatlich), lädt sie plus zwei archivierte Snapshots (Jul 2024, Jul 2025) für den Trend herunter.
Validiert (Zeilenanzahlen, erforderliche Spalten mit Header-Aliasing über CMS' Spaltenumbenennungen 2024→2025, Bewertungsbereiche, Nullraten) — schlägt laut fehl, schreibt nie Teil-Artefakte.
Projiziert auf drei Artefakte: Einrichtungs-Slice, CCN→Bewertungsverlauf, nationale Benchmarks (mit Methoden in der Datei vermerkt).
Rohe Downloads werden in data/raw/ zwischengespeichert (gitignored); --force lädt erneut herunter.
Repo-Struktur
data/curated/ hand-verified 10-K facts + operator map (source-cited, checksummed)
data/processed/ generated CMS artifacts (committed; rebuild with npm run ingest)
scripts/ ingest.ts, stdio-smoke.mjs
src/domain/ types, store, resolve, metrics — pure & unit-tested
src/server/ MCP tools + entry (stdio)
tests/ checksums, units, e2e
docs/ PLAN.md (build plan + audit trail), DEMO.md (presentation script)Bekannte Einschränkungen & nächste Schritte
Omega-eigene Einrichtungen sind nicht einzeln identifizierbar → Betreiberketten-Proxy (als Nächstes: Abgleich der Property-Company-Datensätze der CMS-Ownership-Datei).
Die Betreiber-Rangliste des aktuellen Jahres ist inhärent unvollständig (Offenlegung endete im Geschäftsjahr 2020); Omegas vierteljährliche Ergänzungen könnten das eingrenzen, liegen aber außerhalb der Quellen des Auftrags.
Trends (Sterne, Personal, Belegung) verwenden zwei Endpunkt-Snapshots plus einen Mittelpunkt; mehr monatliche Snapshots würden sie glätten.
Einrichtungen im Vereinigten Königreich (17,7 % der Immobilien) haben keine CMS-äquivalente Ingestion (CQC wäre die analoge britische Quelle).
Maintenance
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Related MCP Servers
- FlicenseNot gradedqualityDmaintenanceEnables AI-powered analysis of healthcare market segments, product comparisons, and sales data insights using natural language processing and retrieval-augmented generation.2
- AlicenseAqualityCmaintenanceEnables AI assistants to look up medical billing codes, denial reasons, and payer rules for faster claim resolution.66MIT
- FlicenseNot gradedqualityCmaintenanceEnables document search, grounded question answering, summarization, patient timeline extraction, and PHI redaction for healthcare documents using retrieval-augmented generation.
- AlicenseNot gradedqualityBmaintenanceEnables AI agents to query organizational architecture and governance constraints, returning evidence-grounded answers from documented structures.MIT
Related MCP Connectors
Certified SEC EDGAR fact memory for AI agents with zero hallucination and filing provenance.
Provide AI assistants with real-time access to official SEC EDGAR filings and financial data. Enab…
Deterministic compliance and vertical knowledge bases for autonomous agents. Free 24hr trial.
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/siddak1234/occulytics-mcp'
If you have feedback or need assistance with the MCP directory API, please join our Discord server