# miniagent **Repository Path**: liupras/miniagent ## Basic Information - **Project Name**: miniagent - **Description**: 迷你智能体 - **Primary Language**: Python - **License**: Apache-2.0 - **Default Branch**: master - **Homepage**: http://wfcoding.com - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2026-02-05 - **Last Updated**: 2026-06-19 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # MiniAgent - admin lightweight agent platform **MiniAgent** is a lightweight agent platform (Chinese/English) for individuals and small teams. The backend is a FastAPI app that manages agents, knowledge bases, tools, LLM configs, auth/RBAC, and runtime features (RAG retrieval, SQL agent, web search). The frontend lives in management/ (vue-pure-admin). ## High-level architecture ~~~mermaid flowchart TB subgraph HTTP API["app/api/*"] end subgraph Core SC["ServiceContainer
app/core/service_container.py"] CFG["Settings
app/core/config.py"] end subgraph Runtime AF["AgentFactory"] AR["AgentRunner
LangChain"] TB["ToolBuilder"] end subgraph KB DOC["KBDocumentService"] RET["KBRetrievalService"] SR["KBSmartRouterService"] VS["VectorStore + BM25"] end subgraph Data REPO["repositories/async_*"] SQLITE[(SQLite)] CHROMA[(ChromaDB)] DUCK[(DuckDB)] end API --> SC SC --> AF --> AR AF --> TB SC --> DOC & RET & SR RET --> VS REPO --> SQLITE VS --> CHROMA SC --> DUCK ~~~ **Layering convention** (follow this when adding features): - app/api/ — HTTP only: routing, request/response models, Depends() wiring - app/services/ — Business logic - app/repositories/ — Async DB access (Async*Database classes) - app/schemas/ — Pydantic request/response DTOs - app/infra/ — DB models, LLM helpers, prompts, cache API responses usually use the envelope in app/schemas/common.py: ~~~python ApiResponse(data=...) # { code: 200, message: "success", data: ... } ~~~ ## Startup sequence ~~~python @asynccontextmanager async def lifespan(app: FastAPI) -> AsyncGenerator: # ... init_database_on_startup(force_rebuild=False, seed_data=True) # ... app.state.container = ServiceContainer() await app.state.container.start() ~~~ **On boot**: - DB init — app/infra/db/initializer.py creates SQLite tables and loads seed JSON from app/infra/db/seed/ - ServiceContainer — builds async SQLAlchemy engine, all repositories, and long-lived services - Domain plugins — loads Domain rows from DB and registers KB processors via dynamic import Everything shared lives on request.app.state.container. Routes get it via Depends(get_container). ## Main entry points ### 1. Application root — `app/main.py` CORS, request logging, global exception handler Registers all API routers under /api/v1/... Ops routes: /, /health, /config (debug), /db/info ### 2. Configuration — `app/core/config.py` Pydantic Settings from .env: SQLite/DuckDB/Chroma paths, JWT, CORS, log level, token limits. Required: JWT_SECRET_KEY (no default in code). ### 3. Dependency hub — `app/core/service_container.py` ### 4. Data models — `app/infra/db/database.py` SQLAlchemy ORM for users, roles, menus, agents, tools, LLMs, embeddings, knowledge bases, documents/chunks, chat sessions, router configs, domains, etc. ## Knowledge base pipeline ~~~text Upload → DomainPlugin (general / law_cn) → chunk → embed → Chroma + BM25 Query → RetrievalPipeline (vector + BM25 + RRF + optional reranker) Multi-KB → SmartRouter (router config from DB) ~~~ Domains are configured in seed data and registered at startup: ~~~text "processor_class":"app.services.kb.SmallToBigProcessor", "plugin_class":"app.services.kb.GeneralDomainPlugin", ~~~ ## Other skills - SQL Agent — app/services/sql_agent/: DuckDB manager, sandboxed execution, schema context - Web Search — app/services/skill/: search service + LangChain tool wrapper - Storage — app/storage/: local file backend for uploaded documents ## What to read before changing things 1. app/main.py — router map and lifecycle 2. app/core/service_container.py — where to register new services 3. app/infra/db/database.py — schema 4. app/schemas/common.py — API response shape ## Caching rules (easy to break) Several layers cache compiled objects in-process: - AgentFactory — per agent_id - VectorStoreRegistry — per kb_id - SmartRouterFactory — per router_config_id - KBRetrievalService — per (kb_id, config_id) After DB updates, call the matching invalidate() or users see stale config. Admin services often do this already — follow that pattern.