feat(admin-v2): add Knowledge base management page
- 4 tabs: Items (CRUD + ProTable), Categories (tree management), Search, Analytics - Knowledge service with full API integration - Nav item + breadcrumb + route registration - Analytics overview with 8 KPI statistics Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
128
admin-v2/src/services/knowledge.ts
Normal file
128
admin-v2/src/services/knowledge.ts
Normal file
@@ -0,0 +1,128 @@
|
||||
import request, { withSignal } from './request'
|
||||
|
||||
// === Types ===
|
||||
|
||||
export interface CategoryResponse {
|
||||
id: string
|
||||
name: string
|
||||
description: string | null
|
||||
parent_id: string | null
|
||||
icon: string | null
|
||||
sort_order: number
|
||||
item_count: number
|
||||
children: CategoryResponse[]
|
||||
created_at: string
|
||||
updated_at: string
|
||||
}
|
||||
|
||||
export interface KnowledgeItem {
|
||||
id: string
|
||||
category_id: string
|
||||
title: string
|
||||
content: string
|
||||
keywords: string[]
|
||||
related_questions: string[]
|
||||
priority: number
|
||||
status: string
|
||||
version: number
|
||||
source: string
|
||||
tags: string[]
|
||||
created_by: string
|
||||
created_at: string
|
||||
updated_at: string
|
||||
}
|
||||
|
||||
export interface SearchResult {
|
||||
chunk_id: string
|
||||
item_id: string
|
||||
item_title: string
|
||||
category_name: string
|
||||
content: string
|
||||
score: number
|
||||
keywords: string[]
|
||||
}
|
||||
|
||||
export interface AnalyticsOverview {
|
||||
total_items: number
|
||||
active_items: number
|
||||
total_categories: number
|
||||
weekly_new_items: number
|
||||
total_references: number
|
||||
avg_reference_per_item: number
|
||||
hit_rate: number
|
||||
injection_rate: number
|
||||
positive_feedback_rate: number
|
||||
stale_items_count: number
|
||||
}
|
||||
|
||||
export interface ListItemsResponse {
|
||||
items: KnowledgeItem[]
|
||||
total: number
|
||||
page: number
|
||||
page_size: number
|
||||
}
|
||||
|
||||
// === Service ===
|
||||
|
||||
export const knowledgeService = {
|
||||
// 分类
|
||||
listCategories: (signal?: AbortSignal) =>
|
||||
request.get<CategoryResponse[]>('/knowledge/categories', withSignal({}, signal))
|
||||
.then((r) => r.data),
|
||||
|
||||
createCategory: (data: { name: string; description?: string; parent_id?: string; icon?: string }) =>
|
||||
request.post('/knowledge/categories', data).then((r) => r.data),
|
||||
|
||||
deleteCategory: (id: string) =>
|
||||
request.delete(`/knowledge/categories/${id}`).then((r) => r.data),
|
||||
|
||||
// 条目
|
||||
listItems: (params: { page?: number; page_size?: number; category_id?: string; status?: string; keyword?: string }, signal?: AbortSignal) =>
|
||||
request.get<ListItemsResponse>('/knowledge/items', withSignal({ params }, signal))
|
||||
.then((r) => r.data),
|
||||
|
||||
getItem: (id: string, signal?: AbortSignal) =>
|
||||
request.get<KnowledgeItem>(`/knowledge/items/${id}`, withSignal({}, signal))
|
||||
.then((r) => r.data),
|
||||
|
||||
createItem: (data: {
|
||||
category_id: string
|
||||
title: string
|
||||
content: string
|
||||
keywords?: string[]
|
||||
related_questions?: string[]
|
||||
priority?: number
|
||||
tags?: string[]
|
||||
}) => request.post('/knowledge/items', data).then((r) => r.data),
|
||||
|
||||
updateItem: (id: string, data: Record<string, unknown>) =>
|
||||
request.put(`/knowledge/items/${id}`, data).then((r) => r.data),
|
||||
|
||||
deleteItem: (id: string) =>
|
||||
request.delete(`/knowledge/items/${id}`).then((r) => r.data),
|
||||
|
||||
batchCreate: (items: Array<{
|
||||
category_id: string
|
||||
title: string
|
||||
content: string
|
||||
keywords?: string[]
|
||||
tags?: string[]
|
||||
}>) => request.post('/knowledge/items/batch', items).then((r) => r.data),
|
||||
|
||||
// 搜索
|
||||
search: (data: { query: string; category_id?: string; limit?: number }) =>
|
||||
request.post<SearchResult[]>('/knowledge/search', data).then((r) => r.data),
|
||||
|
||||
// 分析
|
||||
getOverview: (signal?: AbortSignal) =>
|
||||
request.get<AnalyticsOverview>('/knowledge/analytics/overview', withSignal({}, signal))
|
||||
.then((r) => r.data),
|
||||
|
||||
getTrends: (signal?: AbortSignal) =>
|
||||
request.get('/knowledge/analytics/trends', withSignal({}, signal))
|
||||
.then((r) => r.data),
|
||||
|
||||
getTopItems: (signal?: AbortSignal) =>
|
||||
request.get('/knowledge/analytics/top-items', withSignal({}, signal))
|
||||
.then((r) => r.data),
|
||||
}
|
||||
Reference in New Issue
Block a user