hgaol commented on issue #1468:
URL: https://github.com/apache/answer/issues/1468#issuecomment-3723067855

   **Share arch design below for better discussion.**
   
   
   ## Overview
   
   The Copilot Chat plugin provides an AI-powered chat assistant with RAG 
(Retrieval-Augmented Generation) capabilities for Apache Answer. It integrates 
with LLM providers for chat and embeddings, with support for multiple vector 
store backends.
   
   ### Current Support
   
   | Component | Supported Options |
   |-----------|-------------------|
   | **LLM Provider** | Azure OpenAI (gpt-4, gpt-4o, etc.) |
   | **Embedding Provider** | Uses selected LLM provider's embedding API (Azure 
OpenAI: text-embedding-ada-002, text-embedding-3-small, etc.) |
   | **Vector Store** | In-Memory, Qdrant |
   
   > **Note:** Currently, the embedding provider is automatically set to match 
the LLM provider. Provider-specific embedding settings are shown based on the 
selected LLM provider.
   
   ### Future Extensibility
   
   The architecture is designed to be extensible. Future versions could support:
   - **Additional LLM Providers**: OpenAI (direct), Anthropic Claude, Google 
Gemini, local models (Ollama)
   - **Additional Embedding Providers**: OpenAI, Cohere, HuggingFace, local 
embeddings
   - **Additional Vector Stores**: Pinecone, Weaviate, Milvus, PostgreSQL 
(pgvector), Chroma
   
   ## Plugin Structure
   
   ```
   copilot-chat/
   ├── copilot_chat.go      # Backend: Go plugin implementation
   ├── Component.tsx        # Frontend: React chat UI component
   ├── index.ts             # Frontend: Plugin entry point
   ├── info.yaml            # Plugin metadata (slug_name: copilot_chat, type: 
agent)
   ├── go.mod / go.sum      # Go dependencies
   ├── package.json         # Frontend dependencies
   ├── i18n/                # Internationalization
   │   ├── en_US.yaml
   │   ├── zh_CN.yaml
   │   ├── index.ts
   │   └── translation.go
   └── vite.config.ts       # Frontend build config
   ```
   
   ## Architecture Diagram
   
   ```
   ┌─────────────────────────────────────────────────────────────────────┐
   │                         Apache Answer Core                          │
   ├─────────────────────────────────────────────────────────────────────┤
   │  plugin_common_service.go                                           │
   │  ┌─────────────────────────────────────────────────────────────┐   │
   │  │ UpdatePluginConfig()                                         │   │
   │  │   - Detects copilot_chat plugin                              │   │
   │  │   - Calls agent.SetSyncer(SearchSyncer) for RAG access       │   │
   │  └─────────────────────────────────────────────────────────────┘   │
   │                              │                                      │
   │                              ▼                                      │
   │  ┌─────────────────────────────────────────────────────────────┐   │
   │  │ search_sync.go → NewPluginSyncer()                           │   │
   │  │   - GetQuestionsPage()                                       │   │
   │  │   - GetAnswersPage()                                         │   │
   │  └─────────────────────────────────────────────────────────────┘   │
   └─────────────────────────────────────────────────────────────────────┘
                                  │
                                  ▼
   ┌─────────────────────────────────────────────────────────────────────┐
   │                      copilot-chat Plugin                            │
   ├─────────────────────────────────────────────────────────────────────┤
   │  Backend (copilot_chat.go)                                          │
   │  ┌─────────────────────────────────────────────────────────────┐   │
   │  │ CopilotChatPlugin implements plugin.Agent                    │   │
   │  │   - ConfigFields() / ConfigReceiver()                        │   │
   │  │   - RegisterAuthUserRouter() → /copilot-chat/chat (SSE)      │   │
   │  │   - SetSyncer(SearchSyncer)                                  │   │
   │  │   - UpdateEmbeddings() (cron job)                            │   │
   │  │   - SimilaritySearch()                                       │   │
   │  └─────────────────────────────────────────────────────────────┘   │
   │                                                                     │
   │  Vector Stores                                                      │
   │  ┌──────────────────────┐  ┌──────────────────────┐                │
   │  │ MemoryVectorStore    │  │ QdrantVectorStore    │                │
   │  │ (in-memory, dev)     │  │ (persistent, prod)   │                │
   │  └──────────────────────┘  └──────────────────────┘                │
   │                                                                     │
   │  External Services                                                  │
   │  ┌──────────────────────┐  ┌──────────────────────┐                │
   │  │ Azure OpenAI (LLM)   │  │ Azure OpenAI (Embed) │                │
   │  │ - gpt-4              │  │ - text-embedding-*   │                │
   │  └──────────────────────┘  └──────────────────────┘                │
   ├─────────────────────────────────────────────────────────────────────┤
   │  Frontend (Component.tsx)                                           │
   │  ┌─────────────────────────────────────────────────────────────┐   │
   │  │ - Floating/Docked chat panel                                 │   │
   │  │ - Markdown rendering (marked.js)                             │   │
   │  │ - Chat history persistence (localStorage)                    │   │
   │  │ - Reference links display                                    │   │
   │  └─────────────────────────────────────────────────────────────┘   │
   └─────────────────────────────────────────────────────────────────────┘
   ```
   
   ## Key Components
   
   ### Backend (Go)
   
   | Component | Description |
   |-----------|-------------|
   | `CopilotChatPlugin` | Main plugin struct implementing `plugin.Agent` 
interface |
   | `SetSyncer()` | Receives `SearchSyncer` from Answer core for Q&A data 
