【免费】AI智能医疗问诊平台系统(RAG+Spring AI2.0+Neo4j知识图谱+SpringBoot4+Vue3) 锋哥原创出品,必属精品

发布时间:2026/10/3 9:35:07

【免费】AI智能医疗问诊平台系统(RAG+Spring AI2.0+Neo4j知识图谱+SpringBoot4+Vue3) 锋哥原创出品,必属精品 大家好我是Java1234_小锋老师分享一套锋哥原创的AI智能医疗问诊平台系统(RAGSpring AI2.0Neo4j知识图谱SpringBoot4Vue3) 。项目介绍随着分级诊疗制度持续推进和居民健康管理意识不断增强基层医疗机构与互联网平台都面临着“咨询量大、专科医生相对不足、健康知识获取渠道分散”的现实矛盾。传统在线问诊系统多以表单留言或人工即时通讯为主难以对患者的自然语言症状描述进行结构化理解也缺少可追溯的医学依据。与此同时大语言模型、检索增强生成RAG和图数据库技术日趋成熟为构建“可引用、可解释、可转诊”的智能问诊系统提供了技术条件。本文设计并实现了一套面向本科毕业设计场景的AI智能医疗问诊平台系统。系统采用前后端分离架构后端基于Java 17与Spring Boot 4构建RESTful服务集成Spring AI 2.0对接通义千问大语言模型前端采用Vue 3、Vite与Element Plus实现患者门户、医生工作台和管理后台三端界面。业务数据存储于MySQL 8数据库库名db_ai_medical表名均以t_开头医学实体关系存储于Neo4j知识图谱指南类文档经分块与向量化后写入本地向量库形成“关系数据 向量检索 图谱推理”的混合知识底座。在功能层面系统支持患者注册登录、AI多轮问诊、症状图谱推理、人工咨询、预约挂号、健康档案查询和健康资讯浏览支持医生处理咨询工单、确认预约并维护患者档案支持管理员进行用户与科室管理、知识库上传向量化、图谱可视化、文章公告运营以及首页数据统计。AI问诊采用SSE流式输出回答中附带知识库引用片段和图谱候选疾病并明确提示“仅供参考、不能替代面诊”以降低误导风险。测试结果表明系统三角色权限隔离正确核心业务流程闭环完整知识库文件可完成解析、分块与向量化图谱能够根据症状返回候选疾病及推荐科室。本系统对探索大模型在医疗咨询场景中的工程落地具有一定的参考价值。源码下载链接: https://pan.baidu.com/s/1eBPdVADGePMNl83McSUO7Q?pwd1234提取码: 1234系统展示核心代码package com.java1234.controller; import com.java1234.common.PageResult; import com.java1234.common.Result; import com.java1234.dto.AppointmentCreateRequest; import com.java1234.interceptor.RequireRoles; import com.java1234.service.AppointmentService; import jakarta.validation.Valid; import org.springframework.format.annotation.DateTimeFormat; import org.springframework.web.bind.annotation.*; import java.time.LocalDate; import java.util.List; import java.util.Map; /** * 预约挂号接口 */ RestController RequestMapping(/api/v1/appointments) public class AppointmentController { private final AppointmentService appointmentService; public AppointmentController(AppointmentService appointmentService) { this.appointmentService appointmentService; } /** * 创建预约患者 */ PostMapping(/create) RequireRoles(user) public ResultMapString, Object create(Valid RequestBody AppointmentCreateRequest req) { return Result.success(appointmentService.createAppointment(req), 预约成功); } /** * 我的预约患者 */ GetMapping(/my) RequireRoles(user) public ResultListMapString, Object my() { return Result.success(appointmentService.myAppointments()); } /** * 医生的预约 */ GetMapping(/doctor/my) RequireRoles(doctor) public ResultListMapString, Object doctorMy() { return Result.success(appointmentService.doctorAppointments()); } /** * 管理员预约列表 */ GetMapping(/admin/list) RequireRoles(admin) public ResultPageResultMapString, Object adminList( RequestParam(defaultValue 1) int page, RequestParam(name page_size, defaultValue 10) int pageSize, RequestParam(defaultValue ) String keyword, RequestParam(name department_id, required false) Integer departmentId, RequestParam(name visit_date, required false) DateTimeFormat(iso DateTimeFormat.ISO.DATE) LocalDate visitDate, RequestParam(required false) Integer status) { PageResultMapString, Object result appointmentService.adminList( page, pageSize, keyword, departmentId, visitDate, status); return Result.page(result.getItems(), result.getTotal(), result.getPage(), result.getPageSize()); } /** * 管理员删除预约 */ DeleteMapping(/admin/{appt_id}) RequireRoles(admin) public ResultVoid adminDelete(PathVariable(appt_id) Integer apptId) { appointmentService.adminDelete(apptId); return Result.success(null, 删除成功); } /** * 更新预约状态管理员/医生 */ PutMapping(/{appt_id}/status) RequireRoles({admin, doctor}) public ResultVoid updateStatus(PathVariable(appt_id) Integer apptId, RequestParam Integer status) { appointmentService.updateStatus(apptId, status); return Result.success(null, 状态更新成功); } }script setup import { ref, onMounted, onUnmounted } from vue import { ElMessage, ElMessageBox } from element-plus import { Upload } from element-plus/icons-vue import request from /utils/request import { formatDateTime, parseListData } from /utils/format const list ref([]) const loading ref(false) const uploading ref(false) /** 搜索关键词 */ const keyword ref() /** 分页参数 */ const page ref(1) const pageSize ref(10) const total ref(0) /** 状态轮询定时器 */ let pollTimer null /** 判断是否存在待处理或处理中的文件 */ function hasPendingFiles(items) { return items.some((item) item.vector_status 0 || item.vector_status 1) } /** 获取列表请求参数 */ function getListParams() { return { page: page.value, page_size: pageSize.value, keyword: keyword.value.trim(), } } /** 启动状态轮询向量化完成后自动停止 */ function startPolling() { if (pollTimer) return pollTimer setInterval(() { refreshList() }, 3000) } /** 停止状态轮询 */ function stopPolling() { if (pollTimer) { clearInterval(pollTimer) pollTimer null } } /** 加载知识库列表 */ async function loadList(silent false) { if (!silent) loading.value true try { const res await request.get(/knowledge/list, { params: getListParams() }) list.value parseListData(res) total.value res.data?.total ?? list.value.length if (hasPendingFiles(list.value)) { startPolling() } else { stopPolling() } } catch { list.value [] total.value 0 stopPolling() } finally { if (!silent) loading.value false } } /** 静默刷新列表轮询时使用避免 loading 闪烁 */ async function refreshList() { try { const res await request.get(/knowledge/list, { params: getListParams() }) list.value parseListData(res) if (!hasPendingFiles(list.value)) { stopPolling() } } catch { /* 轮询失败时忽略下次继续 */ } } /** 搜索知识库文件 */ function handleSearch() { page.value 1 loadList() } /** 重置搜索条件 */ function handleReset() { keyword.value page.value 1 loadList() } /** 分页切换 */ function handlePageChange(p) { page.value p loadList() } /** 上传知识文件 */ async function handleUpload({ file }) { uploading.value true const formData new FormData() formData.append(file, file) try { await request.post(/knowledge/upload, formData, { headers: { Content-Type: multipart/form-data }, }) ElMessage.success(上传成功正在向量化处理) page.value 1 await loadList() } catch { /* */ } finally { uploading.value false } } /** 删除知识库文件 */ async function handleDelete(row) { try { await ElMessageBox.confirm( 确定删除知识库文件「${row.file_name}」吗删除后不可恢复。, 提示, { type: warning }, ) await request.delete(/knowledge/${row.id}) ElMessage.success(删除成功) if (list.value.length 1 page.value 1) { page.value - 1 } await loadList() } catch { /* */ } } onMounted(loadList) onUnmounted(stopPolling) /script template div div classpage-header h2 classpage-title知识库管理/h2 el-upload :show-file-listfalse :http-requesthandleUpload accept.txt,.pdf,.doc,.docx,.md el-button typeprimary classgradient-btn :loadinguploading :iconUpload 上传文件 /el-button /el-upload /div div classmodern-card !-- 搜索栏 -- div classsearch-bar el-input v-modelkeyword placeholder搜索文件名 / 文件类型 clearable stylewidth: 280px keyup.enterhandleSearch / el-button typeprimary clickhandleSearch搜索/el-button el-button clickhandleReset重置/el-button /div el-table :datalist v-loadingloading classadaptive-table stripe el-table-column propid labelID min-width60 / el-table-column propfile_name label文件名 min-width200 show-overflow-tooltip / el-table-column propfile_type label类型 min-width100 template #default{ row } el-tag sizesmall{{ row.file_type || row.type || - }}/el-tag /template /el-table-column el-table-column propfile_size label大小 min-width100 template #default{ row } {{ row.file_size ? (row.file_size / 1024).toFixed(1) KB : (row.size ? (row.size / 1024).toFixed(1) KB : -) }} /template /el-table-column el-table-column propvector_status label状态 min-width100 template #default{ row } el-tag :typerow.vector_status 2 ? success : row.vector_status 3 ? danger : info sizesmall {{ row.vector_status 2 ? 已向量化 : row.vector_status 3 ? 失败 : row.vector_status 1 ? 处理中 : 已上传 }} /el-tag /template /el-table-column el-table-column propcreate_time label上传时间 min-width170 template #default{ row }{{ formatDateTime(row.create_time || row.created_at) }}/template /el-table-column el-table-column label操作 min-width100 fixedright template #default{ row } el-button link typedanger clickhandleDelete(row)删除/el-button /template /el-table-column /el-table el-empty v-if!loading !list.length description暂无知识库文件 / !-- 分页 -- div v-iftotal 0 classpagination-wrap el-pagination v-model:current-pagepage :page-sizepageSize :totaltotal layouttotal, prev, pager, next background current-changehandlePageChange / /div /div /div /template style scoped .page-header { display: flex; justify-content: space-between; align-items: center; margin-bottom: 20px; } .search-bar { display: flex; align-items: center; gap: 12px; margin-bottom: 16px; } .pagination-wrap { display: flex; justify-content: flex-end; margin-top: 16px; } /style
延伸阅读

