Inspiration

Prior authorization costs the US healthcare system $35 billion a year in administrative waste. Physicians spend 13 hours a week on it, 39 requests each. 94% say it delays care. 29% say it caused a serious adverse event in their patients. 78% have seen a patient abandon treatment because the paperwork took too long.

We kept asking the same question: why is a physician, who spent a decade in medical school, spending their afternoon copy-pasting lab values into an insurance form? The answer is there was no open, trustworthy alternative. We built one.

What it does

PA Navigator automates the prior authorization workflow end-to-end. It connects to any FHIR R4 EHR, pulls the patient's live clinical record, and matches every fact against the payer's criteria using Gemini. It then drafts a formal medical necessity justification letter where every clinical claim is cited to a specific FHIR resource ID.

The physician gets a ready-to-review letter in minutes instead of hours. They check it, sign it, and submit. The agent never submits autonomously. Every claim is traceable. Nothing is invented.

How we built it

The stack is entirely open standards:

  • FHIR R4 for patient data, connecting to any compliant EHR without custom integrations
  • MCP (Model Context Protocol) exposing 8 clinical tools any AI assistant can call
  • A2A (Agent-to-Agent) for the agent layer, deployed on Prompt Opinion with FHIR context injection via the extension schema
  • ChromaDB for payer policy RAG, criteria chunked and embedded at build time, searched semantically at runtime
  • Gemini 2.5 Flash via LiteLLM for criteria matching and letter drafting, temperature=0, 8192 token budget
  • HAPI FHIR R4 as the demo data layer with three synthetic RA patients, no PHI

Source code: https://github.com/AtharvaWaghchoure/pa-navigator

Challenges we ran into

Gemini 2.5 Flash uses internal thinking tokens that consume from the max_tokens budget. At 4096 tokens the JSON response was silently truncating mid-object, causing parse failures with no obvious error. Increasing to 8192 fixed it.

Getting the LLM to only mark criteria as "met" when it had a real FHIR resource to cite was harder than expected. Early runs were marking "no contraindications documented" as met based on absence of evidence. We rewrote the system prompt with explicit rules and added a post-processing deduplication guard.

FHIR resource IDs needed to carry their type prefix (Condition/id, MedicationRequest/id) or the LLM would invent its own formats. A small structural fix in the FHIR extraction layer made all citations consistent and verifiable.

Accomplishments that we're proud of

Every MET criterion in the output is backed by a real FHIR resource ID that exists on the server and belongs to the correct patient. We verified this manually across all three demo scenarios. The letter is not just plausible, it is auditable.

The MCP server is live on the Prompt Opinion marketplace. The A2A agent is deployed and responding. The full pipeline runs against real FHIR data with no mocked steps.

What we learned

Open standards compose well when you respect the boundaries. FHIR handles the data layer, MCP handles the tool layer, A2A handles the agent layer. Each does one thing cleanly and hands off to the next.

Clinical AI needs a different bar for evidence than general AI. "Probably true" is not acceptable when a treatment delay could harm a patient. Conservative defaults, explicit evidence requirements, and human review gates are not optional.

What's next for PA Navigator

Expanding the policy library beyond Aetna adalimumab to cover multiple payers and drug classes. Adding support for Da Vinci PAS v2.1.0 so the approved letter can be submitted directly through the FHIR PA API. Building a physician-facing UI for reviewing and editing the letter before signing. Exploring real EHR integrations through SMART on FHIR for production use cases.

Built With

  • a2a-sdk
  • chromadb
  • fastapi
  • fhir-r4
  • gemini-2.5-flash
  • google-adk
  • hapi-fhir
  • litellm
  • mcp-sdk
  • python
Share this project:

Updates