Files
cutThink_lite/docs/PHASE5_INTEGRATION.md

478 lines
10 KiB
Markdown
Raw Permalink Normal View History

# Phase 5 - AI 分类系统集成指南
本文档说明如何将 Phase 5 实现的 AI 分类功能集成到主应用中。
## 1. 主应用集成 (App.svelte 或主要入口)
### 1.1 导入组件和 Store
```svelte
<script>
import { onMount } from 'svelte';
import { initializeAiStore } from './store/ai';
import AiConfigView from './components/views/AiConfigView.svelte';
import AiTemplatesView from './components/views/AiTemplatesView.svelte';
// 状态
let showAiConfig = false;
let showAiTemplates = false;
onMount(() => {
// 初始化 AI store
initializeAiStore();
});
</script>
```
### 1.2 添加菜单项
在主界面菜单中添加:
```svelte
<nav>
<!-- 现有菜单项 -->
<button on:click={() => showAiConfig = true}>
⚙️ AI 配置
</button>
<button on:click={() => showAiTemplates = true}>
📝 模板管理
</button>
</nav>
<!-- Modals -->
{#if showAiConfig}
<AiConfigView onClose={() => showAiConfig = false} />
{/if}
{#if showAiTemplates}
<AiTemplatesView onClose={() => showAiTemplates = false} />
{/if}
```
## 2. 记录详情页面集成
### 2.1 在记录详情中添加分类功能
```svelte
<script>
import AutoClassifyView from './components/views/AutoClassifyView.svelte';
import { getClassification } from './api/ai';
export let record; // 从父组件传入的记录
let classification = null;
let showClassify = false;
// 加载已保存的分类
async function loadClassification() {
if (record?.id) {
classification = await getClassification(record.id);
}
}
$: if (record?.id) {
loadClassification();
}
</script>
<div class="record-detail">
<!-- 现有内容 -->
<!-- 分类按钮 -->
<button on:click={() => showClassify = !showClassify}>
{showClassify ? '隐藏' : '显示'} AI 分类
</button>
<!-- AI 分类组件 -->
{#if showClassify}
<AutoClassifyView
recordId={record.id}
content={record.content}
ocrText={record.metadata?.ocr_text}
onClassified={(result) => {
console.log('分类结果:', result);
loadClassification();
}}
/>
{/if}
<!-- 显示已保存的分类 -->
{#if classification}
<div class="classification-info">
<h4>分类信息</h4>
<p>分类: {classification.category}</p>
{#if classification.subcategory}
<p>子分类: {classification.subcategory}</p>
{/if}
<p>置信度: {Math.round(classification.confidence * 100)}%</p>
</div>
{/if}
</div>
```
## 3. 全局快捷键集成
### 3.1 添加快捷键
在主应用中添加快捷键:
```svelte
<script>
import { onMount, onDestroy } from 'svelte';
let handleKeyDown = (e) => {
// Ctrl/Cmd + K: 快速分类
if ((e.ctrlKey || e.metaKey) && e.key === 'k') {
e.preventDefault();
// 触发当前选中记录的分类
triggerClassification();
}
// Ctrl/Cmd + Shift + A: 打开 AI 配置
if ((e.ctrlKey || e.metaKey) && e.shiftKey && e.key === 'A') {
e.preventDefault();
showAiConfig = true;
}
};
onMount(() => {
window.addEventListener('keydown', handleKeyDown);
});
onDestroy(() => {
window.removeEventListener('keydown', handleKeyDown);
});
</script>
```
## 4. 自动分类触发
### 4.1 截图后自动分类
在截图完成后触发分类:
```svelte
<script>
import { classification } from './store/ai';
async function handleScreenshot(screenshot) {
// 保存记录
const record = await saveRecord(screenshot);
// 如果 AI 已配置,自动分类
if ($aiConfig.configured && autoClassifyEnabled) {
const variables = {
content_type: 'image',
image_path: screenshot.file_path,
};
// 如果有 OCR 结果,添加到变量
if (screenshot.ocr_text) {
variables.ocr_text = screenshot.ocr_text;
}
try {
await classification.classify(
record.id,
'general', // 使用通用模板
variables,
true // 流式模式
);
} catch (error) {
console.error('自动分类失败:', error);
}
}
return record;
}
</script>
```
### 4.2 剪贴板监听自动分类
```svelte
<script>
import { watchClipboard } from './utils/clipboard';
async function handleClipboardChange(content) {
// 保存记录
const record = await saveRecord({
type: 'text',
content: content,
});
// 自动分类
if ($aiConfig.configured && autoClassifyEnabled) {
await classification.classify(
record.id,
'general',
{
content_type: 'text',
content: content,
},
false // 非流式
);
}
}
onMount(() => {
watchClipboard(handleClipboardChange);
});
</script>
```
## 5. 配置持久化
### 5.1 保存用户偏好
```typescript
// 在 store/settings.ts 中添加
export const autoClassifyEnabled = writable(false);
export const defaultTemplateId = writable('general');
export const minConfidence = writable(0.7);
// 加载设置
export async function loadAiSettings() {
const enabled = await getSetting('auto_classify_enabled');
if (enabled !== null) {
autoClassifyEnabled.set(enabled === 'true');
}
const template = await getSetting('default_template_id');
if (template) {
defaultTemplateId.set(template);
}
const confidence = await getSetting('min_confidence');
if (confidence) {
minConfidence.set(parseFloat(confidence));
}
}
// 保存设置
export async function saveAiSettings() {
await setSetting('auto_classify_enabled', String($autoClassifyEnabled));
await setSetting('default_template_id', $defaultTemplateId);
await setSetting('min_confidence', String($minConfidence));
}
```
## 6. 通知和反馈
### 6.1 分类完成通知
```svelte
<script>
import { notification } from './store/notification';
function handleClassificationComplete(result) {
notification.show({
type: 'success',
title: '分类完成',
message: `已分类为: ${result.category}`,
duration: 3000,
});
}
function handleClassificationError(error) {
notification.show({
type: 'error',
title: '分类失败',
message: error,
duration: 5000,
});
}
</script>
```
## 7. 分类统计显示
### 7.1 在侧边栏显示统计
```svelte
<script>
import { getClassificationStats } from './api/ai';
let categoryStats = [];
async function loadStats() {
categoryStats = await getClassificationStats();
}
onMount(() => {
loadStats();
// 定期更新
const interval = setInterval(loadStats, 60000);
return () => clearInterval(interval);
});
</script>
<aside>
<h3>分类统计</h3>
<ul>
{#each categoryStats as [category, count]}
<li>{category}: {count}</li>
{/each}
</ul>
</aside>
```
## 8. 完整集成示例
### 主应用结构
```svelte
<!-- App.svelte -->
<script>
import { onMount } from 'svelte';
import { initializeAiStore, aiConfig } from './store/ai';
import AiConfigView from './components/views/AiConfigView.svelte';
import AiTemplatesView from './components/views/AiTemplatesView.svelte';
import RecordList from './components/RecordList.svelte';
let showAiConfig = false;
let showAiTemplates = false;
onMount(() => {
initializeAiStore();
});
</script>
<div class="app">
<!-- 侧边栏 -->
<aside>
<nav>
<a href="#records">📋 记录</a>
<a href="#screenshots">📸 截图</a>
<button on:click={() => showAiConfig = true}>
⚙️ AI 配置
</button>
<button on:click={() => showAiTemplates = true}>
📝 模板管理
</button>
</nav>
<!-- AI 状态指示器 -->
<div class="ai-status" class:configured={$aiConfig.configured}>
{$aiConfig.configured ? '✅ AI 已启用' : '⚠️ AI 未配置'}
</div>
</aside>
<!-- 主内容 -->
<main>
<RecordList />
</main>
</div>
<!-- Modals -->
{#if showAiConfig}
<AiConfigView onClose={() => showAiConfig = false} />
{/if}
{#if showAiTemplates}
<AiTemplatesView onClose={() => showAiTemplates = false} />
{/if}
<style>
.ai-status {
padding: 10px;
margin-top: 20px;
border-radius: 6px;
text-align: center;
background: #f39c12;
color: white;
}
.ai-status.configured {
background: #27ae60;
}
</style>
```
## 9. 测试检查清单
在集成完成后,进行以下测试:
### 功能测试
- [ ] AI 配置界面可以打开
- [ ] Claude API Key 可以保存
- [ ] OpenAI API Key 可以保存
- [ ] 模板列表可以正常显示
- [ ] 可以创建新模板
- [ ] 可以编辑现有模板
- [ ] 可以删除自定义模板
- [ ] 可以测试模板渲染
- [ ] 可以导出模板
- [ ] 可以导入模板
- [ ] 分类功能正常工作
- [ ] 流式分类实时显示
- [ ] 分类结果正确保存
- [ ] 分类历史可以查看
- [ ] 分类统计正确显示
### 集成测试
- [ ] 截图后自动触发分类
- [ ] 剪贴板监听自动分类
- [ ] 快捷键正常工作
- [ ] 通知正确显示
- [ ] 错误正确处理
### 性能测试
- [ ] 大文本分类正常
- [ ] 批量分类不卡顿
- [ ] API 限流正常工作
- [ ] 内存占用合理
## 10. 故障排查
### 问题 1: AI 配置保存失败
**检查:**
- 数据库连接正常
- API Key 格式正确
- 网络连接正常
### 问题 2: 分类失败
**检查:**
- AI 提供商已配置
- API Key 有效
- 模板存在且有效
- 变量值正确
### 问题 3: 流式响应不显示
**检查:**
- 事件监听器正确设置
- 窗口对象正确传递
- Tauri 事件系统正常
## 11. 下一步
集成完成后,可以考虑以下增强:
1. **自动化工作流**
- 基于分类自动打标签
- 基于分类自动归档
- 基于分类触发通知
2. **高级功能**
- 批量分类
- 定时分类任务
- 分类规则引擎
3. **用户体验**
- 分类建议
- 快速操作
- 可视化统计
4. **性能优化**
- 结果缓存
- 请求队列
- 批处理
---
如有问题,请参考:
- [Phase 5 实现总结](./PHASE5_SUMMARY.md)
- [API 文档](../src/api/ai.ts)
- [Store 文档](../src/store/ai.ts)