Skip to content
FinVerify Banner

FinVerify

The verification layer for financial AI.

Deterministic correction for AI-generated numbers in the browser, in your backend, in your terminal.


Live Demo Β β€’Β  Docs Β β€’Β  Paper Β β€’Β  Model Β β€’Β  Discussions

License: Apache 2.0 Python 3.11 Next.js 14

Backend Tests SDK Tests PRs Welcome


Ecosystem Β· Extension Β· SDK Β· Benchmark Β· Features Β· Architecture Β· Pipeline Β· Core Components Β· Quick Start Β· Results Β· Research Β· Contributing



πŸ”’ Deterministic 🧾 Auditable 🌱 Open Source
Rule-based correction, not another model guess Every correction logged β€” rule, input, output Apache 2.0, actively developed, open to contributors

FinVerify Ecosystem

FinVerify isn't a single backend anymore it's a monorepo of interoperable components that all share the same verification core (the DVL). Start here, then go deeper via each component's own README.

Component What it does
🧩 finverify-extension Chrome extension providing inline financial verification inside AI chat UIs
πŸ–₯ finverify-terminal Backend services β€” REST API, WebSocket server β€” plus the terminal UI and market dashboard
πŸ“¦ finverify-sdk Official Python SDK (pip install finverify-sdk) for integrating FinVerify into your own applications
πŸ“Š finverify-bench Benchmark suite and evaluation harness for deterministic financial verification
πŸ”¬ research Papers, notebooks, experiments, and reproducibility assets

New here? Jump to Quick Start to run any of these locally, or Repository Structure for the full layout.


Why FinVerify

LLMs answering financial questions are often directionally right and numerically wrong β€” a decimal point misplaced, a percentage reported as a raw fraction, a sign flipped. In a regulated or capital-allocation context, that's not a rounding error. It's a liability.

Most fixes reach for more prompting. FinVerify reaches for a rule engine instead: the Deterministic Verification Layer (DVL). Scale, sign, and magnitude errors are mechanically distinct from reasoning errors β€” they need a rule, not another model call.

Underneath the DVL sits a Numeric Canonicalizer that parses raw numeric tokens into an unambiguous, Decimal-based representation before any correction rule runs, and a Constraint Engine that checks whether multiple claims are consistent with each other (e.g. does GrossProfit actually equal Revenue βˆ’ COGS) using a dependency graph and dimensional analysis, not just single-number correction.


Traditional AI Workflow FinVerify
Trust the output Verify the output
Probabilistic Deterministic
Hidden reasoning Auditable corrections
Fix errors with better prompts Fix errors with rules
Black box Transparent, logged, reproducible

Built for

πŸ› οΈ Developers Shipping AI products that surface financial numbers and need an auditable correction layer
πŸ”¬ Researchers Studying numerical hallucination, who need a reproducible, ground-truth-free method
πŸ“Š Analysts Using AI chat assistants for financial analysis who want a deterministic second check

Actively maintained Β Β·Β  Apache 2.0 Β Β·Β  Discussions enabled Β Β·Β  Extension in active development

TypeScript React Next.js Python FastAPI Mistral-7B (QLoRA) HuggingFace Playwright GitHub Actions


Chrome Extension

FinVerify's flagship surface. It verifies numbers in AI chat output inline, without leaving the page.


Chrome Extension Popup

Default popup state, provider connected.


Capability Description
Inline verification Numerical claims in a chat response run through the DVL as you read
Trust badges Each verified number gets a HIGH / MEDIUM / LOW badge from the Trust Engine
Verification report Expand a badge to see the correction rule, the original value, and the corrected value
Provider Adapters New chat surfaces can be added without touching the DVL

Inline Trust Badge

A HIGH / MEDIUM / LOW badge rendered next to an AI chat answer.



Verification Report

Expanded badge showing the correction rule, original value, and corrected value.


Built as a monorepo workspace (@finverify/core shared package) with separate build targets: content and background scripts as IIFE bundles, popup as an ES module. Playwright end-to-end tests against local chat-UI fixtures are in progress, alongside the existing unit test suite.


Python SDK

The official Python client for FinVerify β€” for developers who want DVL verification inside their own applications, without going through the extension or terminal UI.

pip install finverify-sdk
Capability Description
Sync + async clients FinVerify and AsyncFinVerify, identical public surface
Offline deterministic verification verify_local() runs the DVL correction rules in-process, no network call
Batch verification Verify multiple claims in one call
Typed models Dataclass response models, full type hints, py.typed marker
Automatic retries Exponential backoff with jitter on 429/5xx, honoring Retry-After

