Lattice
A workspace for your research.
Dokumente ablegen, automatisch erkennen, per Label und Ordner wiederfinden, mit Dokumenten chatten. Self-hosted.
Translation pending
ProductivityTypeScript · PythonGitHub @DocuvateOnlineOwner unconfirmed
Have you tried it? One tap is enough. No sign-in needed.
No updates detected yet. GitHub releases will appear here.
Owners of public repositories under a personal GitHub account can sign in to verify ownership and manage the introduction themselves. No administrator approval is needed.
Sign in, generate a verification file, and commit it to this repository’s default branch within 30 minutes. Files on other branches or forks do not count. Then check the file below to manage the project without administrator approval. Keep the file to retain your access.
If needed, you will go to sign-in. After signing in, return here and press your chosen verification button again.
Run /nomorevibe verify in your project folder to verify ownership and manage the introduction yourself.
Verify in one minuteAsk about other verification options
Self-hosted document intelligence: OCR, auto-labeling, search and chat over your documents, on your own hardware.
Loading the full README. The saved excerpt is shown below.
Self-hosted document intelligence: OCR, auto-labeling, search and chat over your documents, on your own hardware.
Paperless tools often stop at full-text search. Docuvate targets structured extraction (fields and layout blocks you can edit), label-first organization, and a product-grade UI, while staying self-hostable and CPU-friendly for typical deployments.
Runtime versions are pinned in .tool-versions. With asdf:
See CONTRIBUTING.md for the full development setup.
Wait until web, api, and worker are healthy (PostgreSQL 18 and Valkey healthchecks pass first).Read the full README ↗Paperless tools often stop at full-text search. Docuvate targets structured extraction (fields and layout blocks you can edit), label-first organization, and a product-grade UI, while staying self-hostable and CPU-friendly for typical deployments.
| Area | Highlights |
|---|---|
| Library | Filter, bulk actions, duplicate stacks, inbox flow |
| Document detail | Preview, OCR text, layout blocks, editable fields, labels |
| Labels | Vocabulary, suggestions from embeddings, inbox triage |
| Connectors | Plugin catalog (mail, DMS, HA, S3) with connect and import flows |
| Filesystem | Nested folders and explorer alongside labels |
| Chat | Per-document chat when a provider (for example Ollama) is configured |
| Integrations | API-first: use Docuvate headless behind your own apps (OpenAPI, ABAC) |
| Auth | Email and password via better-auth, password reset (Mailpit locally) |
Runtime versions are pinned in .tool-versions. With asdf:
asdf plugin add nodejs https://github.com/asdf-vm/asdf-nodejs.git
asdf plugin add pnpm https://github.com/jonathanmorley/asdf-pnpm.git
asdf plugin add python https://github.com/asdf-community/asdf-python.git
asdf plugin add uv https://github.com/asdf-community/asdf-uv.git
asdf install
See CONTRIBUTING.md for the full development setup.
From the repository root:
bash scripts/quickstart.sh
The script checks Docker and host RAM (minimum 6 GiB recommended for the default CPU-only stack), writes .env from .env.example with generated secrets when missing, pulls ghcr.io/docuvate/docuvate-{api,web,worker}:edge, starts Compose, waits for health, and prints the web URL.
Diagnostics after startup:
bash scripts/doctor.sh
Manual equivalent:
cp .env.example .env # set BETTER_AUTH_SECRET (≥32 chars)
docker compose pull api web worker migrate
docker compose up -d
Build from source instead of GHCR:
DOCUVATE_QUICKSTART_BUILD=1 bash scripts/quickstart.sh
# or: docker compose -f docker-compose.yml -f docker-compose.dev.yml up -d --build
Wait until web, api, and worker report healthy (PostgreSQL 18 and Valkey healthchecks pass first).
| Profile | What runs | Document chat | Host RAM (guidance) |
|---|---|---|---|
Default (docker compose up) | API, worker, Postgres, MinIO, Valkey — no Ollama | Cited extractive answers and lookups (no local LLM) | ~6 GiB stack mem_limit + OS |
chat-local | Default stack + Ollama with qwen2.5:1.5b (Q4) | Open-ended LLM answers when tenant flag localChatModel is on | ≥ 8 GiB recommended |
Optional local LLM:
docker compose --profile chat-local -f docker-compose.yml -f docker-compose.chat-local.yml up -d
Set DOCUVATE_FEATURE_LOCAL_CHAT_MODEL=true (default in docker-compose.chat-local.yml) and enable the flag per tenant via remote config / admin overrides. Without the flag, chat still works on the extractive path.
| Service | URL |
|---|---|
| Web app | http://localhost:5173 |
| API health | http://localhost:3001/health |
| API ready | http://localhost:3001/health/ready |
| OpenAPI | http://localhost:3001/v1/openapi.json |
| Mailpit (local mail) | http://localhost:8025 |
First login: open the web URL, register, open Library, upload PDFs or images, then open a document for preview and fields.
Host port overrides (see docker-compose.yml): PostgreSQL 18 on host port 5433, MinIO 9010 / console 9011. With chat-local, Ollama listens on 127.0.0.1:11434.
The optional local model defaults to qwen2.5:1.5b. Increase OLLAMA_MEM_LIMIT in .env for larger models (see .env.example).
| Component | Typical RSS |
|---|---|
Worker with ONNX int8 multilingual-e5-small + OCR/reranker headroom | ~0.9–1.2 GiB |
| API + web + Postgres + Valkey + MinIO (idle stack) | ~1.5–2.5 GiB |
Ollama with qwen2.5:1.5b (chat-local profile) | ~2 GiB (OLLAMA_MEM_LIMIT) |
Plan ≥ 6 GiB host RAM for the default stack without Ollama, or ≥ 8 GiB with chat-local. After an encoder upgrade, the API re-embeds existing documents in the background; track progress at GET /v1/settings/encoder-reindex (per signed-in tenant).
Docker Compose runs PostgreSQL 18.6 (postgres:18.6-alpine). Fresh installs use the pgdata Docker volume.
Back up your database and MinIO documents bucket before upgrading production data. Never use docker compose down -v to reset a stack: that deletes all documents and the database. See Self-hosting for volumes, upgrades, backups, and recovery.
pgdata volume (PostgreSQL 18) and the MinIO documents bucket.docker compose pull api web worker migrate (or set DOCUVATE_*_IMAGE to a release tag).docker compose up -d (migrate runs as a one-shot before API/worker).Non-core and ML features default via DOCUVATE_FEATURE_* in .env (see .env.example and ML feature flags). learnedValueTypes defaults on in 0.1.0 beta; other ML flags default off unless you enable them. Tenants can override flags in the database; the web app loads resolved values from GET /v1/remote-config after sign-in.
Local development without Docker also expects PostgreSQL 18.6 (or compatible 18.x), plus MinIO, Valkey, and the Node / Python / uv versions from .tool-versions for API, web, and worker.
Deploy Docuvate on Kubernetes with Kustomize (primary, GitOps-friendly) or an equivalent Helm chart. Overlays cover local dev (kind smoke), homelab (in-cluster Postgres 18, MinIO, Valkey), and cloud (managed Postgres and S3-compatible object storage; no in-cluster database).
| Path | Purpose |
|---|---|
| docs/deploy/kubernetes.md | Homelab, cloud, migrations, backups |
| deploy/README.md | Layout of manifests, scripts, and examples |
deploy/kustomize/overlays/* | Environment-specific manifests |
deploy/helm/docuvate | Helm chart with matching values files |
Validate rendered manifests locally (kubeconform strict, Helm/Kustomize parity):
bash tools/k8s-manifest-validate.sh
Optional end-to-end smoke on kind (local registry, migrate Job, health and OpenAPI checks):
bash tools/k8s-kind-smoke.sh
CI runs manifest validation on every workflow; kind smoke runs when deploy or image-related paths change.
flowchart TB
subgraph clients ["Clients"]
Web["Web app"]
SDK["SDKs and integrations"]
end
Web --> API["NestJS API"]
SDK --> API
API --> PG[("PostgreSQL 18")]
API --> VK[("Valkey")]
API --> S3[("MinIO")]
API --> Worker["FastAPI worker"]
Worker --> S3
API --> Ollama["Ollama optional"]
Worker --> Ollama
Clean architecture in API and worker: domain, application, infrastructure, presentation. Details in docs/architecture.md.
Use Docuvate headless behind your own apps and automations.
| Edition | What you get | License |
|---|---|---|
| Community (self-hosted) | Full core product: OCR, labels, search, chat, connectors, API | Sustainable Use License 1.0 — free private and internal business use on your infrastructure |
| Enterprise + Cloud | Business features, vendor-hosted SaaS, support — separate product built on CE (docuvate.de) | Commercial license (not in this repository) |
Docuvate is source-available / fair-code, not OSI “open source”. Official SDKs (packages/sdk-node, packages/sdk-flutter) are MIT.
Commercial builds extend CE via optional Nest extension modules (DOCUVATE_EXTENSION_MODULES / DOCUVATE_EXTENSION_PATH in ExtensionHostModule); this repository does not ship those modules.
These items are not promised timelines; they track known gaps and stubs on main:
See CONTRIBUTING.md, CODE_OF_CONDUCT.md, and SECURITY.md. Before opening a pull request, run the same jobs as .github/workflows/ci.yml locally (see docs/local-ci.md).
Report vulnerabilities privately: SECURITY.md.
Community Edition: LICENSE (Sustainable Use License 1.0). Enterprise and Cloud are offered separately under commercial terms (docuvate.de). SDKs: MIT. Name and branding policy: TRADEMARKS.md.