Skip to main content

VikingRAG 0.4.0

VikingRAG

Structure-aware retrieval for documents that actually have structure.

Production hierarchical RAG inspired by the VikingRAG paper.
Hierarchy-preserving ingestion. Multi-granular semantic Search. Built to extend.

GitHub stars   GitHub forks   GitHub watchers

Release v0.4.0 Apache 2.0 Python 3.12+ FastAPI PostgreSQL + pgvector Redis PyPI arXiv paper

Install · Features · Architecture · Quick start · SDK · API · Docs · Cite

LinkedIn   mhuzaifa.com   GitHub


Why VikingRAG?

Classic RAG often flattens documents into unrelated chunks. Structure is lost - sections, subsections, and provenance disappear into a top-k bag of text.

VikingRAG (Gao et al., 2026) showed that hierarchy-preserving storage, multi-granular indexing, evidence-gap tools (Search / List / Grep / Read), and adaptive escalation can improve accuracy while cutting tokens.

This project turns those ideas into a production-ready stack:

Research idea This repo today
Hierarchical documents document → section → subsection → chunk with stable + canonical object URIs
Multi-granular indexing Bottom-up abstracts + embeddings at document/section/chunk
Semantic Search pgvector cosine discovery returning viking:// URIs
Cheap path / agents Algorithm 1 agentic loop; E+ one-round fast path then escalate
Evidence-first grounding Authoritative Reads, citations, POST /v1/answers
Experience edges Algorithm 2 construction + Algorithm 3 Search+ (γ-gated)
Production constraints Auth allowlist, migrations, prod Compose, eval smoke, typed settings

Independent implementation inspired by the paper - not a fork of the AGPL research artifacts.

Comparison visuals

Drop charts into docs/assets/ (see that folder’s README), then uncomment:

Best place for side-by-side paper-style figures is right here (under Why), or a short Results section after Features. Use only real measurements or clearly cited paper figures — never invent scores.


Install

Option A — PyPI (fastest on any laptop)

python -m venv .venv && source .venv/bin/activate   # Windows: .venv\Scripts\activate
pip install -U vikingrag
# optional richer DOCX parsing:
# pip install "vikingrag[docx]"

You still need Postgres + pgvector and Redis, plus a .env (copy from the repo .env.example):

export VIKINGRAG_DATABASE_URL=postgresql+asyncpg://vikingrag:vikingrag@localhost:5432/vikingrag
export VIKINGRAG_REDIS_URL=redis://localhost:6379/0
export VIKINGRAG_LLM_PROVIDER=fake          # or openai / deepseek / gemini / anthropic
export VIKINGRAG_EMBEDDING_PROVIDER=deterministic

vikingrag-migrate upgrade head
vikingrag-api
# API: http://localhost:8000/docs

SDK:

from vikingrag import VikingRAGClient
client = VikingRAGClient.from_settings()

Option B — Clone + uv (full stack / contributors)

git clone https://github.com/mhuzaifadev/VikingRAG.git
cd VikingRAG
cp .env.example .env
# Python 3.12+, https://docs.astral.sh/uv/
make install && make docker-up && make migrate && make dev

Option C — pip from GitHub (pre-release / specific tag)

pip install "git+https://github.com/mhuzaifadev/VikingRAG.git@v0.4.0"

Option D — Docker Compose

git clone https://github.com/mhuzaifadev/VikingRAG.git && cd VikingRAG
cp .env.example .env
docker compose up -d --build

Production-shaped: docker compose -f docker-compose.prod.yml up -d --build — see docs/OPERATIONS.md.


Features

  • Hierarchical documents - preserve section / subsection / chunk structure instead of flattening everything
  • Stable URIs - address any node with viking://documents/... (storage-independent)
  • Structure-aware ingestion - Markdown, TXT, and PDF with region-local chunking
  • Idempotent uploads - skip_identical, replace, or create_version
  • Structural navigation - parent, children, ancestors, descendants, and URI resolve
  • Hierarchical abstracts - bottom-up summaries with token budgets and idempotent reuse
  • Multi-granular embeddings - chunk content + structural summaries with explicit embedding identity
  • Semantic Search - pgvector cosine retrieval with granularity weights and URI-addressable hits
  • List / Grep / Read - structural children, scoped literal Grep, authoritative Read with provenance
  • Evidence collection - bounded Search→List/Read pipeline assembling deduplicated evidence bundles
  • Evidence sufficiency - structured assessment (sufficient / insufficient / unknown) with citation checks
  • Agentic Algorithm 1 - tool-calling Search/List/Grep/Read loop with shared budgets and finalization reserve
  • Answers API - POST /v1/answers and POST /v1/query with modes vikingrag / vikingrag_e / vikingrag_e_plus
  • Experience edges - Algorithm 2 learning jobs + Algorithm 3 Search+ expansion
  • Evaluation scaffolding - six dataset adapters + offline smoke (vikingrag-eval smoke --offline)
  • Auth - optional API-key + server document allowlist (single-tenant)
  • Shared budgets - cumulative tool/embedding/read/LLM limits across a request
  • Replaceable providers - openai / deepseek / gemini / anthropic / vllm; fakes rejected in production
  • SDK facade - VikingRAGClient for embed-in-process use without FastAPI
  • Production foundation - FastAPI, PostgreSQL + pgvector, Redis, object store, typed settings, health checks