See finverify-sdk/README.md for the full API and finverify-sdk/CHANGELOG.md for release notes.


Benchmark

finverify-bench is the evaluation side of FinVerify: a benchmark suite and harness for measuring deterministic financial verification, independent of any single model.

  • Reproducible evaluation harness for FinQA-derived and synthetic samples
  • Ground-truth-blind DVL scoring β€” corrections never see the answer key
  • Documented benchmark methodology in BENCHMARK_DESIGN.md

See finverify-bench/README.md to run the harness yourself.


Features

Category Highlights
Verification DVL β€” deterministic scale, sign, and magnitude correction Β· Numeric Canonicalizer β€” Decimal-based numeric token parsing shared by DVL and the parser Β· Constraint Engine β€” dependency-graph + dimensional-analysis consistency checks across multiple claims Β· Batch Verification API β€” one shared constraint pass across a batch of claims Β· Trust Engine β€” delta-based confidence scoring
Browser Extension Inline trust badges and verification reports Β· Provider Adapter architecture Β· Monorepo workspace
Backend FastAPI REST + WebSocket API Β· Live market data verified through the DVL Β· SEC EDGAR & earnings-transcript ingestion Β· RAG pipeline (Pinecone + fallback)
Research FinVerifyBench β€” synthetic diagnostic benchmark Β· Reproducible FinQA evaluation harness Β· Published ablation study
Developer Experience Standalone SDK (pip install finverify-sdk) Β· Terminal UI Β· CI pipelines for backend and SDK
Open Source Apache 2.0 Β· CONTRIBUTING guide, Code of Conduct, Security policy Β· Issues triaged by label

Architecture

End-to-end

flowchart TD
    A[Browser: AI chat page] --> B[Provider Adapter]
    B --> C[DVL]
    C --> D[Backend: FastAPI]
    D --> E[Trust Engine]
    E --> F["UI (extension badge / terminal / dashboard)"]
Loading

Backend detail β€” single-claim pipeline

flowchart TD
    A[User Query] --> B{Query Classifier}
    B -->|advisory| C[LLM Only] --> D[Unverified Response]
    B -->|numerical| E["LLM Inference (Mistral-7B + QLoRA)"]
    E --> F["Numeric Canonicalizer: token β†’ Decimal + unit"]
    F --> G["DVL Pipeline: scale β†’ sign β†’ magnitude + audit log"]
    G --> H["Trust Engine (delta-based)"]
    H --> I[Verified Output + correction log]
Loading

Multi-claim pipeline β€” Constraint Engine

flowchart TD
    A["Batch of claims (POST /v1/verify/batch)"] --> B["verify() per claim (DVL)"]
    B --> C["Formula Parser + concepts.yaml"]
    C --> D["Constraint Graph (dependency order, cycle detection)"]
    D --> E["Dimensional Analysis (Currency / % / Ratio / PerShare / …)"]
    E --> F["Constraint Verifier (tolerance-based comparison)"]
    F --> G["BatchVerifyResponse: per-claim results + shared violations"]
Loading

Why it matters β€” every surface (extension, terminal, API) calls the same DVL for single-claim correction. The Constraint Engine adds a second, independent check across claims: does GrossProfit actually equal Revenue βˆ’ COGS, not just "is this one number formatted correctly."

TODO (unverified in-repo): the backend currently contains two constraint-checking code paths β€” backend/fcg/constraint_engine.py (older) and backend/core/financial/constraints/ (newer, described above). Both have live test suites. This README describes the newer constraints/ module since it's the one wired into verify_batch(); the relationship between the two, and whether fcg/ is being deprecated, isn't documented in the repo and should be clarified rather than assumed.

This diagram intentionally omits ingestion and RAG subsystems β€” see Repository Structure for those.


Verification Pipeline

The full flow a claim goes through, end to end:

  1. Input β€” a claim arrives either from LLM output (extension, terminal query) or as a direct API call (/verify, /v1/verify/batch).
  2. Claim Extraction β€” the numeric assertion and its associated concept (e.g. "gross margin") are pulled out of the surrounding text.
  3. Numeric Canonicalization β€” the raw numeric token is parsed into a structured, unambiguous form (Decimal value + unit), rejecting ambiguous input rather than guessing.
  4. DVL β€” scale, sign, and magnitude correction rules run against the canonicalized value, with every correction logged.
  5. Constraint Verification (multi-claim only) β€” if two or more related claims are present, they're checked against each other via the dependency graph and dimensional analysis, producing Violation or INDETERMINATE results rather than silently passing.
  6. Trust Engine β€” a delta-based confidence score is computed from how much correction was needed.
  7. Output β€” a VerificationResult (or BatchVerifyResponse for batches) containing the corrected value, the trust score, and the full audit trail.

