Skip to content

saltFishCode/Ruici-AI-Platform

Repository files navigation

Ruici-AI-Platform

泛职业文档分析 + 多场景情景模拟平台,基于大语言模型、知识库与实时语音能力构建。

Java Spring Boot Spring AI React PostgreSQL


项目定位

Ruici-AI-Platform 是一个面向多职业者的真实业务场景的 AI 平台。

项目当前的核心方向是:

  • 泛职业文档分析:进行各种职业者的文档理解、结构提取、评估建议、报告导出。
  • 多情景情景模拟:进行情景模拟, AI 充当模拟对象, 根据文档信息与方向对职业者进行拷打。
  • 知识库驱动能力编排:通过知识库、提示词模板和 Skill 组合出不同垂类能力。

默认三个情景模拟方向是:

  1. 求职面试:面试官角度,围绕相关岗位的准备、模拟问答、文档评估、语音面试展开。
  2. 专业答疑:提问者角度,围绕相关专业的文档分析、专业问答和场景化解释展开。
  3. 职业沟通表达:职场同事/高层角度,围绕汇报、邮件、会议发言、跨部门协作与反馈沟通,进行话术优化、场景演练和表达评估。

AI Provider 策略

项目采用 多 Provider 架构,但默认策略已经切换为“自定义 OpenAI-compatible 中转优先”。

v1.3.x 当前阶段说明

v1.3.0 开始,聊天链路已经接入 运行时动态配置基础能力,目标是把 Provider / Model / Fallback Model 的决策,从"各业务模块自行读取静态配置"收敛为 "统一 resolver 解析 + Registry 缓存 + 模块按快照消费"。

