富客户端的数据智能实践

数据智能(data_agent_app)技术解析

页面预览:


系统托盘

首页

一、项目概述

数据智能exe可执行程序是一款基于 Tauri v2 的原生桌面应用,面向企业数据分析师和开发者,提供「自然语言驱动的数据分析」体验。用户通过对话方式与本地 PostgreSQL 数据库交互,由 AI Agent 自动生成 SQL、执行查询并智能解读结果。

核心价值主张

  • 零 SQL 门槛:用自然语言提问,AI 自动生成精准 SQL
  • 本地优先:数据库直连,数据不出本机,安全可控
  • 原生体验:系统托盘、全局快捷键、桌面通知
  • 智能增强:查询结果自动可视化 + AI 洞察总结

二、技术架构

2.1 整体架构

┌─────────────────────────────────────────────────────────┐
│                    Tauri v2 Desktop App                   │
│  ┌────────────────────┐    ┌──────────────────────────┐ │
│  │   Frontend         │    │    Rust Backend           │ │
│  │  React 18 + TS     │    │  ┌─────────────────┐     │ │
│  │  Ant Design 5      │    │  │ Database Manager │     │ │
│  │  Zustand           │    │  │ (tokio-postgres) │     │ │
│  │  Monaco Editor     │    │  └────────┬────────┘     │ │
│  │                    │    │           │               │ │
│  │  invoke("db_query")│───▶│  ┌────────▼────────┐     │ │
│  │  invoke("db_*")    │    │  │ Tauri Commands   │     │ │
│  └────────────────────┘    └──────────────────────────┘ │
└─────────────────────────────────────────────────────────┘
          │                              │
          │ HTTP/SSE                      │ TCP/PostgreSQL
          ▼                              ▼
┌─────────────────────┐    ┌──────────────────────────┐
│  QzClaw Backend      │    │  PostgreSQL               │
│  (FastAPI :8088)     │    │  (localhost:5432)        │
└─────────────────────┘    └──────────────────────────┘

2.2 技术栈

层级 技术 说明
桌面框架 Tauri v2 Rust 后端 + WebView 前端
前端框架 React 18 + TypeScript SPA 应用
UI 组件 Ant Design 5 企业级组件库
状态管理 Zustand 5 轻量级状态管理
SQL 编辑 Monaco Editor VSCode 同款编辑器
路由 react-router-dom v7 SPA 路由
数据库 tokio-postgres Rust 侧直连 PostgreSQL
AI 后端 QzClaw (QwenPaw) FastAPI 服务,端口 8088
对话协议 SSE 流式 text/event-stream

三、核心技术实现

3.1 Rust 后端:数据库连接管理

文件:[src-tauri/src/database.rs]

pub struct DatabaseManager {
    client: Arc<RwLock<Option<Client>>>,
    config: Arc<RwLock<Option<DbConfig>>>,
    status: Arc<RwLock<ConnectionStatus>>,
}

pub async fn connect(&self, config: DbConfig) -> Result<(), String> {
    let conn_str = format!(
        "host={} user={} password={} dbname={} port={}",
        config.host, config.username, config.password, 
        config.database, config.port
    );
    
    let start = std::time::Instant::now();
    match tokio_postgres::connect(&conn_str, NoTls).await {
        Ok((client, connection)) => {
            // 异步连接管理
            tokio::spawn(async move {
                if let Err(e) = connection.await {
                    log::error!("数据库连接错误: {}", e);
                }
            });
            // ...
        }
    }
}