Core Components

Numeric Canonicalizer (backend/numeric/canonicalizer.py) β€” the single source of truth for turning a raw numeric token into a Decimal value with an explicit unit. Deliberately refuses to guess on ambiguous input (e.g. locale-ambiguous grouping, unclear scale words) rather than silently picking an interpretation. Lives outside core/ specifically to avoid a circular import with app.dvl.

Constraint Engine (backend/core/financial/constraints/) β€” a formula parser, a dependency graph (Kahn's algorithm, explicit cycle reporting), and a tolerance-based verifier that together check whether multiple financial claims are mutually consistent, independent of whether any single claim's number is "correct" in isolation.

Formula Engine β€” the sole evaluator of parsed equations; the constraint parser deliberately only parses (produces an intermediate representation) and never evaluates, keeping evaluation logic in one place.

Trust Engine β€” computes a delta-based HIGH / MEDIUM / LOW confidence score from how much a claim's raw value had to be corrected.

Transcript Ingestion (backend/ingestion/transcripts.py) β€” extracts and verifies numerical claims from earnings-call transcripts.

Financial Constraint Graph β€” see the TODO above: this term currently refers ambiguously to either backend/fcg/constraint_engine.py (older) or the dependency graph inside backend/core/financial/constraints/graph.py (newer). Not yet resolved in-repo.


Quick Start

πŸ–₯ Backend

Runs the FastAPI verification service.

git clone https://github.com/aadityat23/finverify-llm.git
cd finverify-llm/finverify-terminal/backend
python -m venv venv
source venv/bin/activate
pip install -r requirements.txt
cp .env.example .env        # fill in HF_TOKEN
uvicorn app.main:app --reload --port 8000

πŸ–Ό Frontend

Runs the terminal and market dashboard UI.

cd finverify-llm/finverify-terminal/frontend
npm install
cp .env.local.example .env.local
npm run dev    # http://localhost:3000

πŸ“¦ SDK

Installs the standalone Python SDK for local, offline verification.

pip install finverify-sdk

For local development against this repo instead:

cd finverify-llm/finverify-sdk
pip install -e ".[dev]"

See finverify-sdk/README.md to use it against a hosted API instead of local, offline verification.

🧩 Chrome Extension

Builds the browser extension for inline verification.

cd finverify-llm/finverify-extension
npm install
npm run build

Load it via chrome://extensions β†’ Load unpacked.

Verify the backend is running:

curl http://localhost:8000/health

curl -X POST http://localhost:8000/verify \
  -H "Content-Type: application/json" \
  -d '{"question": "What was the profit margin?", "raw_number": 0.1240}'

curl http://localhost:8000/market/quotes?symbols=AAPL,TSLA

Showcase


Terminal

Query flow in the terminal-style UI.



Market Dashboard

Watchlist with verified metric cards and sparklines.


Screenshots are an open contribution β€” see Contributing.


Results

FinQA dev set, n=873, 95% bootstrap CI:

Configuration Accuracy 95% CI Ξ”
Baseline (no context) 1.00% [0.4, 1.9] β€”
+Document Context 24.00% [21.2, 26.9] +23.0pp
+DVL v1 32.00% [29.0, 35.1] +8.0pp
+QLoRA Fine-tuning 38.50% [35.4, 41.7] +6.5pp
+DVL v2 (final) 42.61% [39.5, 45.7] +4.1pp

Negative results: CoT prompting βˆ’9.0pp, CoT fine-tuning βˆ’12.0pp, cross-doc RAG βˆ’7.5pp.

At 42.61%, this is 5.4pp behind GPT-3.5 (no CoT, 48.0%) β€” using a model 25x smaller, no proprietary compute, and fully deterministic, auditable output.

The DVL only fires on formatting-level errors, not reasoning errors β€” see the error taxonomy below.

Error taxonomy (n=539 remaining failures)

Error type Count %
Reasoning (close, <50% rel.) 210 39.0%
Reasoning (far, >50% rel.) 184 34.1%
Magnitude 66 12.2%
Order-of-magnitude 62 11.4%
Sign 9 1.6%
Scale 4 0.8%

73.1% of remaining failures are reasoning errors, not correctable by the DVL. 0% are formatting or extraction failures after fine-tuning.


Repository Structure

finverify-llm/
β”œβ”€β”€ README.md                    # this file
β”œβ”€β”€ docs/                        # cross-component documentation, images
β”œβ”€β”€ artifacts/                   # build artifacts, exported reports
β”œβ”€β”€ finverify-extension/         # Chrome Extension (monorepo)
β”‚   β”œβ”€β”€ packages/
β”‚   β”‚   └── core/                 # @finverify/core β€” shared verification client
β”‚   β”œβ”€β”€ content/                  # content script (IIFE build)
β”‚   β”œβ”€β”€ background/                # background script (IIFE build)
β”‚   └── popup/                    # popup UI (ESM build)
β”œβ”€β”€ finverify-terminal/           # backend services + terminal/dashboard UI
β”‚   β”œβ”€β”€ backend/
β”‚   β”‚   β”œβ”€β”€ app/
β”‚   β”‚   β”‚   β”œβ”€β”€ main.py          # FastAPI app and route definitions
β”‚   β”‚   β”‚   β”œβ”€β”€ dvl.py           # Deterministic Verification Layer
β”‚   β”‚   β”‚   β”œβ”€β”€ router.py        # numerical vs advisory query classifier
β”‚   β”‚   β”‚   β”œβ”€β”€ parser.py        # numeric extraction from LLM text
β”‚   β”‚   β”‚   β”œβ”€β”€ market.py        # yfinance wrapper, DVL-verified metrics
β”‚   β”‚   β”‚   └── models.py        # request/response schemas
β”‚   β”‚   β”œβ”€β”€ numeric/             # Numeric Canonicalizer (Decimal-based token parsing)
β”‚   β”‚   β”œβ”€β”€ core/
β”‚   β”‚   β”‚   β”œβ”€β”€ engine.py        # verify(), verify_batch()
β”‚   β”‚   β”‚   β”œβ”€β”€ math_engine/     # DVL rule engine
β”‚   β”‚   β”‚   └── financial/
β”‚   β”‚   β”‚       └── constraints/ # Formula Parser, Constraint Graph, Dimensional Analysis, Verifier
β”‚   β”‚   β”œβ”€β”€ fcg/                 # TODO: older constraint-checking module β€” see note above on
β”‚   β”‚   β”‚                        # its relationship to core/financial/constraints/, unresolved in-repo
β”‚   β”‚   β”œβ”€β”€ ingestion/           # SEC EDGAR and earnings-transcript ingestion
β”‚   β”‚   β”œβ”€β”€ rag/                 # retrieval pipeline (Pinecone + fallback search)
β”‚   β”‚   └── evals/               # cross-model evaluation harness
β”‚   └── frontend/
β”‚       β”œβ”€β”€ app/                 # Next.js pages: terminal, market, metrics
β”‚       β”œβ”€β”€ components/          # TrustScore, DVLReport, VerificationLog, etc.
β”‚       └── lib/                 # API client, offline DVL fallback, history
β”œβ”€β”€ finverify-sdk/                # standalone `pip install finverify-sdk` package
β”‚   └── finverify/                # SDK source β€” sync/async clients, typed models
β”œβ”€β”€ finverify-bench/               # benchmark suite and evaluation harness
β”‚   β”œβ”€β”€ BENCHMARK_DESIGN.md        # methodology and construction notes
β”‚   └── DVL_mapping/               # ground-truth-blind DVL evaluation mapping
└── research/                     # papers, notebooks, experiments, reproducibility assets
Component reference (click to expand)
Component Path Purpose
Chrome Extension core finverify-extension/packages/core Shared verification client used across content/background/popup
DVL engine backend/app/dvl.py Scale/sign/magnitude correction with audit logging
Numeric Canonicalizer backend/numeric/canonicalizer.py Decimal-based numeric token parsing shared by DVL and the parser
Constraint Engine backend/core/financial/constraints/ Formula parsing, dependency graph, dimensional analysis, tolerance-based multi-claim verification
Batch Verification backend/core/engine.py (verify_batch) Β· POST /v1/verify/batch One shared constraint pass across a batch of claims
Query classifier backend/app/router.py Routes numerical vs advisory queries
Market layer backend/app/market.py Live yfinance data, DVL-verified financial metrics
Financial Constraint Graph (legacy) backend/fcg/constraint_engine.py Older multi-number accounting-identity checker; TODO β€” relationship to the newer Constraint Engine above is not documented in-repo
SEC EDGAR ingestion backend/ingestion/sec_edgar.py XBRL/fallback ingestion of 10-K/10-Q fundamentals
Earnings transcript verification backend/ingestion/transcripts.py Regex extraction and DVL verification of earnings-call claims
RAG pipeline backend/rag/pipeline.py Pinecone vector + keyword-overlap fallback retrieval
WebSocket server backend/app/main.py Real-time market data push (5s interval)
Terminal UI frontend/app/page.tsx Terminal-style query interface, three-panel layout
Market mode frontend/app/market/page.tsx Live watchlist, verified metric cards, sparklines
Metrics dashboard frontend/app/metrics/page.tsx Paper results, ablation study, error taxonomy
Python SDK finverify-sdk/finverify/ Sync/async client, typed models, verify_local() offline mode
Benchmark suite finverify-bench/ FinVerifyBench dataset, DVL evaluation mapping, design docs

Test suite size: finverify-terminal/backend/tests/ currently defines 224 test functions across 19 files (largest: test_constraint_engine.py with 37, test_numeric_canonicalizer.py with 23). This count was taken directly from the test files, not from a CI run β€” TODO: confirm the actual passing count from a real pytest run in CI, since the backend's heavier dependencies (torch, transformers) weren't installed for this audit.


API Reference

Method Path Description
POST /query LLM inference + DVL verification
POST /verify DVL-only verification, no LLM call
GET /health Health check
GET /market/quotes?symbols=AAPL,TSLA Live stock quotes
GET /market/indices S&P 500, NASDAQ, VIX
GET /market/verified-metrics?symbol=AAPL&metric=profit_margin DVL-verified metric
GET /market/all-metrics?symbol=AAPL All five metrics for a symbol
POST, GET /v1/fcg/* FCG endpoints: verify, normalize, list constraints
POST, GET /v1/rag/* RAG endpoints: query, stats, seed
GET, POST, DELETE /v1/history/* User query-history persistence
WS /ws/market Real-time market data stream

/v1/fundamentals/{ticker}, /v1/earnings/{ticker}, and /v1/ingest/* are also exposed, for on-demand SEC and transcript ingestion. Endpoint-by-endpoint documentation is an open contribution β€” see Contributing.


Research

Paper Modular Verification Outperforms Chain-of-Thought Reasoning in Small Financial LLMs: A Systematic Ablation Study on Numerical Hallucination Reduction
Submitted to FinNLP @ EMNLP 2026 / IEEE Access
Author Aaditya Thokal, Universal College of Engineering, Mumbai β€” aaditya.thokal24@gmail.com
Model aadi2026/finverify-lora β€” Mistral-7B + QLoRA, trained on 2,000 FinQA examples
Dataset FinQA dev set (n=873); FinVerifyBench isolates formatting-level errors from reasoning errors

Roadmap

Tracked through GitHub Milestones β€” here's where things stand, and where help is most useful.

Core Infrastructure

  • βœ… FastAPI backend, WebSocket market stream
  • βœ… CI pipelines for backend and SDK
  • πŸ”§ API stability & docs for ingestion routes

Verification Engine

  • βœ… DVL, Trust Engine
  • βœ… Numeric Canonicalizer
  • βœ… Constraint Engine (formula parser, dependency graph, dimensional analysis)
  • βœ… Batch Verification API
  • πŸ”§ Reconciling backend/fcg/ (legacy) with the newer core/financial/constraints/ module
  • πŸ“‹ Verification methods beyond scale/sign/magnitude

Browser Extension

  • βœ… Core, monorepo restructure, Provider Adapters
  • πŸ”§ Playwright E2E against chat-UI fixtures
  • πŸ“‹ Additional Provider Adapters

Developer Experience & Research

  • βœ… Standalone SDK, Terminal UI
  • πŸ”§ Expanding backend test coverage
  • πŸ“‹ Broader model evaluation, deployment tooling

βœ… Completed πŸ”§ In progress πŸ“‹ Planned


Contributing

FinVerify is a young project with a lot of open surface area β€” there's a meaningful way to contribute regardless of your background.

Start with CONTRIBUTING.md for setup and workflow, and CODE_OF_CONDUCT.md for community guidelines.

Label Good for
good first issue Self-contained, no deep internals required
help wanted Open tasks looking for a contributor
research Benchmark design, ablations, evaluation methodology
backend FastAPI, DVL, ingestion, RAG
frontend Next.js terminal and dashboard
extension Chrome Extension, Provider Adapters, Playwright E2E
documentation Endpoint docs, guides, screenshots

First open-source contribution? good first issue is the place to start.


Community

🌐 Website Live Demo
πŸ’¬ Discussions GitHub Discussions β€” design questions, feedback, "is this worth doing" conversations
πŸ› Issues GitHub Issues β€” bugs and tracked work
πŸ“„ Contributing guide CONTRIBUTING.md
πŸ‘₯ Contributors CONTRIBUTORS.md

FinVerify was created and is maintained by Aaditya Thokal, University of Mumbai/ IITM.


License

Apache License 2.0 β€” see LICENSE.


If FinVerify is useful to you, consider starring the repository. ⭐