How to Build a compliance checking Agent Using LlamaIndex in TypeScript for insurance

By Cyprian AaronsUpdated 2026-04-21
compliance-checkingllamaindextypescriptinsurance

A compliance checking agent for insurance reads policy documents, claims notes, underwriting guidelines, and regulatory rules, then flags whether a case violates internal or external requirements. It matters because insurance teams need fast, repeatable checks with an audit trail: missed disclosures, bad claims handling, and inconsistent underwriting decisions turn into regulatory exposure very quickly.

Architecture

  • Document ingestion layer

    • Pulls in policy wordings, underwriting manuals, claims procedures, and regulator guidance.
    • Stores source metadata like document version, jurisdiction, and effective date.
  • Indexing layer

    • Uses LlamaIndex to turn those documents into a searchable knowledge base.
    • Keeps chunks small enough for retrieval but large enough to preserve clause context.
  • Compliance rules layer

    • Encodes insurer-specific checks such as disclosure requirements, waiting periods, exclusions, appeal timelines, and claim handling SLAs.
    • Separates hard rules from advisory guidance.
  • Retrieval + reasoning layer

    • Retrieves the most relevant clauses for a case.
    • Asks the model to produce a structured compliance verdict with citations.
  • Audit logging layer

    • Persists every input, retrieved source, decision, and confidence score.
    • This is non-negotiable in insurance.
  • Human review workflow

    • Routes borderline cases to compliance officers.
    • Prevents the agent from being the final authority on high-risk decisions.

Implementation

1) Install dependencies and prepare your documents

Use LlamaIndex’s TypeScript packages plus a local or hosted model provider. For insurance workloads, keep your source docs in a controlled store and attach metadata for jurisdiction and document type.

npm install llamaindex dotenv
import "dotenv/config";
import { Document } from "llamaindex";

const docs = [
  new Document({
    text: `
      Claims must be acknowledged within 2 business days.
      Denials must include the exact policy clause relied upon.
      Appeals must be accepted within 30 days of denial.
    `,
    metadata: {
      docType: "claims_policy",
      jurisdiction: "UK",
      version: "2025.01",
      source: "internal-compliance-manual"
    }
  }),
  new Document({
    text: `
      Pre-existing condition exclusions apply only if explicitly disclosed
      in the schedule and approved by legal review.
    `,
    metadata: {
      docType: "underwriting_guideline",
      jurisdiction: "UK",
      version: "2025.01",
      source: "internal-underwriting-manual"
    }
  })
];

2) Build an index over the compliance corpus

For this pattern, VectorStoreIndex.fromDocuments() is the simplest starting point. In production you can swap the vector store behind it without changing the retrieval flow.

import {
  VectorStoreIndex,
  Settings,
} from "llamaindex";

Settings.chunkSize = 512;
Settings.chunkOverlap = 80;

const index = await VectorStoreIndex.fromDocuments(docs);
const retriever = index.asRetriever({ similarityTopK: 4 });

3) Query with a structured compliance prompt

The key is not “does this sound right,” but “which rule was violated, what evidence supports that conclusion, and what should happen next.” Use asQueryEngine() for direct Q&A or retrieve first when you want tighter control over citations.

import { OpenAI } from "@llamaindex/openai";

const llm = new OpenAI({
  model: "gpt-4o-mini",
});

Settings.llm = llm;

const queryEngine = index.asQueryEngine({
  retriever,
});

const caseNote = `
Claim ID C-1042:
Customer reported loss on day 18 after policy start.
Agent approved payout without checking waiting period clause.
No denial letter was generated.
`;

const response = await queryEngine.query({
  query: `
You are a compliance checker for an insurance carrier.
Review the case note against the indexed policies.
Return:
1. verdict: PASS | FAIL | REVIEW
2. violated_rules: array of short strings
3. evidence: quoted snippets from sources
4. action_required: next operational step

Case note:
${caseNote}
`
});

console.log(String(response));

4) Add a deterministic review gate for high-risk outcomes

Do not let the model auto-close claims or underwriting decisions. Wrap the output in a simple policy gate so any denial-related or jurisdiction-sensitive result gets escalated.

type Verdict = "PASS" | "FAIL" | "REVIEW";

function routeDecision(verdict: Verdict, jurisdiction: string) {
  if (jurisdiction === "UK" && verdict !== "PASS") return "human_review";
  if (verdict === "FAIL") return "human_review";
  return "auto_log";
}

const decision = routeDecision("FAIL", "UK");
console.log({ decision });

Production Considerations

  • Keep data residency explicit

    • Insurance data often cannot leave a region.
    • Pin storage, embeddings, and model endpoints to approved jurisdictions.
  • Log every retrieval step

    • Save query text, top-k chunks returned by Retriever, final verdict, model version, and timestamps.
    • Auditors will ask why a specific clause was surfaced.
  • Separate policy sources by line of business

    • Life, health, auto, and property have different rule sets.
    • Mixing them increases false positives and creates bad citations.
  • Use guardrails around final actions

    • The agent can recommend outcomes, but claims payment changes or denial letters should require approval for sensitive cases.
    • Add thresholds based on claim amount, complaint history, or jurisdiction.

Common Pitfalls

  • Using generic RAG without metadata

    • If you do not tag documents by jurisdiction and version, you will retrieve outdated clauses.
    • Fix it by storing docType, jurisdiction, version, and effectiveDate in every Document.
  • Letting the model decide without citations

    • A free-form answer is useless during audits.
    • Force structured output with verdicts plus quoted evidence from retrieved sources.
  • Treating all compliance issues as equal

    • Missing an acknowledgment SLA is not the same as denying a protected-class claim incorrectly.
    • Build severity levels and escalate anything that affects customer rights or regulated communications.

Keep learning

By Cyprian Aarons, AI Consultant at Topiax.

Want the complete 8-step roadmap?

Grab the free AI Agent Starter Kit — architecture templates, compliance checklists, and a 7-email deep-dive course.

Get the Starter Kit

Related Guides