更多相关文章

2026/9/26 7:52:32

Windows系统文件TtlsCfg.dll丢失找不到问题解决

在使用电脑系统时经常会出现丢失找不到某些文件的情况,由于很多常用软件都是采用 Microsoft Visual Studio 编写的,所以这类软件的运行需要依赖微软Visual C运行库,比如像 QQ、迅雷、Adobe 软件等等,如果没有安装VC运行库或者安装…

2026/10/2 16:58:49

边缘 AI 协同架构在物联网系统中的应用

一、引言随着大语言模型(LLM)和多模态AI技术的快速发展,将人工智能能力注入物联网(IoT)系统已成为产业数字化转型的核心驱动力。传统“端-云”集中式部署范式面临高延迟、隐私风险与带宽瓶颈等结构性挑战。边缘AI协同架…

2026/10/4 9:11:27

Meta开源Muse Gadgets,让全球开发者自己「造AI外设」

Muse刚火,Meta就让开发者自己造AI硬件! Meta 的 Muse 还在持续升温。 这款刚推出不久的个人 AI Agent,已经成为 Meta 今年 AI 战略中的重要产品。不同于传统聊天机器人,Muse 被设计为能够替用户执行任务的智能助手:处…

2026/10/4 9:11:27

wifit3 WPA握手被动嗅探:如何不开火抓下4-way的完整时机指南