access |
   | `UpdateEmbeddings()` | Fetches all Q&A content and creates vector 
embeddings |
   | `SimilaritySearch()` | Searches vector store for relevant context |
   | `handleChat()` | POST endpoint returning full JSON response |
   | `MemoryVectorStore` | In-memory vector store (no external deps) |
   | `QdrantVectorStoreWrapper` | Qdrant integration with deduplication |
   
   ### Frontend (React/TypeScript)
   
   | Component | Description |
   |-----------|-------------|
   | `Component.tsx` | Main chat UI with floating/docked modes |
   | `localStorage` | Persists chat history, panel state, width |
   
   ## Changes Required in Answer Core
   
   The following changes are needed in the `apache/answer` repository:
   
   ### 1. Plugin Service Integration
   
   **File:** `internal/service/plugin_common/plugin_common_service.go`
   
   When a plugin config is saved, automatically detect any Agent plugin that 
implements `SetSyncer(plugin.SearchSyncer)` and inject the syncer. This allows 
Agent plugins to access Q&A content for RAG without hardcoding plugin names.
   
   ### 2. Plugin Config Field Dependencies (DependsOn/ShowWhen)
   
   Support for conditional field visibility based on other field values.
   
   **Files:**
   - `plugin/config.go` - Add `DependsOn` and `ShowWhen` fields to 
`ConfigFieldUIOptions` struct
   - `internal/schema/plugin_admin_schema.go` - Add same fields to schema for 
API response
   - `ui/src/pages/Admin/Plugins/Config/index.tsx` - Frontend logic to:
     - Read `depends_on` and `show_when` from backend config
     - Apply visibility rules when form values change
     - Hide fields when parent field value doesn't match `show_when` values
   
   
   ## Configuration Options
   
   ### LLM Provider Selection
   
   | Option | Description |
   |--------|-------------|
   | `llm_provider` | LLM provider to use (currently: Azure OpenAI) |
   
   ### Azure OpenAI Settings
   *Shown when `llm_provider` = azure_openai*
   
   | Option | Description | Depends On |
   |--------|-------------|------------|
   | `azure_endpoint` | Azure OpenAI endpoint URL | `llm_provider` = 
azure_openai |
   | `azure_api_key` | Azure OpenAI API key | `llm_provider` = azure_openai |
   | `azure_deployment` | LLM deployment name (e.g., gpt-4) | `llm_provider` = 
azure_openai |
   | `azure_api_version` | API version (e.g., 2024-02-15-preview) | 
`llm_provider` = azure_openai |
   
   ### Chat Settings
   
   | Option | Description |
   |--------|-------------|
   | `system_prompt` | Custom system prompt |
   | `max_tokens` | Max response tokens |
   | `temperature` | Response randomness (0.0-1.0) |
   | `require_login` | Require user login to access chat |
   | `enable_rag` | Enable RAG with Q&A context |
   
   ### RAG Settings
   *Shown when `enable_rag` = true*
   
   | Option | Description | Depends On |
   |--------|-------------|------------|
   | `chunk_level` | `item` (per answer) or `question` (full thread) | 
`enable_rag` = true |
   | `top_k` | Number of context documents | `enable_rag` = true |
   | `similarity_threshold` | Min similarity score (0.0-1.0) | `enable_rag` = 
true |
   | `embedding_cron` | Cron schedule for embedding updates | `enable_rag` = 
true |
   | `vector_store_type` | `memory` or `qdrant` | `enable_rag` = true |
   
   ### Embedding Provider Settings
   
   > **Note:** Currently, the embedding provider uses the same provider as the 
LLM. The embedding deployment config is shown when RAG is enabled. Future 
versions may support independent embedding provider selection.
   
   #### Azure OpenAI Embedding
   *Shown when `enable_rag` = true*
   
   | Option | Description | Depends On |
   |--------|-------------|------------|
   | `azure_embedding_deployment` | Embedding model deployment (e.g., 
text-embedding-ada-002) | `enable_rag` = true |
   
   ### Qdrant Settings
   *Shown when `vector_store_type` = qdrant*
   
   | Option | Description | Depends On |
   |--------|-------------|------------|
   | `qdrant_url` | Qdrant server URL | `vector_store_type` = qdrant |
   | `qdrant_api_key` | Qdrant API key (optional) | `vector_store_type` = 
qdrant |
   | `qdrant_collection_name` | Qdrant collection name | `vector_store_type` = 
qdrant |
   
   ## API Endpoints
   
   | Method | Endpoint | Auth | Description |
   |--------|----------|------|-------------|
   | POST | `/answer/api/v1/copilot-chat/chat` | User | Chat (JSON response) |
   | GET | `/answer/api/v1/copilot-chat/status` | Admin | Plugin status |
   | POST | `/answer/api/v1/copilot-chat/embeddings/update` | Admin | Trigger 
embedding update |
   | GET | `/answer/api/v1/copilot-chat/embeddings/status` | Admin | Embedding 
status |
   
   ## Data Flow (RAG)
   
   1. **Embedding Phase** (cron or manual trigger):
      - Plugin calls `syncer.GetQuestionsPage()` / `syncer.GetAnswersPage()`
      - Content is chunked based on `chunk_level` setting
      - Azure OpenAI creates embeddings
      - Embeddings stored in vector store
   
   2. **Query Phase**:
      - User sends POST request with message
      - Plugin performs similarity search
      - Top-K relevant documents retrieved
      - Context + user message sent to Azure OpenAI LLM
      - Full JSON response returned to frontend


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to