Use subshells for cd to lightrag/ so user remains at repo root. Add CLAUDE.md with purpose, architecture, and known issues. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
4.0 KiB
CLAUDE.md
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
Purpose
Private learning tool. Ingest study materials → build a knowledge graph → query concepts → export flashcards to Anki.
Two systems:
- LightRAG (
lightrag/submodule) — graph-based RAG server. Ingests documents, builds a knowledge graph, answers queries. Primary interface. - Graphiti (
graphiti/submodule) — temporal knowledge graph library. Tracks when concepts were learned and how understanding evolves. Used as a Python library, not a server.
Both run fully local via Ollama. No cloud dependencies.
Running Things
Always enter via nix develop from the repo root — never activate the venv directly. The shellHook sources .env.lightrag / .env.graphiti and sets LD_LIBRARY_PATH needed for native wheels on NixOS.
# LightRAG server (API + WebUI)
nix develop .#lightrag
lightrag-server
# → http://localhost:9621/webui (React frontend)
# → http://localhost:9621/docs (Swagger API)
# Graphiti (library, no server)
nix run .#neo4j-start # required first, separate terminal
nix develop .#graphiti
# Neo4j management
nix run .#neo4j-start
nix run .#neo4j-stop
Current Models (Ollama)
| Role | Model | Dim |
|---|---|---|
| LLM | qwen3:0.6b |
— |
| Embeddings | qwen3-embedding:0.6b |
1024 |
Critical: if the embedding model or EMBEDDING_DIM changes, rag_storage/ must be deleted before restarting — old vectors are incompatible.
Configuration
.env.lightrag is sourced by the shellHook and read by lightrag-server at startup. Changes require a server restart — the server does not hot-reload env vars.
Key vars:
LLM_MODEL/EMBEDDING_MODEL— Ollama model tagsEMBEDDING_DIM— must exactly match what the embedding model outputs (verify withcurl -s http://localhost:11434/api/embed -d '{"model":"<name>","input":"test"}' | python3 -c "import sys,json; d=json.load(sys.stdin); print(len(d['embeddings'][0]))")EMBEDDING_TIMEOUT/TIMEOUT— in seconds; worker execution timeout is2× EMBEDDING_TIMEOUTRAG_DIR— resolved relative to wherelightrag-serveris invoked (insidelightrag/subdir due to shellHookcd)
Infrastructure Notes
Nix / NixOS
- Impure devShells: Nix provides Python 3.12 + uv;
uv syncinstalls PyPI deps intolightrag/.venvorgraphiti/.venvat shell entry. LD_LIBRARY_PATHis set in shellHook forlibstdc++.so.6— required for numpy and other native wheels on NixOS.UV_PYTHONis pinned to the nix-provided Python 3.12 binary to prevent uv from picking up the system Python (3.14 on this machine).- LightRAG installs with
--extra api --extra offline-llm(theollamaPython package lives inoffline-llm, notapi). - WebUI (React/Bun) is built on first shell entry if
lightrag/lightrag/api/webui/doesn't exist.
Ollama
- Configured in
~/nix-config/machines/n1n1/services/ollama.nix - Uses
pkgs.ollama-rocm(AMD ROCm) — iGPU is detected and used by default OLLAMA_NUM_GPU=0is set in NixOS config to force CPU-only mode (iGPU was consuming shared RAM)- Ollama CORS origin includes
http://127.0.0.1:8080(open-webui) andhttps://ollama.jibai.dev
LightRAG Storage
File-based by default (JsonKVStorage, NanoVectorDBStorage, NetworkXStorage). All data lives in rag_storage/ (gitignored). Safe to delete entirely to reset.
Known Issues / Active Debugging
LightRAG pipeline getting stuck: After a server restart following config changes, the pipeline shows busy: true with pending async locks but doesn't process documents. Symptoms:
GET /documents/pipeline_statusreturnsbusy: true,request_pending: truekeyed_locks.pending_async_cleanup> 0- New inserts stay at
status: pendingindefinitely POST /documents/cancel_pipelinemay be needed to unblock
The root cause is not yet determined. Suspicion: stale lock state inherited from previous failed runs persisted in rag_storage/ JSON files. Try deleting rag_storage/ and restarting the server fresh.