wifit3 WPA握手被动嗅探:如何不开火抓下4-way的完整时机指南 【免费下载链接】wifit3 Wifite but USB-only & cross-platform. 项目地址: https://gitcode.com/GitHub_Trending/wi/wifit3 wifit3 是一款跨平台(Linux / Windows / macOS)的独立 USB Wi-Fi 审计工具,核…

2026/10/4 9:06:27

ENVI遥感水质反演实战:从模型原理到叶绿素a与悬浮物制图

经常有同行问我,说看到别人用ENVI做水质反演,一键就能出叶绿素a或者悬浮物的分布图,自己照着操作却总是不对劲,要么反演结果出现成片负值,要么模型精度低到不敢用。其实遥感水质反演这件事,听起来高大上&am…

2026/10/4 0:01:02

Jev+Agent接管浏览器:browser-use实战与jev-ultrafast性能优化

1. 从“Jev”说起:为什么我要把Agent接进浏览器“Jev”这个词最近在圈子里出现的频率越来越高,很多人第一次听到会以为是某个新模型的名字,其实它更像是一种思路——把Jev模型的能力当作底座,通过Agent的方式去接管浏览器&#xf…

2026/10/4 0:01:02

多智能体集群实战:DeepAgents编排、MCP与A2A协议及Skills体系

1. 从"单兵作战"到"集群协同":多智能体编排到底在解决什么问题如果你最近在折腾 Agent 相关的东西,大概率会有一种感觉:单个 Agent 能做的事情,其实很快就摸到天花板了。你给它一个提示词,挂几个工…

2026/10/4 1:01:05

无源低通滤波器设计实战:从RC到LC,手把手教你避开那些坑

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/4 0:01:02

Jev+Agent接管浏览器:browser-use实战与jev-ultrafast性能优化

1. 从“Jev”说起:为什么我要把Agent接进浏览器“Jev”这个词最近在圈子里出现的频率越来越高,很多人第一次听到会以为是某个新模型的名字,其实它更像是一种思路——把Jev模型的能力当作底座,通过Agent的方式去接管浏览器&#xf…

2026/10/4 0:01:02

多智能体集群实战:DeepAgents编排、MCP与A2A协议及Skills体系

1. 从"单兵作战"到"集群协同":多智能体编排到底在解决什么问题如果你最近在折腾 Agent 相关的东西,大概率会有一种感觉:单个 Agent 能做的事情,其实很快就摸到天花板了。你给它一个提示词,挂几个工…

2026/10/4 1:01:05

无源低通滤波器设计实战:从RC到LC,手把手教你避开那些坑

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
☎咨询二维码 ☎ ↑