Docs hub: docs/README.md · docs/RETRIEVAL.md · docs/PAPER_PARITY.md · AGENTS.md


Architecture

flowchart TB
    Client[Client / SDK / UI]
    API[FastAPI Gateway]

    subgraph Ingest[Ingestion]
      Parse[Parsers TXT / MD / PDF]
      Hier[Hierarchy builder]
      Chunk[Structure-aware chunker]
      Persist[(PostgreSQL + object store)]
    end

    subgraph Retrieve[Retrieval]
      Search[Search]
      List[List]
      Grep[Grep]
      Read[Read]
      Judge[Evidence sufficiency]
      Agent[Bounded agent]
    end

    Client --> API
    API --> Ingest
    API --> Retrieve
    Parse --> Hier --> Chunk --> Persist
    Search --> Persist
    List --> Persist
    Grep --> Persist
    Read --> Persist
    Judge -->|insufficient| Agent

Document model

Documents are not flat chunk lists:

flowchart TD
    D["DOCUMENT<br/>viking://documents/{id}"]
    S1[SECTION · Storage]
    S2[SECTION · Retrieval]
    S3[SECTION · Operations]
    SS1[SUBSECTION · PostgreSQL]
    SS2[SUBSECTION · Object Storage]
    SS3[SUBSECTION · Semantic Search]
    C1[CHUNK]
    C2[CHUNK]

    D --> S1
    D --> S2
    D --> S3
    S1 --> SS1
    S1 --> SS2
    S2 --> SS3
    SS1 --> C1
    SS1 --> C2

Stable URIs:

viking://documents/{document_id}
viking://documents/{document_id}/nodes/{node_id}

Ingestion pipeline

flowchart LR
    A[Upload] --> B[Hash / idempotency]
    B --> C[Parse]
    C --> D[Structure extract]
    D --> E[Normalize]
    E --> F[Hierarchy]
    F --> G[Chunk in-region]
    G --> H[Persist nodes + blob]

Layout

src/vikingrag/
  api/             FastAPI routes & schemas
  application/     Use-cases (ingest, navigation)
  domain/          Models, URIs, errors
  ingestion/       Parse → hierarchy → chunk pipeline
  infrastructure/  Postgres, Redis, object store
  providers/       LLM / embedding / rerank Protocols
  observability/   Structured logging + correlation
  settings/        Typed configuration

Quick start

After Install, check health:

curl -s http://localhost:8000/health/live  | jq
curl -s http://localhost:8000/health/ready | jq

Ingest a document, index it, and search (with .env defaults: VIKINGRAG_LLM_PROVIDER=fake, VIKINGRAG_EMBEDDING_PROVIDER=deterministic):

curl -s -X POST http://localhost:8000/v1/documents \
  -F "file=@tests/fixtures/system_architecture.md;type=text/markdown" \
  -F "strategy=skip_identical" | jq

DOC_ID="<document_id from response>"
curl -s "http://localhost:8000/v1/documents/${DOC_ID}/tree" | jq

curl -s -X POST "http://localhost:8000/v1/documents/${DOC_ID}/index" \
  -H "Content-Type: application/json" \
  -d '{"force_summaries":false,"force_embeddings":false}' | jq

curl -s -X POST http://localhost:8000/v1/search \
  -H "Content-Type: application/json" \
  -d '{"query":"How do we verify retrieved evidence?","top_k":5}' | jq

Interactive API docs: http://localhost:8000/docs


Verify before go-live

0.4.0 is an algorithm-complete milestone, not “I ran paper Tables 3–5.” Use this ladder:

# 1) Offline gates (always)
make install && make lint && make typecheck && make test
uv run vikingrag-eval smoke --offline

# 2) Integration (Postgres + Redis)
make docker-up && make migrate && make test-integration

# 3) Local API with fake/deterministic providers (wiring only)
make dev
# then ingest → index → search → POST /v1/answers (see Quick start)

# 4) Production-shaped stack with real providers + auth
#    (see docs/OPERATIONS.md — rejects fake/scripted/deterministic)
docker compose -f docker-compose.prod.yml up -d --build

Full checklist and result meanings: docs/OPERATIONS.md.

What counts as a result today

Output How Claims
Unit / lint / mypy make test etc. Code quality
Offline eval smoke JSON vikingrag-eval smoke --offline Fixture integrity only (measured_scores: null)
Integration pass make test-integration DB/migrate/API contracts
Paper accuracy/token tables Paid corpora + real LLM runs BLOCKED until you run them — never invent

