feat(reins): knowledge base isolation — every base answers only for itself (CLEAN-48) - #44
Open
maksymhryzodub-prog wants to merge 11 commits into
Open
feat(reins): knowledge base isolation — every base answers only for itself (CLEAN-48)#44maksymhryzodub-prog wants to merge 11 commits into
maksymhryzodub-prog wants to merge 11 commits into
Conversation
Current-state audit of the knowledge module and the specification built on it. The audit's central finding: retrieval isolation does not exist. The workspace namespace is attached to writes only, the retrieval service binds it at process start and none is configured, so every base answers from one shared pool and the graph describes the whole installation. The product owner settled the open scope question on 2026-08-27: Ranch is personal, and an agent given one base must neither read nor inspect another. That reversed two earlier decisions -- the isolation boundary is the knowledge base rather than a container above it, and the transition needs a one-time re-index because the shared pool cannot be split after the fact. The re-index costs the operator nothing: every source type is rebuildable from Ranch's own storage. 36 requirements, 14 success criteria, 6 prioritised stories. Ready for planning, which owes an arrangement for running one retrieval process per isolated base. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01SErhdDayRqyC2hRhmFvLnf
Phase 0 research and Phase 1 design for making a knowledge base a real isolated retrieval area. The research finding that shapes the plan: an isolated instance per base is not a new capability for ranch but a second manifest builder. The platform already provisions a pod per agent through Argo, already watches those pods, and already reports free cluster slots. Sized as an agent slot (100m CPU, 512Mi, Burstable) rather than as the shared instance's 500m/1Gi, ten bases reserve 1 CPU and 5Gi -- which is what makes per-base isolation affordable after it was rejected on footprint. Alternatives are recorded with why they lost, including a custom Python service holding many LightRAG instances in one process, kept as the documented escape hatch if pod count becomes the binding constraint. Artifacts: research.md (R1-R10, no unknowns left), data-model.md, contracts/knowledge-api.md, contracts/retrieval-instance.md, quickstart.md. Three items are flagged for verification on dev, each with a fallback; the load-bearing one is whether emptyDir replaces the per-instance PVCs. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01SErhdDayRqyC2hRhmFvLnf
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…n (CLEAN-48) Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…ing (CLEAN-48) Phase 1+2 of knowledge base isolation: instance gateway mirroring the workflow slice (Argo/mock/router, manifest builder with unit spec, pinned image digest), per-base LightRAG routing with migration-aware policy, instance lifecycle on base create/delete, startup reconciliation, and the schema fields (instanceState, migrationState, per-source indexState). emptyDir sufficiency verified live; shared pool still serves all reads. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…umable migration (CLEAN-48) US1: queries answer only from the asked base's instance (no_relevant_content instead of generated answers from no context), graph endpoints become /knowledges/:id/graph[/labels] with api-side search, references resolve to Source rows via file_source ids, the agent tool attributes per base and refuses unbound ids, per-source indexState is driven from track_status, and a resumable per-base re-index moves content off the shared pool. SC-001 and SC-002 are executable Jest specs (31 tests); contract regenerated into both consoles. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…with context (CLEAN-48) US2: GET /knowledges becomes a paged envelope with search (name, description, source names) and per-item context (sourcesCount, totalSizeBytes); admin list searches server-side and pages; the agent knowledge tab edits bindings in place, marks template-inherited lists, and surfaces bindings to deleted bases instead of silently dropping them; binding pickers show what each base holds. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
… header (CLEAN-48) US3: entityTypes/relationshipTypes dropped from schema, contract and both consoles (never sent anywhere in the product's history); query tuning controls fold behind a disclosure with defaults that answer unaided, each stating what it trades; opening a base shows what it holds and whether it can answer without further navigation; graph demoted to the last tab as an inspection surface; empty states name the next action. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…ker (CLEAN-48) US4: tabs bind exactly one class set from NuxtLink's custom-slot isActive (the old two-utility conflict was decided by stylesheet order and never highlighted); /knowledges/:id lands on Sources instead of an empty body. US5: the entity picker becomes a reka-ui virtualized combobox fed by the base-scoped labels endpoint with server-side search capped at 200, and it distinguishes "no entities yet" from "no match". Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…e-source retry (CLEAN-48) US6: indexStatus is derived from source states (empty/indexing/partial/ready) instead of asserted — a base can no longer read ready while nothing is searchable; the misleading `indexed` boolean is removed from the contract; POST /knowledges/:id/sources/:sourceId/reindex retries one failed source without touching the batch; the admin sources table shows each source's own state and failure reason with a retry action, polling while processing. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…n (CLEAN-48) 46/47 tasks done; T045 (shared-pool decommission) deferred — operational, gated on every base reaching migrationState done on the live installation. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Implements CLEAN-48 — the knowledge-workspaces research outcome: a knowledge base becomes a real isolated area instead of a label on a shared pool, and the module stops needing a briefing.
reins/instancesub-slice mirroringworkflow; image pinned by digest; slot-sized requests). Query, graph and entity list are base-scoped; a migrated base never falls back to the shared pool — a down instance is a stated 503, not silently borrowed content. Empty/no-coverage bases returnanswer: null, reason: no_relevant_contentinstead of a generated answer. References resolve to Source rows (file_sourcecarries the source id). The agent tool lists only bound bases, refuses unbound ids, attributes every block, and names unreachable bases. SC-001/SC-002 are executable Jest specs.reins/migration) rebuilt entirely from Ranch's own storage — the operator supplies nothing. Reads stay on the shared pool until a base flips todone; the shared deployment remains the rollback until decommission (deliberately deferred, gated on every base migrating).entityTypes/relationshipTypesremoved from schema and contract (never sent anywhere in the product's history); retrieval tuning folded behind a disclosure with trade-off copy; the base header shows what it holds and whether it can answer.customslot (root cause: two utilities setting the same property at equal specificity);/knowledges/:idlands on Sources; the entity picker is a virtualized reka-ui combobox over the base-scoped labels endpoint with server-side search.indexStatusderived from per-source states (empty/indexing/partial/ready); the misleadingindexedboolean removed; per-source failure reasons with a single-source retry endpoint.Spec, plan, research, contracts, task list and a verification log live in
specs/007-knowledge-workspaces-research/.Test plan
tsc --noEmitclean; OpenAPI regenerated into both consoles at every breaking stepqueued→processing→indexedvia track_status → query answers with resolved reference; empty base refuses without touching retrieval; scoped label search; reindex 202; derived rollupemptyDirsufficiency proven live (both working dirs 0 bytes through ingest; query answers after restart with empty dirs)quickstart.md)migrationState: doneon the live installation🤖 Generated with Claude Code