关键技术点

  • 使用 tokio-postgres 实现异步 PostgreSQL 连接
  • RwLock 保证多线程安全
  • 连接超时控制(5秒)
  • Schema 元数据查询(information_schema

3.2 SQL 安全分级

SQL 类型 行为 示例
SELECT 自动执行,加 LIMIT 1000 SELECT * FROM users
INSERT/UPDATE/DELETE 弹窗确认 UPDATE users SET ...
CREATE/ALTER/DROP 默认拒绝 DROP TABLE users
EXPLAIN 自动执行 EXPLAIN SELECT ...

3.3 前端:SSE 流式对话

文件:[src/api/qzagent.ts]

export async function sendChatMessage(
  agentId: string,
  message: string,
  schemaContext: string | null,
  callbacks: StreamCallbacks,
  abortSignal?: AbortSignal
): Promise<void> {
  // 自动注入 Schema 上下文
  let fullMessage = message;
  if (schemaContext) {
    fullMessage = `[System Context - Database Schema]\n${schemaContext}\n\n[User Question]\n${message}`;
  }

  const response = await fetch(`${baseUrl}/api/console/chat`, {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify(body),
    signal: abortSignal,
  });

  // SSE 流式读取
  const reader = response.body?.getReader();
  const decoder = new TextDecoder();
  
  while (true) {
    const { done, value } = await reader.read();
    // 解析 message/response/content 事件
    // 提取增量文本并回调
  }
}

SSE 事件处理

  • message:累积式文本快照(主要输出)
  • response:最终总结(跳过)
  • content:AI 思考过程(过滤)

3.4 状态管理:Zustand

文件:[src/stores/chat.ts]

interface ChatStore {
  messages: ChatMessage[];
  streaming: boolean;
  currentResponse: string;
  
  // Actions
  sendMessage: (text: string) => Promise<void>;
  stopGeneration: () => void;
  clearHistory: () => void;
}

export const useChatStore = create<ChatStore>((set, get) => ({
  // 流式增量更新
  onDelta: (delta: string) => {
    set((state) => {
      // 防御:完整文本 vs 增量
      if (delta.includes(current)) {
        return { currentResponse: delta };
      }
      return { currentResponse: current + delta };
    });
  },
}));

四、Tauri invoke 命令清单

前端通过 invoke() 调用 Rust 侧命令:

命令名 参数 返回值 说明
db_connect DbConfig Result<()> 连接数据库
db_disconnect - Result<()> 断开连接
db_status - DbStatus 获取连接状态
db_list_databases - Result<Vec<String>> 列出所有数据库
db_list_tables Option<String> Result<Vec<TableInfo>> 列出表及行数
db_describe_table String Result<TableSchema> 获取表结构详情
db_query String, Option<u32> Result<QueryResult> 执行 SQL 查询
export_csv Vec<Value>, String Result<String> 导出 CSV 文件
get_schema_context Option<String> Result<String> 获取 Schema 上下文

五、关键设计亮点

5.1 Schema 上下文自动注入

当用户提问时,系统自动将数据库 Schema 拼入 Agent Prompt:

[System Context - Database Schema]
Database: mydb
Tables:
- users (id SERIAL PK, name VARCHAR(100), email VARCHAR(200), created_at TIMESTAMP)
- orders (id SERIAL PK, user_id INT FK, amount DECIMAL, status VARCHAR(20))

[User Question]
查询最近7天订单金额最高的前10个用户

5.2 流式响应去重机制

通过全局累积器 lastFullText 防止重复输出:

if (fullText === lastFullText) continue; // 跳过重复
if (fullText.startsWith(lastFullText)) {
  // 正常增量
  const delta = fullText.slice(lastFullText.length);
} else {
  // 非线性变化,发送完整新文本
}

5.3 Markdown 渲染增强

  • 安全过滤:DOMPurify XSS 防护
  • 代码高亮:rehype-highlight 语法着色
  • 主题适配:暗色/亮色模式 CSS 变量

六、项目目录结构

data_agent_app/
├── src/                          # 前端源码
│   ├── api/                      # API 客户端
│   │   ├── commands.ts           # Tauri invoke 封装
│   │   └── qzclaw.ts            # QzClaw SSE 流式对话
│   ├── components/               # 公共组件
│   │   ├── MarkdownViewer.tsx   # Markdown 渲染器
│   │   ├── SqlWorkbench.tsx     # SQL 工作台
│   │   └── FileDropZone.tsx     # 文件拖拽
│   ├── pages/                    # 页面组件
│   │   ├── AnalysisChat.tsx     # 智能对话分析
│   │   ├── DatabaseExplorer.tsx # 数据库浏览器
│   │   ├── Dashboard.tsx        # 仪表盘
│   │   └── Settings.tsx         # 设置
│   ├── stores/                   # 状态管理 (Zustand)
│   │   ├── chat.ts              # 对话状态
│   │   └── database.ts          # 数据库状态
│   └── App.tsx                   # 根组件
├── src-tauri/                    # Tauri/Rust 后端
│   ├── src/
│   │   ├── database.rs          # PostgreSQL 连接管理
│   │   ├── commands.rs          # Tauri invoke 命令
│   │   ├── tray.rs              # 系统托盘
│   │   ├── hotkey.rs            # 全局快捷键
│   │   └── main.rs              # 入口
│   └── Cargo.toml               # Rust 依赖
├── TECH_ARCHITECTURE.md          # 技术架构文档
├── PRODUCT_DESIGN.md             # 产品设计文档
└── MARKDOWN_IMPROVEMENTS.md      # Markdown 优化文档

七、总结

数据智能项目展现了 Tauri v2 在构建数据密集型桌面应用方面的优势:

  1. 性能:Rust 后端直接操作 PostgreSQL,避免网络延迟
  2. 安全:数据不出本机,SQL 分级控制
  3. 体验:原生桌面应用,流式 AI 对话
  4. 扩展:模块化的命令设计,易于扩展更多数据源

这个项目是「AI + 本地数据库 + 桌面应用」模式的优秀实践,适合作为数据分析类工具的参考架构。

©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容