SDK

Embed VikingRAG in your process (same settings / providers as the API):

from vikingrag import VikingRAGClient

client = VikingRAGClient.from_settings()
# await client.search.search(...)
# await client.answer_generator().generate(...)
# await client.aclose()

Providers via env: VIKINGRAG_LLM_PROVIDER=openai|deepseek|gemini|anthropic|vllm (and matching embeddings). Production forbids fake / deterministic / scripted.

pip install vikingrag

API

Method Path Purpose
GET /health/live Liveness
GET /health/ready Readiness (Postgres + Redis)
POST /v1/documents Multipart ingest (.md / .txt / .pdf / .docx)
GET /v1/documents/{id} Document metadata
GET /v1/documents/{id}/tree Structural tree
POST /v1/documents/{id}/index Summarize + embed (idempotent)
GET /v1/documents/{id}/index-status Index stage and counts
POST /v1/search Semantic Search (scope_uri optional)
POST /v1/retrieval/list List direct children
POST /v1/retrieval/grep Scoped Grep
POST /v1/retrieval/read Authoritative Read
POST /v1/retrieval/evidence Collect evidence + assess sufficiency
POST /v1/answers Cited answer (vikingrag / vikingrag_e / vikingrag_e_plus)
POST /v1/query Mode-switched query orchestration
GET /v1/nodes/{id} Node metadata (+ optional content)
GET /v1/uris/resolve?uri= Resolve a viking://… URI

Development

Command Purpose
make install Sync deps (uv) + pre-commit
make dev API with reload
make lint Ruff
make typecheck mypy (strict)
make test Unit tests
make test-integration Integration tests (Postgres + Redis)
make migrate Apply Alembic migrations
make docker-up / make docker-down Compose stack (volumes preserved on down)
uv run vikingrag-eval smoke --offline Offline evaluation scaffolding smoke

Citation

If you use ideas from VikingRAG or this software in research, please cite the paper:

@article{gao2026vikingrag,
  title   = {VikingRAG: Accurate and Token-efficient Retrieval-augmented
             Generation over Structured Documents},
  author  = {Gao, Peiyuan and others},
  year    = {2026},
  eprint  = {2609.11390},
  archivePrefix = {arXiv},
  primaryClass  = {cs.CL},
  url     = {https://arxiv.org/abs/2609.11390}
}

Paper: arXiv:2609.11390 · Machine-readable: CITATION.cff · Legal notices: NOTICE


License

Apache License 2.0 - see LICENSE.

VikingRAG is independently authored for production use. Do not copy code from AGPL research repositories into this tree unless you intentionally accept those obligations.


Contributing

Issues and PRs are welcome. Please:

  1. Keep layers clean (API ≠ domain ≠ adapters)
  2. Prefer typed contracts over dict[str, Any]
  3. Add tests with features
  4. Run make lint && make typecheck && make test before opening a PR

⭐ If this project helps you, starring the repo helps others find it.



LinkedIn · mhuzaifa.com · GitHub

built with curiosity   shipped with love

Metadata

Release files for vikingrag 0.4.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for vikingrag 0.4.0
File Size Uploaded
vikingrag-0.4.0.tar.gz 133.6 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for vikingrag 0.4.0
File Interpreter ABI Platform
vikingrag-0.4.0-py3-none-any.whl Python 3 none any Details

Total release size: 335.2 kB

Release files / vikingrag-0.4.0.tar.gz

Download URL vikingrag-0.4.0.tar.gz
Size 133.6 kB
Tags Source
SHA-256 checksum
How to use checksums
9037689043af954f3b9b106fa14294a4c01119c5e61289a9f175d52f023dc208
BLAKE2b-256 checksum
How to use checksums
b3938dda5244d1cc4b6c62d7eeff05797eaff194c162bf035dde8902b6ea1d8a
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.9.26 {"installer":{"name":"uv","version":"0.9.26","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release files / vikingrag-0.4.0-py3-none-any.whl

Download URL vikingrag-0.4.0-py3-none-any.whl
Size 201.6 kB
Tags Python 3
SHA-256 checksum
How to use checksums
01353f40ef14dcc93e8d01f5791d2a5c001f3bafc6d0f1ee2b93f734c55c723a
BLAKE2b-256 checksum
How to use checksums
5b414fde0930e4094b848af718bf3793df4f82460419a71417ad3452e5b1d363
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.9.26 {"installer":{"name":"uv","version":"0.9.26","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release history Release notifications | RSS feed

0.5.2

2 release files

0.5.1

2 release files

0.5.0

2 release files

0.4.4

2 release files

0.4.3

2 release files

0.4.2

2 release files

0.4.1

2 release files

This release

0.4.0 This release

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page