当前阶段的边界非常明确:

  • 已接入动态解析:chat 相关链路(document / simulation / knowledgebase
  • embedding 已接入:任务级 / 查询级快照,用于知识库向量化与检索链路
  • voice 已接入:会话级 LLM / ASR / TTS 快照,用于实时对话与异步评估链路
  • 优先级统一:请求级覆盖(允许时)→ 数据库运行时配置 → 静态环境配置 → code default
  • 缓存按模型区分LlmProviderRegistry 不再只按 provider 缓存,而是按 provider + clientType
    • model + fallback + baseUrl + configVersion 组合缓存,避免模型切换后复用旧 client
  • last-known-good 兜底:chat resolver 内部保留最近一次可用快照,用于数据库配置失效或异常场景的 稳定回退
  • 多实例缓存失效:通过 Redis Topic 广播,支持单 key 和全量刷新

这意味着:当前默认聊天 Provider 仍然可以是 third-party,但具体聊天链路最终使用哪个 model / fallback model,已经不再建议由业务模块自己拼接判断,而应统一走运行时解析。

默认路由

  • 主聊天 / 通用推理 / 情景模拟:默认走第三方 OpenAI-compatible 中转
    • Base URL: https://api-s.zwenooo.link/v1
    • Model: gpt-5.2
  • 向量化 / Embedding:默认保留 Qwen / DashScope
  • 语音 ASR / TTS / Realtime:继续保留 Qwen / DashScope

为什么这样设计

  • 第三方 OpenAI-compatible 中转更适合作为统一聊天入口,方便切换模型和成本控制。
  • 向量化与实时语音的兼容性、稳定性和能力覆盖目前仍以 Qwen / DashScope 更稳妥。
  • “OpenAI-compatible” 不是“完全等价 OpenAI”,不同中转在 /chat/completions、流式事件、工具调用、结构化输出上可能存在差异,因此需要把聊天和语音/向量能力分层配置,而不是强行共用一个 Provider。
  • v1.3.x 先把 chat 做成统一运行时控制面,是为了先稳定最常用、最容易频繁切换模型的链路; embedding 已进一步按任务级 / 查询级快照接入知识库向量化与检索,避免 chunk 级频繁查库; voice 已按会话级快照接入 LLM / ASR / TTS 三类配置,WebSocket 实时链路真正消费快照。

ChatClient 语义边界

  • default client:带 SkillsTool 与 advisors(受配置开关影响),用于需要保留增强能力的常规聊天链路。
  • plain client:不带 tools / advisors,用于简历题生成、解析等不希望发生工具调用的链路。
  • voice client:当前实现同样是 plain/no-tools,目的是避免实时语音链路因 tool calling 增加首包时延或流式不稳定。
  • knowledgebase 的 OpenAI-compatible gateway 分支会直接调用 gateway client,不经过 ChatClient 挂载的 tools / advisors;因此“默认 client 具备增强能力”并不等于所有 RAG 请求都一定经过增强链。

技术栈

后端

技术 版本 说明
Spring Boot 4.0.1 应用框架
Java 21 开发语言,启用虚拟线程
Spring AI 2.0.0-M4 OpenAI-compatible 集成与向量能力
PostgreSQL + pgvector 16+ 关系数据库与向量检索
Redis + Redisson 6.2.14 / 4.0.0 缓存、限流、Redis Stream
Apache Tika 2.9.2 文档解析
iText 8 8.0.5 PDF 导出
MapStruct 1.6.3 对象映射
DashScope SDK 2.22.7 Qwen 实时语音 ASR/TTS
Maven 3.8.8+ 构建工具

前端

React 18 + TypeScript + Vite + TailwindCSS 4,位于 frontend/ 目录。

当前能力地图

1. 文档分析

  • 支持 PDF、DOCX、DOC、TXT、Markdown、HTML 等多格式输入。
  • 支持内容清洗、结构抽取、评估建议、异步处理和 PDF 报告导出。
  • 支持前端直连对象存储的原文件预览(PDF/图片/DOCX/Markdown/HTML)。
  • 当前代码中仍有部分 resume 命名残留,但业务语义已经按"通用职业文档"理解。

2. 情景模拟

  • 支持基于 Skill 的题目/话术生成、多轮追问、评估与报告导出。
  • 当前默认能力仍以求职面试为主,但平台目标是承载更多场景模板。
  • 三个默认专项可通过内置的 知识库 + prompts + skills 继续扩展。

3. 知识库问答

  • 支持文档上传、切分、向量化、检索增强生成(RAG)和流式回答。
  • 适合作为中医药答疑、小说知识库、岗位知识库等垂类能力底座。

4. 语音交互

  • 语音能力继续使用 Qwen / DashScope 实时链路。
  • 适合面试模拟、口语问答、角色扮演等低延迟场景。

业务结构说明

从产品语义上,Ruici 的业务结构应该理解为:

平台语义 当前代码承载
document 文档分析 modules/document
simulation 情景模拟 modules/simulation
knowledgebase 知识库 modules/knowledgebase
schedule 日程场景 modules/schedule
voice 语音交互 modules/voice

部分配置键、数据库字段和兼容命名仍然带有旧项目色彩,这是当前重构过程中的兼容层,不代表最终产品语义。

前后端对接时,建议直接查看 api/ 目录下的模块接口说明,而不是只根据类名猜测语义。

运行时 AI 配置(v1.3.x)

v1.3.0 新增的不是“更多 Controller 接口”,而是后端内部的 AI 运行时控制面基础层。当前代码里, 这部分主要位于:

src/main/java/com/ruici/ai/common/config/runtime/
   model/         枚举(Domain / Scene / Source)
   snapshot/      快照与解析上下文(Snapshot / ResolveContext)
   entity/        JPA 实体(Config / Audit)
   repository/    JPA 仓库
   resolver/      解析器接口与实现(Resolver + DefaultResolver)
   policy/        策略校验(PolicyService + ValidationService)
   service/       管理服务(CommandService / QueryService)
   controller/    REST 端点(/api/ai-runtime-config)
   dto/           数据传输对象

其中关键职责可以这样理解:

  • AiRuntimeConfigEntity / AiRuntimeConfigRepository:承载数据库中的非敏感运行时控制信息 (如 scene / domain / provider / model / fallback model / priority / version)
  • AiRuntimePolicyService:约束当前允许的覆盖范围与快照合法性
  • AiRuntimeConfigResolver:把请求级覆盖、数据库配置、静态配置、兜底策略收敛为单一快照
  • AiRuntimeConfigSnapshot:把一次调用真正使用的 provider/model/fallback/version/source 固化下来
  • LlmProviderRegistry:根据快照创建并缓存 ChatClient

当前接线范围

已经切到 resolver + snapshot 的 chat 链路包括:

  • modules/document:文档分析评分链路
  • modules/simulation:题目生成 / 会话创建 / 评估链路
  • modules/knowledgebase:RAG 改写、问答与流式回答链路

当前已接入动态配置但仍有治理空间的链路:

  • embedding:已接入知识库向量化与检索的任务级 / 查询级快照,但未扩展到更细粒度热切换或重向量化治理
  • voice:已接入会话级 LLM / ASR / TTS 快照,保证单个语音会话内配置一致;WebSocket 实时链路真正消费快照

对前端 / 接口的影响

  • 当前没有新增必传接口字段,也没有把现有公开接口改成新的路径。
  • 运行时配置管理接口已在 api/ai-runtime-config.md 中单独沉淀,前端可通过 /api/ai-runtime-config/* 端点管理模型选择。

项目结构

ruici-ai-platform/
├── src/main/java/com/ruici/ai/
│   ├── common/                # 通用能力:异常、限流、Provider 路由、Redis Stream、AI 运行时配置
│   ├── infrastructure/        # 文件、导出、Redis、映射等基础设施
│   └── modules/
│       ├── document/          # 文档上传、解析、分析、导出
│       ├── simulation/        # 情景模拟、题目生成、回答评估
│       ├── knowledgebase/     # 知识库上传、向量化、RAG 问答
│       ├── schedule/          # 场景化日程解析与管理
│       └── voice/             # 语音交互:WebSocket 实时通话、ASR/TTS、多轮评估
├── src/main/resources/
│   ├── application.yml
│   ├── application-dev.yml
│   ├── logback-spring.xml
│   ├── voice-interview-opening.yml
│   ├── fonts/
│   ├── prompts/               # StringTemplate 提示词模板(.st)
│   ├── scripts/               # Redis Lua 脚本
│   └── skills/                # Skill 资源包(方向题/评估参考)
├── frontend/                  # React 18 + TypeScript + Vite + TailwindCSS 4
├── api/                       # 后端接口文档(按模块)
├── docker/                    # Docker 初始化脚本(postgres init.sql 等)
├── word/                      # 版本改动记录与已知问题
├── .env.example               # 环境变量模板
├── pom.xml                    # Maven 构建配置
├── Dockerfile                 # Docker 镜像构建
├── docker-compose.yml         # 标准环境一体化部署
├── docker-compose.ecs.yml     # ECS 环境兼容部署
├── docker-compose.dev.yml     # 本地开发(只起依赖)
├── deploy-remote.sh           # 服务器环境部署脚本
├── CLAUDE.md                  # AI 开发指南(业务导向)
├── PROMPTS_AND_SKILLS_WIRING.md  # 提示词与技能调用链路文档
├── CODEX_CLAUDE_RULES.md      # 编码规范速查
├── SETUP_API_KEYS.md          # API Key 配置说明
└── README.md                  # 本文件

快速开始

1. 环境要求

依赖 版本 必需 说明
JDK 21+ 后端运行环境
Maven 3.8.8+ 后端构建工具
Node.js 18+ 前端开发环境
Docker 最新版 推荐 本地启动 PostgreSQL / Redis / RustFS / MinIO

在真正启动前,先记住 4 个最容易混淆的初始化职责:

  • API Key:由你自己在 .env 或环境变量里配置。
  • 数据库 ruici_ai_platformdocker compose 会自动创建;手动安装 PostgreSQL 时需要自己创建。
  • 数据表:由 spring.jpa.hibernate.ddl-auto=update 在开发环境自动补齐。
  • 对象存储 bucketdocker-compose.dev.yml 与完整 docker-compose.yml 都会自动创建默认 bucket ruici-ai-platform

2. 配置环境变量

推荐先复制模板:

cp .env.example .env

至少需要按场景配置两类 Provider:

  • 第三方 OpenAI-compatible 中转:用于默认聊天与情景模拟
  • DashScope / Qwen:用于向量化和语音

核心变量如下:

AI_DEFAULT_PROVIDER=third-party
THIRD_PARTY_BASE_URL=https://api-s.zwenooo.link/v1
THIRD_PARTY_API_KEY=your_gateway_key
THIRD_PARTY_MODEL=gpt-5.2
THIRD_PARTY_FALLBACK_MODEL=qwen-plus

AI_BAILIAN_API_KEY=your_dashscope_key
AI_EMBEDDING_MODEL=text-embedding-v3
APP_VOICE_INTERVIEW_LLM_PROVIDER=dashscope

完整字段说明见 SETUP_API_KEYS.md.env.example

安全提醒:请仅在 .env 或环境变量中填写真实密钥,严禁把真实 API Key/Token/Password 写入 READMESETUP_API_KEYS.md、测试用例或其他会进入版本库的文件。

安全数据区(基于 .gitignore

为了降低误提交敏感信息的风险,本项目把以下内容视为“安全数据区”,默认不进入版本控制:

  • 环境变量与密钥:.env.env.*(仅保留 .env.example 作为模板)。
  • 本地 Spring 覆盖配置:application-local.*application-dev-local.*bootstrap-local.*
  • 证书/私钥/Keystore:*.pem*.key*.p12*.pfx*.jksid_rsa 等。
  • 内部资料与提示词草案:private/
  • 工具缓存(可能携带 token/会话态):.playwright-mcp/.playwright-cli/

另外,.gitignore 里也默认忽略 src/main/resources/application-dev.yml

  • 如果你需要团队共享开发环境默认配置,建议改为提交一个不含密钥的 application-dev.example.yml,并在本地用 application-dev.yml 覆盖。
  • 如果你只在本地开发使用它,请确保里面不出现真实 API Key/Password

2.1 关于“旧键名”和“新语义”的关系

为了兼容当前代码,项目里还有一些历史命名没有一次性全部改掉。新手第一次看到时,最容易误会它们只服务于面试场景。

你可以先按下面这张表理解:

现有键名 / 目录名 现在真正的语义
app.resume / resume 通用职业文档分析
app.interview / interview 情景模拟主流程
app.voice-interview 语音交互 / 语音情景模拟
APP_VOICE_INTERVIEW_LLM_PROVIDER 语音模块默认 Provider

也就是说:看到旧命名时,优先按 Ruici 的新业务语义理解,不要按旧项目 InterviewGuide 的边界去理解。

3. 启动基础设施

推荐新手先用开发编排启动基础设施:

docker compose -f docker-compose.dev.yml up -d

启动完成后,请按下面顺序检查:

3.1 PostgreSQL 是否已自动建库

docker-compose.dev.yml 里已经设置了 POSTGRES_DB=ruici_ai_platform,因此 容器首次启动时会自动创建数据库

如果你不是用 Docker,而是本地自己装的 PostgreSQL,请手动执行:

CREATE DATABASE ruici_ai_platform;

CREATE EXTENSION IF NOT EXISTS vector;

这里要特别注意:

  • ddl-auto 只能建表,不能建数据库
  • docker/postgres/init.sql 只负责执行 CREATE EXTENSION IF NOT EXISTS vector;,不负责建库。

3.2 对象存储 bucket 是否已创建

如果你使用的是 docker-compose.dev.yml

  • 访问 http://localhost:9001
  • 登录对象存储控制台确认对象存储服务已启动
  • docker-compose.dev.yml 默认会自动创建 bucket:ruici-ai-platform

如果你使用的是根目录完整编排 docker-compose.yml,项目里的 createbuckets 初始化容器会自动创建这个 bucket。

3.3 ddl-auto 在开发环境应该是什么

开发环境推荐保持:

spring:
  jpa:
    hibernate:
      ddl-auto: update

原因是:

  • update:适合开发,缺表时自动创建,已有数据尽量保留。
  • create:每次启动都可能删表重建,新手很容易误删数据。
  • validate:适合生产,只校验,不自动建表。

4. 启动后端

mvn spring-boot:run

如果启动失败,请优先检查下面 5 项:

  1. 当前 Java 版本是否是 21
  2. .env 中的 THIRD_PARTY_API_KEYAI_BAILIAN_API_KEY 是否已配置。
  3. PostgreSQL 中是否存在数据库 ruici_ai_platform
  4. PostgreSQL 中是否已启用 vector 扩展。
  5. 对象存储中是否已存在 bucket ruici-ai-platform

后端默认地址:http://localhost:8080

5. 启动前端

cd frontend
pnpm install
pnpm dev

前端默认地址:http://localhost:5173

Docker 部署

项目根目录提供 docker-compose.yml,可启动:

  • PostgreSQL + pgvector
  • Redis
  • MinIO(完整编排 / ECS)
  • RustFS(开发编排)
  • Spring Boot 后端
  • React 前端

Compose 文件作用与异同

文件 主要用途 包含服务 对象存储 网络模式 端口暴露方式
docker-compose.dev.yml 本地开发(只起依赖) postgresredisrustfscreatebuckets RustFS bridge ports 显式映射(5432/6379/9000/9001)
docker-compose.yml 标准环境一体化部署 postgresredisminiocreatebucketsappfrontend MinIO bridge ports 显式映射(80/8080/5432/6379/9000/9001)
docker-compose.ecs.yml ECS 老环境兼容部署 postgresredisminiocreatebucketsappfrontend MinIO network_mode: host 走宿主机端口(不依赖 ports 映射)

选择建议:

  • 仅在本机调试后端(mvn spring-boot:run)时,用 docker-compose.dev.yml
  • 需要本地一键起完整前后端时,用 docker-compose.yml
  • 当前阿里云 ECS 老环境(bridge 异常场景)优先用 docker-compose.ecs.yml
  • 三套编排都会通过 createbuckets 自动创建 APP_STORAGE_BUCKET(默认 ruici-ai-platform)。

启动方式:

docker compose up -d --build

常见问题

v1.3.0 为什么只先做 chat 运行时动态配置?

因为聊天链路最容易遇到模型切换、fallback 和中转兼容问题,也是当前 document / simulation / knowledgebase 三个核心模块的共性依赖。先把 chat 统一到 resolver + snapshot + model-aware cache, 可以先把收益最大的部分稳定下来。

数据库动态配置会不会把密钥也放进数据库?

不会。当前运行时配置表只存 providerId、modelName、fallbackModelName、scene、domain、priority、 configVersion 等 非敏感控制信息。真实 API Key 仍然只保留在 .env 或环境变量中。

voice / embedding 的动态配置做到了什么程度?

截至 v1.3.1

  • embedding 已按任务/批次级快照接入知识库向量化与检索,避免 chunk 级频繁查库
  • voice 已按会话级快照接入 LLM / ASR / TTS 三类配置,WebSocket 实时链路真正消费快照

当前仍未推进的是 embedding 相关的更高阶治理(例如重向量化策略),目的是保证稳定链路不被一次性放大风险。

向量化为什么仍然依赖 Qwen / DashScope?

因为当前项目保留了 Qwen / DashScope 作为稳定的 Embedding 与实时语音能力来源,这部分不跟随主聊天 Provider 一起切换。

为什么默认不是直接用 OpenAI?

因为项目当前的主策略是 自定义 OpenAI-compatible 中转优先,OpenAI 原生 Provider 作为可选项保留在多 Provider 注册表中。

OpenAI-compatible 一定完全兼容吗?

不一定。不同网关在 chat/completions、流式事件结构、工具调用和结构化输出上可能存在差异。项目已经采用 Provider 分层:聊天默认走中转,语音/向量保留 Qwen。

About

泛职业文档分析 + 多场景情景模拟平台

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors