互联网医院源码核心拆解:在线问诊与在线开处方链路如何打通 简介这是一套面向医疗信息化开发者的互联网医院平台源码整合在线问诊、在线开处方等核心业务适合需要搭建远程医疗服务系统或学习医疗SaaS架构的团队与个人。系统覆盖患者端问诊沟通、医生端电子处方开具与审核涉及药品库对接、支付、附件管理等功能模块可帮助理解从医患交互到处方流转的完整链路也能大幅缩短自研周期。压缩包约83.55MB上游暂未提供文件总数及类型明细但就源码说明来看代码按应用层、API接口、Web入口、框架核心、插件扩展、支付处理、附件存储等目录组织结构清晰。已有248人浏览学习适合医疗IT开发者、产品经理及运维人员将其作为功能参考或二次开发基底尤其对电子处方合规、问诊数据存储与支付对接具有直接借鉴价值。 互联网医院这个方向最近找我咨询源码的人明显变多了。前阵子帮朋友评估了一套号称“完整”的互联网医院源码代码拿到手一看在线问诊和在线开处方两个模块确实都有但真正跑起来才发现核心不在这两个功能“有没有”而在它们之间的业务链条通不通。这篇就结合我实际看过、改过、部署过的经验把互联网医院源码里最关键的在线问诊、在线开处方这两块掰开揉碎讲清楚给正在选型、二次开发或者打算自己从零搭一套的朋友做个参考。1. 问诊和处方在主链路里的真实位置1.1 一次线上问诊的完整业务闭环很多人第一次接触互联网医院源码时最容易犯的错就是把它当成“聊天系统 一个开药窗口”。实际上一次完整的线上问诊链路远比这复杂患者提交病情描述、上传历史病历和检查报告系统自动或人工完成分诊医生接诊后进入问诊会话问诊过程中可能需要开具检查检验单问诊结束后根据病情在线开处方处方提交后进入药师审核环节审核通过后患者支付支付完成后由药房配药、物流发货或到院自取最后是诊后随访和复诊提醒。这个闭环里最关键的两个节点就是问诊和处方。问诊是信息采集和医患互动的过程而在线开处方是整个线上诊疗行为的“产出物”。一套合格的互联网医院源码问诊和处方必须是无缝衔接的——医生在问诊会话里可以直接看到患者全量资料一键发起开方处方里的诊断、用药要和问诊结论对得上不能问诊归问诊、开方归开方各管各的。1.2 电子处方模块在其中的支撑作用再说直白点在线开处方是患者能感知到的“结果”问诊则是这个结果的前置过程。处方模块要支撑的不仅是“填个药品名称、填个剂量”而是完整的药品目录、用法用量、频次、疗程、医生电子签名、合理用药监测、处方有效期、药师复核标记这一整串规则。我评估源码时有个习惯先不看问诊聊天写得多花哨先打开处方模块的表结构和业务规则看看状态有没有做全、校验有没有落到数据库层、药品信息是同步的还是实时调用的。因为这些直接决定这套源码能不能过审、能不能应对真实业务压力也决定你二次开发时要填多少坑。2. 在线问诊模块的状态机与数据模型设计2.1 问诊单状态流转是源码的“骨架”问诊模块如果只是“患者发消息、医生回消息”那就没有任何门槛了。真正体现源码功底的是问诊单的状态机设计。正常一套可用的问诊流程状态至少包括待支付、待接诊、问诊中、待开方、已完成、已取消、退款中、已退款。状态设计里最常见的坑就是把状态字段做成一个普通字符串哪里需要就 update 一下结果状态流转完全失控医生可以给一个已取消的问诊单开处方患者可以对已完成的问诊单发起退款。正规的源码应该在服务层统一封装状态流转方法每个流转动作都做前置校验非法流转直接抛异常。public enum ConsultState { PENDING_PAY(0, 待支付), WAITING_DOCTOR(1, 待接诊), IN_CONSULT(2, 问诊中), PENDING_PRESCRIPTION(3, 待开方), COMPLETED(4, 已完成), CANCELED(5, 已取消), REFUNDING(6, 退款中), REFUNDED(7, 已退款); private final int code; private final String desc; }核心就一条问诊单的每一次状态变更都必须走同一个入口校验当前状态是否允许跳转到目标状态。我把这一层叫“状态机守卫”没有这个守卫的源码后面越改越乱。2.2 问诊关键数据表结构参考问诊单的数据结构设计直接决定后面扩展顺不顺手。主表通常叫consult核心字段包括问诊单号、患者ID、医生ID、科室ID、问诊类型、状态、费用金额、支付单号、创建时间、接诊时间、结束时间。问诊单号一定要独立生成别用数据库自增ID直接对外业务上你需要一个类似于“ZX20250101001”这样可读性强的编号。除了主表问诊相关信息建议拆子表存储。比如consult_im_message存聊天消息consult_attachment存患者上传的病历、检查报告图片consult_detail存问诊的补充信息主诉、现病史、既往史等。CREATE TABLE consult ( id bigint(20) NOT NULL AUTO_INCREMENT, consult_no varchar(32) NOT NULL COMMENT 问诊单号, patient_id bigint(20) NOT NULL COMMENT 患者ID, doctor_id bigint(20) DEFAULT NULL COMMENT 医生ID, dept_id bigint(20) DEFAULT NULL COMMENT 科室ID, consult_type tinyint(4) NOT NULL COMMENT 问诊类型1图文 2电话 3视频, state tinyint(4) NOT NULL COMMENT 状态, amount decimal(10,2) NOT NULL COMMENT 问诊费用, pay_no varchar(64) DEFAULT NULL COMMENT 支付单号, create_time datetime NOT NULL, accept_time datetime DEFAULT NULL, finish_time datetime DEFAULT NULL, PRIMARY KEY (id), KEY idx_patient (patient_id), KEY idx_doctor (doctor_id), KEY idx_state (state) ) ENGINEInnoDB DEFAULT CHARSETutf8mb4;为什么要强调这个表结构我在实际业务里遇到过不少坑比如pay_no字段没有唯一索引导致重复支付回调时产生了两个不同问诊单比如没有finish_time导致统计问诊时长的时候只能拿update_time来凑数。这些看似小问题后期运维和出报表的时候都是大麻烦。2.3 费用结算与医患匹配如何联动问诊费用这块是源码里最容易出隐性Bug的地方。一套完整的问诊流程里费用状态大致是待支付 → 已支付 → 已结算给医生 →或退款。只要支付和问诊状态没有放在同一个事务或者同一个最终一致性方案里就一定会出现“钱付了问诊单还是待支付”的情况。我推荐的稳妥方案是支付回调更新支付单状态然后发一个领域事件或者MQ消息由问诊服务消费后更新问诊单状态。两个服务各管各的数据通过消息对账必要时启用定时任务拉取两边数据做补偿。医患匹配这块初期可以做成“患者选医生/选科室下单”源码里对应的逻辑是医生排班表和问诊号源池。更合理的是加一层智能分诊——根据患者填的症状关键词先推荐科室再在科室下推荐当前在线且空闲的医生。这个功能做成规则引擎就够了不需要上什么复杂模型但很多源码在这块做得非常粗糙甚至连科室推荐都没有全靠患者自己猜。3. 在线开处方模块的核心实现与校验逻辑3.1 处方结构的组织方式在线开处方是整个系统里业务规则最密集的部分。一套标准的电子处方结构通常包含三个层级处方主表、处方明细药品、处方操作记录。主表记录患者ID、医生ID、诊断编码、诊断描述、处方类型、状态、开方时间、有效截止时间、备注明细表记录每种药品、单次剂量、用量单位、给药途径、频次、频次单位、疗程天数、总量、药品备注。public class PrescriptionDTO { private String consultNo; private String patientId; private String doctorId; private String diagnosisCode; // 诊断编码ICD-10 private String diagnosisDesc; // 诊断描述 private ListPrescriptionItemDTO items; } public class PrescriptionItemDTO { private String drugId; private String drugName; private String spec; // 规格 private String dosage; // 单次剂量 private String dosageUnit; // 剂量单位 private String frequency; // 频次如 tid private String route; // 给药途径口服/外用/静脉 private Integer days; // 疗程天数 private String remark; // 备注 }从源码角度讲开方入口通常放在问诊会话页里医生点“去开方”系统从问诊单上下文自动带入患者和医生信息医生只需要填诊断、选药品、填用法然后提交。这个过程看似简单实际上每一次开方动作都要做接口幂等否则医生手抖点了两次提交患者那边就会收到两笔待支付订单药品重复了还容易造成库存超卖。3.2 药品剂量、频次和超量校验药品校验是处方模块的加分项也是让源码从“能用”变成“好用”的关键。基础的校验至少包括必填校验诊断、药品、单次剂量、频次、天数都不能为空剂量范围校验不能超出药品目录里标注的单次极量和每日极量频次合理性bid/tid/qd 要和药品说明书匹配疗程控制普通处方一般不得超过7天用量慢性病等特殊病种可以延长但必须走额外标识重复用药同一张处方里不应出现两种相同通用名的药品相互作用不同药品之间的配伍禁忌有条件的接合理用药数据库没条件的至少内置一份常用禁忌表public void validateDosage(PrescriptionItemDTO item, DrugInfo drug) { BigDecimal dailyDose calcDailyDose(item.getDosage(), item.getFrequency()); if (dailyDose.compareTo(drug.getDailyMaxDose()) 0) { throw new BizException(药品[ item.getDrugName() ]每日用量超出安全范围); } if (item.getDays() drug.getMaxCourseDays()) { throw new BizException(药品[ item.getDrugName() ]疗程超出限制); } }别小看这段校验逻辑我在实测中发现很多源码根本没有“合理用药校验”或者校验逻辑散落在各个Controller里同一套规则在PC端、App端、H5端各写了一遍改一处漏三处。正确的做法是抽取一个独立的处方校验服务所有端都调同一个接口。3.3 处方状态的流转与处方有效期处理处方状态流转和问诊单状态一样重要如果定义不清线上问题会非常多。我常用的状态集合是状态含义说明DRAFT草稿医生正在编辑未正式提交SUBMITTED已提交医生签名并提交进入审核REVIEWING审核中药师已接单正在复核REVIEW_PASSED审核通过药师复核通过患者可支付REVIEW_REJECTED审核驳回药师退回必须写明驳回原因PAID已支付患者已支付药品费用DISPENSING配药中药房已接单DELIVERING配送中已发货COMPLETED已完成患者已签收或到院自取完成EXPIRED已过期超过有效期未支付自动失效CANCELED已取消医生主动作废或患者取消这里重点说两个容易踩坑的点。第一个是处方有效期通常从开方时间起算超过有效期未支付的处方自动置为失效。这个逻辑不能靠用户访问时被动触发要有一个定时任务每天扫描并批量更新状态否则数据库里会躺着大量永远停留在“审核通过”状态的死处方。第二个是状态机流转药师审核通过后不允许再改回草稿已支付处方不允许取消除非走退款流程处方和问诊单一样也要加状态守卫。4. 互联网医院源码的技术选型与模块边界4.1 服务拆分与核心模块划分从技术架构角度一套相对完整的互联网医院源码模块拆分通常长这样患者端服务注册登录、个人中心、预约问诊、支付医生端服务接诊、问诊、开方、查看患者画像运营管理后台医生管理、排班管理、药品目录管理、问诊记录查询、处方查询基础服务用户中心、消息中心、支付中心、文件存储处方中心处方创建、校验、状态流转、与HIS互通药师审方服务处方审核工作台、驳回/通过操作微服务有微服务的好处但也要量力而行。如果团队就三五个人别一上来就搞十几个微服务加上一套K8s光运维就能把人拖垮。单体应用或者按业务边界拆三四个服务就够用了互联网医院的核心价值在业务规则不在架构炫技。4.2 第三方能力集成支付、推送、电子签名支付、推送、电子签名这三块我建议直接选成熟方案甚至源码里自带的实现如果是“阉割版”二次开发时也优先考虑替换。支付这一环重点看回调处理的可靠性。源码里如果支付回调只是简单地判断“你付没付过”那肯定不行。正规做法是回调里先查询支付单通过唯一业务号加幂等控制再用分布式事务或本地消息表保证支付状态和业务单状态最终一致。消息推送要同时考虑站内信、App推送、短信或者微信服务号通知。问诊模块里医生接诊通知、患者发起问诊通知、处方审核结果通知都依赖消息中心。我个人习惯是把消息模板独立成一张表不同场景的文案和推送渠道都能在后台动态配置避免每次改文案都要发版。电子签名是处方合规性的关键保障正规方案是接入权威CA机构的数字证书服务服务器端完成签名操作并附上时间戳。这个能力千万不要自己造轮子签名链路里涉及的证书存储、密钥管理自己从零做既费时又容易出安全漏洞。4.3 HIS集成为什么是最麻烦的一环所谓互联网医院不可能脱离实体医院独立存在。患者档案、药品库存、历史就诊记录这些数据大部分在医院的HIS系统里而HIS系统普遍部署在医院内网有严格的网络安全隔离要求。在线问诊开出的处方也要同步回HIS系统才能完成后续的院内配药或者医保报销。源码在这一块的做法通常是走中间库或者消息队列。中间库方案在HIS内网数据库侧建一张同步表互联网侧系统定时把需要同步的数据写入中间库HIS侧的服务读取中间表后写入HIS反之亦然。消息队列方案通过具备网络安全隔离区代理能力的消息组件把数据变更事件投递给对方。两种方案各有优劣但核心原则一致——两边系统不直连数据库只通过约定好的数据接口或者消息通道交互。我评估源码时如果一套源码的HIS集成写死了某个厂商的接口协议基本就不考虑了。因为每家医院的HIS厂商不一样接口千差万别源码里这部分必须是可配置、可适配的最好是抽象出一套适配器接口针对不同医院做定制实现。5. 从源码落地到上线我最想提醒的几个坑5.1 问诊超时无人接单的处理策略线上问诊最怕的就是患者付了钱结果医生半天不接单体验直接崩了。源码里如果没有超时处理机制这个问题在业务量上来之后一定会被投诉淹没。常规做法是配置一个“接单超时时间”比如15分钟。定时任务每隔1分钟扫描一次待接诊状态的问诊单超过15分钟未接单的自动退还费用并关闭问诊单同时给患者推送一条说明通知。更复杂的做法是增加“转诊”或“重新分诊”机制系统自动把问诊单转给同科室其他在线医生。5.2 药品目录不规范带来的连锁问题药品目录是整个处方模块的数据地基。我见过有源码把药品名称、规格、厂家、剂型、用法、剂量单位全塞在一个字段里的这种数据设计处方校验根本无从谈起。药品目录至少需要独立的药品表字段要覆盖通用名、商品名、剂型、规格、生产厂家、批准文号、单次极量、每日极量、默认频次、给药途径、是否冷链、是否特殊管制。药品数据本身建议对接权威药品库初始化时批量导入日常运营中同步维护价格、库存、上架状态。没有一套干净药品目录的互联网医院源码处方写得再漂亮也是空中楼阁。5.3 并发场景下的重复处方与幂等设计想象这个场景医生在问诊会话里开了一张处方网络卡了一下医生又点了两次提交。如果接口没做幂等系统里就会出现两张一模一样的待审核处方患者端就要付两笔钱。这个问题在并发稍高的时候必现。我的处理方式是开方接口强制要求一个幂等键从问诊上下文中取consultNo doctorId生成后端收到请求后先查这个幂等键是否已存在成功记录存在就直接返回原结果不存在才执行业务逻辑。数据库层还要给consult_no加唯一索引双保险兜底。处方提交后所有关联的药品明细和费用快照都在这一个事务里写完不能拆成好几个接口调。5.4 处方审核与操作留痕电子处方涉及诊疗过程每一步操作都必须留痕这一点是底线。患者什么时间提交的问诊医生什么时间开方处方内容是什么药师审核的意见是什么系统都要有完整的日志和操作记录。我在评估源码时会重点看操作日志表的字段设计比如是否记录了操作人、操作时间、操作前后数据快照、操作来源IP、操作接口标识。没有操作留痕的处方模块后期一旦产生纠纷平台会非常被动。留痕实现上基于Spring的AOP切面配合自定义注解做操作日志采集是主流做法注解标注在Controller层或者Service层的方法上框架自动记录入参、出参、耗时和操作人。业务数据变更则通过监听实体变更事件统一写入数据变更日志表。最后说点实在的。互联网医院源码功能列表再齐全都不如把“问诊-开方”这条主链路打磨扎实。选型的时候多看状态机、多挖数据表、多测边界条件重点看处方校验是不是服务化、支付回调是不是幂等、HIS对接是不是可配置、操作日志是不是完整。把这几个点都过一遍源码本身的底子是好是坏基本就有数了。我自己实践下来最耗精力的反而不是那些炫酷功能恰恰是这些平时看不见的“链路可靠性”。本文还有配套的精品资源点击获取