基于springboot的医药管理系统的设计与

一、引言

在医疗卫生行业持续发展与人们健康意识日益提升的背景下,医药管理在医疗机构和药店运营中占据着愈发关键的地位。传统的医药管理方式,主要依赖人工记录和纸质文件,在实际操作中暴露出众多弊端。比如,手工记录容易出现笔误、数据遗漏等人为失误,导致药品信息的不准确,进而可能影响到患者的治疗效果;数据共享和实时查询困难,不同部门之间难以快速获取所需信息,严重阻碍了工作流程的顺畅进行,降低了工作效率;缺乏统一的管理平台,使得各部门之间协作效率低下,无法形成有效的合力,难以应对复杂多变的业务需求;难以及时掌握药品库存和流向情况,容易造成库存积压或缺货现象,不仅增加了运营成本,还可能延误患者的救治时机。

随着信息技术的飞速发展,开发一套高效、智能的医药管理系统已成为提升医药管理水平的迫切需求。Spring Boot 作为 Java 领域一款优秀的框架,以其快速开发、易于部署及集成多种开源技术的优势,成为构建医药管理系统的理想选择。它能够帮助我们快速搭建稳定、可扩展的 Web 应用,有效解决传统管理方式中的诸多问题,实现药品从采购、库存、销售到患者用药跟踪的全链条信息化管理,提升医药企业的运营效率,增强药品质量追溯能力,为保障患者用药安全提供有力支持。

二、相关技术介绍

2.1 Spring Boot 框架

Spring Boot 是基于 Spring 框架的全新框架,其设计目的是简化 Spring 应用的初始搭建及开发过程。它采用 “约定优于配置” 的理念,大幅减少了项目开发过程中的 XML 配置和代码编写量,开发者能够将更多的精力投入到业务逻辑的实现上 。

在快速开发方面,Spring Boot 提供了丰富的 “开箱即用” 特性,通过一系列的启动器(Starters),可快速集成各种常用功能,如数据库连接、消息传递、缓存等。例如,在本医药管理系统中,使用 Spring Boot 的 Spring Data JPA 启动器,能够轻松实现与 MySQL 数据库的交互,无需繁琐地编写大量的数据库连接和操作代码。

其内嵌服务器(如 Tomcat、Jetty 等)的特性,使得应用程序可以独立运行,无需外部服务器的支持。在部署医药管理系统时,只需使用 “java -jar” 命令即可启动应用,极大地简化了部署流程,提高了部署效率,降低了运维成本。

Spring Boot 拥有庞大且活跃的生态系统,这意味着在开发过程中遇到问题时,能够轻松地在社区中找到解决方案和相关资源。同时,它与众多常用框架和库(如 Spring Security、Spring Data 等)有着良好的集成,为系统的开发和扩展提供了强大的支持,使系统具备更高的稳定性和可维护性。

2.2 Java 语言

Java 是一种高级的面向对象编程语言,由 Sun Microsystems 公司于 1995 年推出。它具有诸多特性,使其非常适合用于开发医药管理系统。

Java 的面向对象特性,允许开发者将现实世界中的实体抽象为类,通过类与类之间的关系来构建复杂的系统。在医药管理系统中,可以将药品、供应商、患者、医护人员等都抽象为类,每个类封装其相关的属性和行为。例如,药品类可以包含药品名称、规格、生产日期、有效期、功效等属性,以及入库、出库、查询库存等行为,这种方式使得代码结构更加清晰,易于理解和维护。

Java 具有 “一次编写,到处运行” 的跨平台特性,这得益于 Java 虚拟机(JVM)。编写好的 Java 程序会被编译成字节码,字节码可以在任何安装了 JVM 的操作系统上运行,无论是 Windows、Linux 还是 Mac OS 等。对于医药管理系统而言,这意味着系统可以轻松地部署在不同的服务器环境中,满足不同医疗机构的多样化需求,而无需针对不同操作系统进行大量的代码修改。

安全性是 Java 语言的重要特性之一。Java 在编译和运行时进行严格的类型检查,消除了许多潜在的类型不匹配问题;它不支持指针,避免了因指针操作不当而导致的内存安全问题;提供了完善的异常处理机制,能够有效地捕获和处理程序运行过程中出现的异常情况,保证系统的稳健运行。在医药管理系统中,涉及大量敏感的医疗数据,Java 的这些安全特性能够确保数据的安全性和完整性,防止数据泄露和非法篡改,为患者的隐私保护提供有力保障。

此外,Java 拥有丰富的类库,涵盖了网络通信、文件处理、图形界面等各个方面,为开发者提供了便捷的开发工具。在开发医药管理系统时,可以直接使用这些类库中的功能,减少重复开发,提高开发效率。

2.3 MySQL 数据库

MySQL 是一款开源的关系型数据库管理系统,凭借其众多优点,在医药数据存储方面展现出显著优势。

开源特性使得 MySQL 的使用成本极低,医疗机构无需支付高昂的软件授权费用,降低了信息化建设的成本。同时,开源社区活跃,开发者可以获取大量的技术支持和资源,方便解决使用过程中遇到的问题。

MySQL 具有高性能和可靠性。它采用了优化的存储引擎,如 InnoDB 和 MyISAM,能够根据不同的应用场景选择最合适的存储方式,提供高效的数据读写性能。在医药管理系统中,需要频繁地对药品信息、患者信息、销售记录等进行查询和更新操作,MySQL 能够快速响应这些请求,确保系统的高效运行。其具备完善的事务处理和数据恢复机制,能够保证数据的完整性和一致性,即使在系统出现故障的情况下,也能最大程度地恢复数据,保障医药业务的连续性。

MySQL 支持多种操作系统,如 Windows、Linux 等,具有良好的兼容性,能够与使用不同操作系统的服务器无缝集成。并且,它可以轻松地进行扩展,无论是增加存储容量还是提升处理能力,都能通过简单的配置调整或硬件升级来实现,以满足医药管理系统随着业务发展而不断增长的数据存储和处理需求。

2.4 其他技术(如前端技术 Vue 等)

在本医药管理系统中,前端采用了 Vue 框架进行开发。Vue 是一款轻量级的 JavaScript 框架,专注于构建用户界面。

Vue 具有简洁易用的特点,其语法简单直观,易于上手,开发者能够快速掌握并运用到项目中。在构建医药管理系统的前端界面时,Vue 的模板语法使得 HTML 和 JavaScript 代码的结合更加自然流畅,能够方便地实现数据的绑定和渲染。例如,通过简单的指令,就可以将从后端获取的药品信息动态地展示在页面上,实现数据与界面的实时同步。

它采用组件化的开发模式,将整个页面拆分成一个个独立的组件,每个组件都有自己的逻辑和样式,提高了代码的复用性和可维护性。在医药管理系统中,像药品列表展示组件、用户登录组件、订单管理组件等,都可以独立开发和维护,当某个组件需要修改或升级时,不会影响到其他组件的正常运行,大大降低了开发和维护的难度。

Vue 还拥有丰富的插件和工具,能够方便地实现各种交互功能。例如,结合 Element – UI 插件,可以快速构建出美观、功能强大的用户界面,提供丰富的组件库,如表格、表单、弹窗等,满足医药管理系统中各种业务场景的交互需求;使用 Axios 库进行数据请求,能够轻松地与后端的 Spring Boot 应用进行数据通信,实现数据的获取、提交和更新等操作,为用户提供流畅的交互体验。

三、系统需求分析

3.1 可行性分析

技术可行性:本系统采用 Spring Boot 框架进行后端开发,利用其强大的依赖管理和自动配置功能,能够快速搭建稳定的后端服务,大大提高开发效率。结合 Java 语言的跨平台性、面向对象特性以及丰富的类库,为系统的功能实现提供了坚实的技术基础。前端使用 Vue 框架,其简洁的语法和组件化开发模式,使得构建交互性强、用户体验良好的界面变得更加容易。MySQL 数据库以其开源、高性能、可靠性以及良好的兼容性,能够满足系统对数据存储和管理的需求。开发团队成员具备相关技术的学习和实践经验,能够熟练运用这些技术进行系统开发,因此在技术层面上,本系统的开发是可行的。

操作可行性:系统在设计时充分考虑了用户体验,界面布局简洁明了,操作流程符合用户的日常习惯。对于管理员和员工角色,系统提供了直观的操作界面,各类功能按钮和菜单易于查找和点击。例如,在药品管理模块,管理员可以通过简单的表单填写完成药品信息的添加、修改和删除操作;员工在进行进货和销售操作时,系统会给出清晰的提示和引导,确保操作的准确性。即使是非专业技术人员,经过简单的培训也能快速上手使用本系统,保证了系统的操作可行性。

经济可行性:开发本医药管理系统主要的成本在于开发人员的人力成本以及开发过程中使用的一些软件工具和服务器资源。Spring Boot、Vue、MySQL 等技术均为开源免费的,无需支付额外的软件授权费用。服务器可以选择租用云服务器,根据实际使用情况灵活选择配置和计费方式,成本相对较低。而系统开发完成后,能够显著提高医药管理的效率,减少人工成本和因管理不善导致的药品损耗,为企业带来更大的经济效益。从长远来看,系统的投入产出比是可观的,因此在经济上是可行的。

法律可行性:在系统开发过程中,所使用的技术和工具均遵循开源协议和相关法律法规,不存在侵权行为。系统开发团队保证所有代码均为自主编写,不存在抄袭和盗用他人代码的情况。同时,系统在设计和实现过程中,严格遵守药品管理相关的法律法规,如药品经营质量管理规范(GSP)等,确保药品信息的安全性、准确性和合规性,保障患者的合法权益。因此,本系统在法律层面是可行的。

3.2 系统性能需求分析

响应时间:系统应具备快速响应能力,对于用户的各类操作请求,如查询药品信息、提交进货或销售订单等,在正常网络环境下,平均响应时间应不超过 3 秒 ,确保用户能够及时获得操作结果,提高工作效率。在高并发情况下,如多个员工同时进行销售操作时,系统的响应时间也应控制在可接受范围内,最大响应时间不超过 5 秒,以避免用户等待时间过长而影响使用体验。

吞吐量:系统需要满足一定的业务吞吐量要求,能够支持同时处理多个并发请求。根据预估的业务量,系统应能够支持至少 50 个并发用户同时在线操作,保证在业务高峰期,如医院或药店的繁忙时段,系统仍能稳定运行,不出现卡顿或崩溃现象。随着业务的发展,系统应具备良好的扩展性,能够方便地进行性能优化和升级,以满足不断增长的吞吐量需求。

可靠性:医药管理系统涉及到大量重要的药品信息和业务数据,因此系统必须具备高度的可靠性。系统应采用可靠的技术架构和设计模式,确保在硬件故障、网络异常等情况下,数据的完整性和一致性不受影响。例如,采用数据库备份和恢复机制,定期对数据进行备份,当出现数据丢失或损坏时,能够及时恢复到最近的可用状态;使用事务处理机制,保证业务操作的原子性,避免因部分操作失败而导致数据不一致的问题。系统的可靠性指标应达到 99.9% 以上,确保业务的连续性和稳定性。

可维护性:为了便于系统的后续维护和升级,系统在设计时应遵循良好的软件设计原则,采用模块化、分层架构,使代码结构清晰,各模块之间的耦合度低。每个模块应具有明确的功能和职责,方便开发人员进行代码的修改和扩展。同时,系统应具备完善的日志记录功能,记录系统运行过程中的关键事件和错误信息,以便在出现问题时能够快速定位和解决。开发过程中应编写详细的技术文档,包括需求文档、设计文档、使用手册等,为系统的维护和升级提供有力支持。

安全性:系统的安全性至关重要,需保障药品信息和用户数据的安全。采用安全的通信协议(如 HTTPS),防止数据在传输过程中被窃取或篡改;对用户进行严格的身份认证和授权管理,只有经过授权的用户才能访问系统的相应功能和数据;对敏感数据(如药品价格、患者信息等)进行加密存储,确保数据的保密性。同时,系统应具备防范常见安全攻击(如 SQL 注入、XSS 攻击等)的能力,定期进行安全漏洞扫描和修复,保障系统的安全稳定运行。

3.3 系统功能需求分析

3.3.1 角色分析

管理员:管理员是系统的最高权限用户,负责系统的整体管理和维护工作。其职责包括对药品信息的全面管理,如添加新药品、修改药品的基本信息(名称、规格、功效、价格等)、删除过期或不再销售的药品,以及实时监控药品库存,当库存低于设定的警戒线时及时进行补货提醒。对供应商信息进行管理,包括添加新供应商、更新供应商的联系方式、信用等级等信息,评估供应商的信誉和供货能力,与优质供应商建立长期合作关系。管理员工信息,如添加新员工、设置员工的账号密码、分配员工的工作权限,对员工的工作表现进行考核和评价。同时,管理员还负责管理药品的进货和销售信息,生成进货和销售报表,以便对业务数据进行分析和决策。

员工:员工在系统中主要负责日常的业务操作。他们可以查看供应商的详细信息,包括供应商的基本资料、供应的药品种类和价格等,以便在进货时做出合理的选择。员工有权查询药品信息,根据药品名称、功效、所治疾病等条件快速检索所需药品,了解药品的库存、进价、售价等信息。在药品进货环节,员工可以新增药品进货记录,填写进货数量、进货时间、供应商等信息,并对进货信息进行查询和核对。在销售环节,员工能够新增药品销售记录,记录销售药品的名称、数量、销售对象等信息,同时可以查询药品的销售历史和销售统计信息,以便更好地了解销售情况,为销售策略的调整提供依据。

3.3.2 功能模块分析

供应商类型管理:该模块允许管理员对供应商类型进行分类管理,如分为药品生产厂家、药品批发商等。管理员可以添加新的供应商类型,设置类型的名称和描述信息,以便更清晰地对供应商进行归类和管理。同时,能够对已有的供应商类型进行修改和删除操作,确保供应商类型信息的准确性和合理性。

供应商信用等级管理:管理员在这个模块中负责对供应商的信用等级进行评定和管理。根据供应商的供货及时性、药品质量、售后服务等多方面因素,为每个供应商设定相应的信用等级,如 A 级(优秀)、B 级(良好)、C 级(合格)、D 级(不合格)等。定期对供应商的信用等级进行更新和调整,对于信用等级高的供应商,可以给予一定的优惠政策或优先合作机会;对于信用等级低的供应商,加强对其供货情况的监督和管理,甚至考虑终止合作关系。

药品类型管理:管理员可以在该模块中对药品类型进行划分和管理,如分为西药、中药、医疗器械等。添加新的药品类型时,填写类型名称、特点、适用范围等详细信息;对现有药品类型进行修改和删除操作,以适应不断变化的药品市场和管理需求。通过合理的药品类型管理,方便对药品进行分类查询和统计分析。

药品管理:此模块是系统的核心功能之一。管理员可以添加药品的详细信息,包括药品名称、规格、生产厂家、生产日期、有效期、功效、用法用量、价格、库存数量、药品照片等。当药品信息发生变化时,如价格调整、库存更新等,管理员能够及时进行修改操作;对于过期、淘汰或因质量问题下架的药品,管理员可以执行删除操作。同时,管理员还可以根据药品的各种属性进行查询,如按药品名称、功效、所治疾病等条件查询,方便快速定位所需药品信息。员工也可以通过该模块查询药品的相关信息,但不具备添加、修改和删除的权限。

进货管理:员工在进货管理模块中,首先可以查看药品的进货详情,包括每次进货的药品名称、进货数量、进货时间、供应商名称、进货价格等信息。当需要进行药品进货时,员工可以新增进货记录,填写相关的进货信息,并提交审核。在进货过程中,系统会自动更新药品的库存数量,确保库存数据的准确性。员工还可以根据进货编号、药品编号、进货时间等条件对进货信息进行查询,以便对进货业务进行跟踪和管理。管理员可以对所有的进货信息进行查看和审核,确保进货流程的合规性和数据的准确性。

销售管理:员工在销售管理模块中,能够查看药品的销售详情,包括销售药品的名称、销售数量、销售时间、销售对象(如患者姓名、医院名称等)、销售价格等信息。员工在进行药品销售时,新增销售记录,记录销售的相关信息,系统会实时更新药品的库存数量和销售统计数据。员工还可以根据销售编号、药品功效、所致疾病等条件查询药品的销售信息,以便分析销售趋势和销售业绩。管理员可以对所有的销售信息进行查看、统计和分析,生成销售报表,为企业的经营决策提供数据支持,同时可以对销售数据进行修改(如因价格调整或销售错误等原因),确保销售数据的准确性。

3.4 系统流程分析

3.4.1 登录流程

用户打开医药管理系统的登录页面,在页面中输入自己的账号和密码。系统接收到用户输入的账号和密码后,将这些信息发送到服务器进行验证。服务器首先在数据库中查询该账号是否存在,如果账号不存在,则返回登录失败的提示信息,告知用户账号错误。如果账号存在,服务器将进一步验证输入的密码是否与数据库中存储的该账号对应的密码一致。若密码正确,系统根据用户账号查询其对应的角色信息(管理员或员工),并根据角色信息为用户分配相应的操作权限,然后跳转到系统的主界面,用户可以根据自己的权限进行相应的操作。若密码错误,系统返回登录失败提示信息,告知用户密码错误,并提示用户重新输入密码,用户最多可尝试输入密码 3 次,若 3 次均输入错误,系统将锁定该账号一段时间,以保障系统的安全性。登录流程如图 1 所示:


@startuml

start

:用户打开登录页面;

:输入账号和密码;

:发送账号和密码到服务器;

if (账号是否存在) then (是)

if (密码是否正确) then (是)

:查询用户角色信息;

:根据角色分配操作权限;

:跳转到系统主界面;

else (否)

:提示密码错误,可重试;

if (重试次数<3) then (是)

:返回登录页面重新输入;

else (否)

:锁定账号一段时间;

endif

endif

else (否)

:提示账号错误;

:返回登录页面重新输入;

endif

stop

@enduml

图 1 登录流程图

3.4.2 业务操作流程(如进货、销售流程)

进货流程:员工在系统中发起进货操作,首先进入进货管理模块,点击 “新增进货” 按钮,系统弹出进货信息录入表单。员工在表单中填写进货的相关信息,包括进货药品的名称(通过下拉菜单选择或手动输入药品编号进行检索)、进货数量、进货时间(系统默认当前时间,可手动修改)、供应商名称(同样通过下拉菜单选择或输入供应商编号检索)、进货价格等信息。填写完成后,员工点击 “提交” 按钮,系统对输入的信息进行合法性校验,如检查药品名称是否存在、进货数量是否为正整数、进货价格是否合理等。若信息校验通过,系统将进货信息保存到数据库中,并自动更新药品的库存数量,即库存数量 = 原有库存数量 + 进货数量。同时,系统生成进货记录的唯一编号,并将该编号显示给员工,以便员工进行后续的查询和跟踪。若信息校验不通过,系统弹出错误提示框,告知员工错误信息,员工根据提示修改信息后重新提交。进货流程如图 2 所示:


@startuml

start

:员工进入进货管理模块,点击新增进货;

:弹出进货信息录入表单;

:员工填写进货信息;

:点击提交;

:系统进行信息合法性校验;

if (校验是否通过) then (是)

:保存进货信息到数据库;

:更新药品库存数量;

:生成进货记录编号并显示;

else (否)

:弹出错误提示框;

:员工修改信息后重新提交;

endif

stop

@enduml

图 2 进货流程图

销售流程:员工在系统中进行销售操作时,进入销售管理模块,点击 “新增销售” 按钮,系统弹出销售信息录入表单。员工首先在表单中选择销售药品的名称(通过搜索或下拉菜单选择),系统自动带出该药品的规格、售价等信息。员工填写销售数量、销售时间(默认当前时间,可修改)、销售对象(如患者姓名、单位名称等)等信息。填写完毕后,点击 “提交” 按钮,系统对销售信息进行校验,检查销售数量是否超过库存数量、销售对象信息是否完整等。若校验通过,系统将销售信息保存到数据库中,更新药品的库存数量,即库存数量 = 原有库存数量 – 销售数量,同时生成销售记录的唯一编号,并显示给员工。若校验不通过,系统弹出错误提示,员工根据提示修改信息后再次提交。销售流程如图 3 所示:


@startuml

start

:员工进入销售管理模块,点击新增销售;

:弹出销售信息录入表单;

:选择销售药品名称,带出药品信息;

:填写销售数量、时间、对象等信息;

:点击提交;

:系统进行信息校验;

if (校验是否通过) then (是)

:保存销售信息到数据库;

:更新药品库存数量;

:生成销售记录编号并显示;

else (否)

:弹出错误提示框;

:员工修改信息后重新提交;

endif

stop

@enduml

图 3 销售流程图

四、系统设计

4.1 系统架构设计

本医药管理系统采用 Browser/Server(B/S)架构,这种架构模式在当今的 Web 应用开发中应用广泛。在 B/S 架构下,用户通过浏览器与系统进行交互,无需在本地安装专门的客户端软件,降低了用户的使用门槛和系统部署成本 。系统的前端负责呈现用户界面,接收用户的操作请求,并将请求发送到后端服务器;后端服务器负责处理业务逻辑,与数据库进行交互,执行数据的查询、更新等操作,然后将处理结果返回给前端;数据库则用于存储系统运行所需的各类数据,如药品信息、供应商信息、员工信息、进货销售记录等。

在前端开发中,使用 Vue 框架构建用户界面。Vue 具有简洁易用、组件化开发的特点,能够快速搭建出交互性强、用户体验良好的页面。通过 Vue 的指令和组件,可以方便地实现数据的绑定、动态渲染以及页面元素的交互效果。例如,在药品列表展示页面,使用 Vue 的 v – for 指令可以快速遍历从后端获取的药品数据,并将其展示在页面上;通过 v – on 指令可以为按钮等元素绑定点击事件,实现查询、添加、修改、删除等操作。同时,结合 Element – UI 组件库,能够快速构建出美观、功能齐全的界面,提供丰富的组件,如表格、表单、弹窗等,满足医药管理系统中各种业务场景的交互需求。

后端基于 Spring Boot 框架进行开发。Spring Boot 框架简化了 Spring 应用的搭建和开发过程,采用 “约定优于配置” 的理念,减少了大量的 XML 配置文件,提高了开发效率。它提供了丰富的 Starters,能够方便地集成各种功能,如数据库连接、数据访问、安全认证等。在本系统中,通过 Spring Data JPA Starter 实现与 MySQL 数据库的无缝连接,利用 Spring Security Starter 实现用户的身份认证和授权管理。后端的业务逻辑层负责处理系统的核心业务,如药品的添加、修改、删除操作,进货和销售业务的处理等。它接收前端传来的请求,调用相应的数据访问层方法与数据库进行交互,然后将处理结果返回给前端。

数据库采用 MySQL,它是一款开源的关系型数据库管理系统,具有高性能、可靠性和良好的兼容性。在本系统中,MySQL 负责存储系统的所有数据,通过合理的表结构设计和索引优化,确保数据的高效存储和快速查询。系统各层次之间通过 HTTP 协议进行通信,前端发送的请求经过网络传输到后端服务器,后端服务器处理请求后将响应数据返回给前端,实现了系统的前后端交互,如图 4 所示:


@startuml

package "前端(Vue)" as front {

component "用户界面" as ui

component "交互逻辑" as logic

ui -- logic : 交互

}

package "后端(Spring Boot)" as back {

component "控制器层(Controller)" as controller

component "业务逻辑层(Service)" as service

component "数据访问层(Repository)" as repository

controller -- service : 调用业务逻辑

service -- repository : 访问数据

}

package "数据库(MySQL)" as db {

component "数据表" as tables

}

front -- back : HTTP请求与响应

back -- db : SQL语句交互

@enduml

图 4 B/S 架构示意图

4.2 系统功能模块设计

本系统主要包含管理员和员工两种角色,不同角色拥有不同的功能权限。下面以药品管理模块为例,详细说明功能模块的设计与实现。

4.2.1 界面设计

药品管理模块的界面设计遵循简洁、易用的原则。在页面布局上,分为查询区域、操作按钮区域和药品信息展示区域。查询区域提供了多个查询条件输入框,如药品名称、功效、所治疾病等,方便用户根据不同需求进行药品查询;操作按钮区域放置了 “添加药品”“修改药品”“删除药品” 等按钮,用户可以通过点击这些按钮执行相应的操作;药品信息展示区域以表格的形式展示查询到的药品信息,每一行代表一条药品记录,包括药品编号、药品名称、规格、生产厂家、生产日期、有效期、功效、用法用量、价格、库存数量等字段,表格的列头清晰地标识了每个字段的含义,方便用户查看和理解。在界面设计过程中,注重了颜色搭配和字体大小的选择,以提供舒适的视觉体验;同时,对按钮和输入框等元素进行了合理的布局,使其符合用户的操作习惯,提高操作的便捷性。

4.2.2 功能操作

添加药品:管理员点击 “添加药品” 按钮,弹出添加药品的表单模态框。在表单中,管理员依次填写药品的各项信息,如药品名称、规格、生产厂家、生产日期(通过日期选择器选择)、有效期(同样通过日期选择器选择,且系统会自动校验有效期是否大于生产日期)、功效、用法用量、价格、库存数量、药品照片(支持文件上传功能,限制上传文件的格式为常见的图片格式,如 jpg、png 等)等。填写完成后,点击 “保存” 按钮,系统会对输入的信息进行合法性校验,如检查药品名称是否为空、价格是否为正数、库存数量是否为非负整数等。若信息校验通过,系统将药品信息发送到后端服务器进行保存;若校验不通过,系统弹出提示框,告知管理员错误信息,管理员根据提示修改信息后重新提交。

修改药品:在药品信息展示表格中,管理员找到需要修改的药品记录,点击该行对应的 “修改” 按钮,弹出修改药品信息的表单模态框,表单中已经填充了该药品的当前信息。管理员可以对需要修改的字段进行编辑,如修改药品价格、库存数量等。修改完成后,点击 “保存” 按钮,系统同样会进行信息校验,校验通过后将修改后的信息发送到后端服务器进行更新操作;若校验不通过,提示管理员修改错误信息。

删除药品:管理员在药品信息展示表格中勾选需要删除的药品记录,然后点击 “删除” 按钮,系统弹出确认删除的提示框,提示管理员确认是否真的要删除所选药品,以防止误操作。管理员点击 “确定” 按钮后,系统将选中的药品信息发送到后端服务器进行删除操作;若点击 “取消” 按钮,则取消删除操作。

查询药品:用户在查询区域输入查询条件,如在 “药品名称” 输入框中输入药品的部分名称,然后点击 “查询” 按钮。系统将用户输入的查询条件发送到后端服务器,后端服务器根据这些条件在数据库中进行查询,将查询到的药品信息返回给前端,前端将查询结果展示在药品信息展示区域的表格中。同时,系统支持模糊查询,即用户输入的部分名称只要包含在药品名称中,就能查询到相关药品记录。

4.2.3 数据处理

在后端,药品管理模块的数据处理主要通过 Spring Data JPA 实现。Spring Data JPA 是 Spring 框架中用于简化数据库访问的模块,它基于 JPA 规范,提供了统一的接口和实现,使得数据库操作更加方便和高效。

添加药品数据处理:当后端接收到前端发送的添加药品请求时,首先解析请求中的药品信息,将其封装成药品对象(如 Drug 类)。然后,通过 Spring Data JPA 的 Repository 接口将药品对象保存到数据库中。例如,在 DrugRepository 接口中定义了 save 方法,用于保存药品对象,代码示例如下:


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

public interface DrugRepository extends JpaRepository<Drug, Long> {

}

在业务逻辑层(Service 层)中,调用 DrugRepository 的 save 方法将药品信息保存到数据库,代码示例如下:


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Drug;

import com.example.medicals.repository.DrugRepository;

@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public Drug addDrug(Drug drug) {

return drugRepository.save(drug);

}

}

修改药品数据处理:后端接收到修改药品请求后,同样先解析请求中的修改后药品信息,封装成药品对象。然后,根据药品对象的主键(如药品编号)从数据库中查询出原有的药品记录,将修改后的信息更新到原记录中,最后通过 DrugRepository 的 save 方法将更新后的药品对象保存回数据库,实现药品信息的修改。代码示例如下:


@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public Drug updateDrug(Drug drug) {

Drug existingDrug = drugRepository.findById(drug.getId()).orElse(null);

if (existingDrug != null) {

// 更新药品信息

existingDrug.setName(drug.getName());

existingDrug.setSpecification(drug.getSpecification());

// 其他字段更新...

return drugRepository.save(existingDrug);

}

return null;

}

}

删除药品数据处理:当后端接收到删除药品请求时,根据请求中包含的药品主键(如药品编号),通过 DrugRepository 的 deleteById 方法从数据库中删除对应的药品记录。代码示例如下:


@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public void deleteDrug(Long id) {

drugRepository.deleteById(id);

}

}

查询药品数据处理:后端接收到查询药品请求后,根据请求中的查询条件构建查询语句。例如,若用户通过药品名称进行查询,后端会使用 Spring Data JPA 的方法命名查询或自定义查询语句来实现查询功能。若使用方法命名查询,在 DrugRepository 接口中定义如下方法:


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

public interface DrugRepository extends JpaRepository<Drug, Long> {

List<Drug> findByNameContaining(String name);

}

在业务逻辑层中调用该方法进行查询,代码示例如下:


@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public List<Drug> searchDrugs(String name) {

return drugRepository.findByNameContaining(name);

}

}

通过上述界面设计、功能操作和数据处理的协同工作,实现了药品管理模块的增删改查功能,满足了系统对药品信息管理的需求。其他功能模块,如进货管理、销售管理等,也采用类似的设计思路和实现方式,通过合理的界面设计、便捷的功能操作和高效的数据处理,为用户提供了完善的医药管理功能。

4.3 数据库设计

4.3.1 数据库表结构设计

本系统设计了多个数据表,用于存储不同类型的数据,各数据表的结构如下:

药品表(drug):用于存储药品的详细信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 药品唯一标识,自增长 | 主键 |

|name|varchar (100)| 药品名称 | |

|specification|varchar (50)| 药品规格 | |

|manufacturer|varchar (100)| 生产厂家 | |

|production_date|date | 生产日期 | |

|expiry_date|date | 有效期 | |

|efficacy|text | 功效 | |

|usage|text | 用法用量 | |

|price|decimal (10, 2)| 价格 | |

|stock|int | 库存数量 | |

|photo|varchar (200)| 药品照片路径 | |

|drug_type_id|bigint | 药品类型 ID | 外键,关联 drug_type 表的 id 字段 |

供应商表(supplier):存储供应商的相关信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 供应商唯一标识,自增长 | 主键 |

|name|varchar (100)| 供应商名称 | |

|contact_person|varchar (50)| 联系人 | |

|contact_number|varchar (20)| 联系电话 | |

|address|varchar (200)| 地址 | |

|credit_level|varchar (20)| 信用等级 | |

|supplier_type_id|bigint | 供应商类型 ID | 外键,关联 supplier_type 表的 id 字段 |

员工表(employee):记录员工的个人和工作相关信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 员工唯一标识,自增长 | 主键 |

|name|varchar (50)| 员工姓名 | |

|gender|varchar (10)| 性别 | |

|phone|varchar (20)| 手机号码 | |

|position|varchar (50)| 职位 | |

|username|varchar (50)| 登录账号 | |

|password|varchar (100)| 登录密码 | |

进货表(purchase):用于存储药品的进货记录。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 进货记录唯一标识,自增长 | 主键 |

|drug_id|bigint | 药品 ID | 外键,关联 drug 表的 id 字段 |

|supplier_id|bigint | 供应商 ID | 外键,关联 supplier 表的 id 字段 |

|purchase_date|date | 进货日期 | |

|quantity|int | 进货数量 | |

|unit_price|decimal (10, 2)| 进货单价 | |

销售表(sale):记录药品的销售信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 销售记录唯一标识,自增长 | 主键 |

|drug_id|bigint | 药品 ID | 外键,关联 drug 表的 id 字段 |

|sale_date|date | 销售日期 | |

|quantity|int | 销售数量 | |

|unit_price|decimal (10, 2)| 销售单价 | |

|employee_id|bigint | 销售人员 ID | 外键,关联 employee 表的 id 字段 |

4.3.2 数据库关系设计

通过绘制 E-R 图(Entity – Relationship Diagram)来展示各数据表之间的关系,如图 5 所示:


@startuml

entity "药品(drug)" as drug {

*id : bigint

name : varchar(100)

specification : varchar(50)

manufacturer : varchar(100)

production_date : date

expiry_date : date

efficacy : text

usage : text

price : decimal(10, 2)

stock : int

photo : varchar(200)

-- 外键

*drug_type_id : bigint

}

entity "供应商(supplier)" as supplier {

*id : bigint

name : varchar(100)

contact_person : varchar(50)

contact_number : varchar(20)

address : varchar(200)

credit_level : varchar(20)

-- 外键

*supplier_type_id : bigint

}

entity "员工(employee)" as employee {

*id : bigint

name : varchar(50)

gender : varchar(10)

phone : varchar(20)

position : varchar(50)

username : varchar(50)

password : varchar(100)

}

entity "进货(purchase)" as purchase {

*id : bigint

-- 外键

*drug_id : bigint

-- 外键

*supplier_id : bigint

purchase_date : date

quantity : int

unit_price : decimal(10, 2)

}

entity "销售(sale)" as sale {

*id : bigint

-- 外键

*drug_id : bigint

sale_date : date

quantity : int

unit_price : decimal(10, 2)

-- 外键

*employee_id : bigint

}

drug "1" -- "n" purchase : 一种药品有多次进货记录

supplier "1" -- "n" purchase : 一个供应商供应多种药品的进货

drug "1" -- "n" sale : 一种药品有多次销售记录

employee "1" -- "n" sale : 一个员工进行多次销售操作

@enduml

图 5 数据库 E-R 图

在 E-R 图中,药品与供应商通过进货表建立关联关系,一个供应商可以供应多种药品的进货,一种药品也可以从多个供应商进货;药品与销售表存在一对多的关系,即一种药品可以有多次销售记录;员工与销售表同样是一对多的关系,一个员工可以进行多次销售操作。通过这种关系设计,能够准确地反映医药管理业务中的数据关联,为系统的功能实现提供了坚实的数据基础,确保了数据的完整性和一致性 。在实际数据库操作中,通过外键约束来维护这些关系,保证数据的正确性和可靠性。例如,在进货表中,drug_id 和 supplier_id 作为外键,分别关联药品表和供应商表的主键,当进行进货操作时,系统会校验关联的药品和供应商是否存在,若不存在则不允许进行进货记录的插入,从而避免了数据的不一致性问题。

五、系统实现

5.1 开发环境搭建

JDK 安装与配置:首先,从 Oracle 官方网站下载适合系统的 JDK 安装包,例如对于 Windows 系统,下载对应的 Windows x64 Installer。下载完成后,双击安装包进行安装,安装过程中可以选择默认安装路径,也可自定义安装目录。安装完成后,需要配置环境变量。在系统环境变量中,新建一个名为 “JAVA_HOME” 的变量,变量值为 JDK 的安装路径,如 “C:Program FilesJavajdk1.8.0_361”。然后,在 “Path” 变量中添加 “% JAVA_HOME%in” 和 “% JAVA_HOME%jrein”,确保系统能够找到 Java 的可执行文件。最后,打开命令提示符,输入 “java -version”,若能正确显示 JDK 版本信息,则说明 JDK 安装与配置成功。

开发工具 IDEA 安装与配置:从 JetBrains 官网下载 IntelliJ IDEA 安装包,根据系统选择对应的版本,如 Windows 系统下载.exe 格式的安装包。下载后,双击安装包开始安装,安装过程中按照提示逐步进行操作,可选择安装路径、关联文件类型等。安装完成后,首次启动 IDEA,会进行一些初始化设置,如选择主题、配置插件等。在配置插件时,可以根据项目需求安装相关插件,如 Maven Helper、Lombok 等。接着,需要配置 JDK 路径,在 “File” -> “Project Structure” 中,找到 “SDKs” 选项,点击 “+” 按钮,选择之前安装的 JDK 目录,完成 JDK 配置。

Maven 安装与配置:从 Maven 官网(Download Apache Maven – Maven)下载 Maven 的二进制压缩包,下载完成后解压到指定目录,如 “D:apache-maven-3.9.6”。解压完成后,配置环境变量,在系统环境变量中新建 “MAVEN_HOME” 变量,变量值为 Maven 的解压路径 “D:apache-maven-3.9.6”。然后,在 “Path” 变量中添加 “% MAVEN_HOME%in”,使系统能够识别 Maven 命令。接下来,打开 Maven 安装目录下的 “conf” 文件夹,编辑 “settings.xml” 文件,配置本地仓库路径,例如在 “settings.xml” 文件中找到 “localRepository” 标签,修改其值为 “D:maven
epository”(自定义的本地仓库路径)。同时,为了加快依赖下载速度,可以配置镜像,在 “mirrors” 标签内添加阿里云镜像配置:


<mirror>

<id>aliyunmaven</id>

<mirrorOf>central</mirrorOf>

<name>阿里云公共仓库</name>

<url>https://maven.aliyun.com/repository/central</url>

</mirror>

配置完成后,打开命令提示符,输入 “mvn -version”,若能正确显示 Maven 版本信息,则说明 Maven 安装与配置成功。

Tomcat 安装与配置:从 Apache Tomcat 官网(https://tomcat.apache.org/download-90.cgi)下载 Tomcat 安装包,选择合适的版本,如 Tomcat 9。对于 Windows 系统,可下载.zip 格式的免安装版。下载完成后,解压到指定目录,如 “D:apache-tomcat-9.0.75”。解压完成后,配置环境变量,在系统环境变量中新建 “CATALINA_HOME” 变量,变量值为 Tomcat 的解压路径 “D:apache-tomcat-9.0.75”。然后,在 “Path” 变量中添加 “% CATALINA_HOME%in”。配置完成后,打开命令提示符,进入 Tomcat 的 “bin” 目录,输入 “startup.bat” 启动 Tomcat,若能成功启动,并在浏览器中访问 “http://localhost:8080/” 出现 Tomcat 欢迎页面,则说明 Tomcat 安装与配置成功。若端口号 8080 被占用,可以修改 Tomcat 的端口号,在 Tomcat 安装目录下的 “conf” 文件夹中,找到 “server.xml” 文件,修改其中的 “Connector” 标签的 “port” 属性值,如将其改为 “8081”。

5.2 关键功能模块的代码实现

5.2.1 药品管理模块

添加药品功能代码实现:在后端,通过 Spring Data JPA 实现药品信息的保存。首先,定义药品实体类 Drug,使用 JPA 的注解标注实体和字段映射关系。


import javax.persistence.Entity;

import javax.persistence.GeneratedValue;

import javax.persistence.GenerationType;

import javax.persistence.Id;

@Entity

public class Drug {

@Id

@GeneratedValue(strategy = GenerationType.IDENTITY)

private Long id;

private String name;

private String specification;

private String manufacturer;

private String productionDate;

private String expiryDate;

private String efficacy;

private String usage;

private BigDecimal price;

private Integer stock;

private String photo;

// 其他属性及getter、setter方法

}

然后,定义 DrugRepository 接口,继承自 JpaRepository,利用 Spring Data JPA 的自动实现功能。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

public interface DrugRepository extends JpaRepository<Drug, Long> {

}

在 DrugService 中实现添加药品的业务逻辑,调用 DrugRepository 的 save 方法保存药品信息。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Drug;

import com.example.medicals.repository.DrugRepository;

@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public Drug addDrug(Drug drug) {

return drugRepository.save(drug);

}

}

在前端,使用 Vue 组件实现添加药品的界面交互。通过表单收集用户输入的药品信息,利用 Axios 库将数据发送到后端。


<template>

<div>

<h2>添加药品</h2>

<form @submit.prevent="addDrug">

<label>药品名称:</label>

<input v-model="drug.name" type="text" required><br>

<!-- 其他表单字段 -->

<button type="submit">保存</button>

</form>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

drug: {

name: '',

specification: '',

// 其他属性初始值

}

};

},

methods: {

addDrug() {

axios.post('/drugs', this.drug)

.then(response => {

console.log('药品添加成功', response.data);

// 其他操作,如清空表单、提示用户等

})

.catch(error => {

console.error('药品添加失败', error);

});

}

}

};

</script>

查询药品功能代码实现:在后端,DrugRepository 中定义根据药品名称模糊查询的方法。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

import java.util.List;

public interface DrugRepository extends JpaRepository<Drug, Long> {

List<Drug> findByNameContaining(String name);

}

在 DrugService 中调用该方法实现查询逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Drug;

import com.example.medicals.repository.DrugRepository;

import java.util.List;

@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public List<Drug> searchDrugs(String name) {

return drugRepository.findByNameContaining(name);

}

}

在前端,通过表单输入查询条件,调用后端接口获取查询结果并展示。


<template>

<div>

<h2>查询药品</h2>

<form @submit.prevent="searchDrugs">

<label>药品名称:</label>

<input v-model="searchName" type="text"><br>

<button type="submit">查询</button>

</form>

<table>

<thead>

<tr>

<th>药品名称</th>

<th>规格</th>

<!-- 其他表头字段 -->

</tr>

</thead>

<tbody>

<tr v-for="drug in drugs" :key="drug.id">

<td>{
{ drug.name }}</td>

<td>{
{ drug.specification }}</td>

<!-- 其他表格数据 -->

</tr>

</tbody>

</table>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

searchName: '',

drugs: []

};

},

methods: {

searchDrugs() {

axios.get('/drugs/search', { params: { name: this.searchName } })

.then(response => {

this.drugs = response.data;

})

.catch(error => {

console.error('查询药品失败', error);

});

}

}

};

</script>

修改和删除药品功能的实现思路与上述类似,在后端通过 DrugRepository 和 DrugService 实现业务逻辑,在前端通过 Vue 组件和 Axios 库实现用户交互和数据传输。

5.2.2 进货管理模块

进货信息录入功能代码实现:在后端,定义进货实体类 Purchase,映射进货表结构。


import javax.persistence.Entity;

import javax.persistence.GeneratedValue;

import javax.persistence.GenerationType;

import javax.persistence.Id;

import javax.persistence.ManyToOne;

@Entity

public class Purchase {

@Id

@GeneratedValue(strategy = GenerationType.IDENTITY)

private Long id;

@ManyToOne

private Drug drug;

@ManyToOne

private Supplier supplier;

private String purchaseDate;

private Integer quantity;

private BigDecimal unitPrice;

// 其他属性及getter、setter方法

}

定义 PurchaseRepository 接口继承 JpaRepository。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Purchase;

public interface PurchaseRepository extends JpaRepository<Purchase, Long> {

}

在 PurchaseService 中实现进货信息保存逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Purchase;

import com.example.medicals.repository.PurchaseRepository;

@Service

public class PurchaseService {

@Autowired

private PurchaseRepository purchaseRepository;

public Purchase addPurchase(Purchase purchase) {

return purchaseRepository.save(purchase);

}

}

在前端,通过 Vue 组件的表单收集进货信息,发送到后端。


<template>

<div>

<h2>新增进货</h2>

<form @submit.prevent="addPurchase">

<label>药品:</label>

<select v-model="purchase.drug.id" required>

<option v-for="drug in drugs" :value="drug.id">{
{ drug.name }}</option>

</select><br>

<!-- 其他表单字段,如供应商、进货日期、数量、单价等 -->

<button type="submit">保存</button>

</form>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

purchase: {

drug: {},

supplier: {},

purchaseDate: '',

quantity: 0,

unitPrice: 0

},

drugs: []

};

},

created() {

this.getDrugs();

},

methods: {

getDrugs() {

axios.get('/drugs')

.then(response => {

this.drugs = response.data;

})

.catch(error => {

console.error('获取药品列表失败', error);

});

},

addPurchase() {

axios.post('/purchases', this.purchase)

.then(response => {

console.log('进货信息添加成功', response.data);

// 其他操作,如清空表单、提示用户等

})

.catch(error => {

console.error('进货信息添加失败', error);

});

}

}

};

</script>

进货信息查询功能代码实现:在后端,PurchaseRepository 中可定义根据进货日期范围查询进货信息的方法。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Purchase;

import java.util.List;

public interface PurchaseRepository extends JpaRepository<Purchase, Long> {

List<Purchase> findByPurchaseDateBetween(String startDate, String endDate);

}

在 PurchaseService 中调用该方法实现查询逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Purchase;

import com.example.medicals.repository.PurchaseRepository;

import java.util.List;

@Service

public class PurchaseService {

@Autowired

private PurchaseRepository purchaseRepository;

public List<Purchase> searchPurchases(String startDate, String endDate) {

return purchaseRepository.findByPurchaseDateBetween(startDate, endDate);

}

}

在前端,通过表单输入查询条件,调用后端接口获取查询结果并展示。


<template>

<div>

<h2>查询进货信息</h2>

<form @submit.prevent="searchPurchases">

<label>开始日期:</label>

<input v-model="startDate" type="date"><br>

<label>结束日期:</label>

<input v-model="endDate" type="date"><br>

<button type="submit">查询</button>

</form>

<table>

<thead>

<tr>

<th>药品名称</th>

<th>供应商</th>

<th>进货日期</th>

<th>数量</th>

<th>单价</th>

</tr>

</thead>

<tbody>

<tr v-for="purchase in purchases" :key="purchase.id">

<td>{
{ purchase.drug.name }}</td>

<td>{
{ purchase.supplier.name }}</td>

<td>{
{ purchase.purchaseDate }}</td>

<td>{
{ purchase.quantity }}</td>

<td>{
{ purchase.unitPrice }}</td>

</tr>

</tbody>

</table>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

startDate: '',

endDate: '',

purchases: []

};

},

methods: {

searchPurchases() {

axios.get('/purchases/search', { params: { startDate: this.startDate, endDate: this.endDate } })

.then(response => {

this.purchases = response.data;

})

.catch(error => {

console.error('查询进货信息失败', error);

});

}

}

};

</script>

进货信息审核功能可通过在 Purchase 实体类中添加审核状态字段,在后端实现审核逻辑,前端实现审核操作的交互。

5.2.3 销售管理模块

销售信息录入功能代码实现:在后端,定义销售实体类 Sale,映射销售表结构。


import javax.persistence.Entity;

import javax.persistence.GeneratedValue;

import javax.persistence.GenerationType;

import javax.persistence.Id;

import javax.persistence.ManyToOne;

@Entity

public class Sale {

@Id

@GeneratedValue(strategy = GenerationType.IDENTITY)

private Long id;

@ManyToOne

private Drug drug;

private String saleDate;

private Integer quantity;

private BigDecimal unitPrice;

@ManyToOne

private Employee employee;

// 其他属性及getter、setter方法

}

定义 SaleRepository 接口继承 JpaRepository。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Sale;

public interface SaleRepository extends JpaRepository<Sale, Long> {

}

在 SaleService 中实现销售信息保存逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Sale;

import com.example.medicals.repository.SaleRepository;

@Service

public class SaleService {

@Autowired

private SaleRepository saleRepository;

public Sale addSale(Sale sale) {

return saleRepository.save(sale);

}

}

在前端,通过 Vue 组件的表单收集销售信息,发送到后端。


<template>

<div>

<h2>新增销售</h2>

<form @submit.prevent="addSale">

<label>药品:</label>

<select v-model="sale.drug.id" required>

<option v-for="drug in drugs" :value="drug.id">{
{ drug.name }}</option>

</select><br>

<!-- 其他表单字段,如销售日期、数量、单价、销售人员等 -->

<button type="submit">保存</button>

</form>

</div>

</

## 六、系统测试

### 6.1 测试目的

系统测试是软件开发过程中的重要环节,对于基于Spring Boot的医药管理系统而言,其测试目的具有多方面的重要性。首要目标是验证系统功能的正确性,确保系统实现了需求分析阶段所确定的各项功能。例如,在药品管理模块,要确认添加药品功能能够准确无误地将药品信息保存到数据库中,修改和删除功能也能按照预期对药品数据进行相应操作;进货管理和销售管理模块中的进货和销售记录添加、查询等功能也需准确实现,保证业务流程的顺畅进行。

性能方面,测试系统是否满足性能需求是关键。要检测系统在不同负载情况下的响应时间、吞吐量等指标,以确定系统是否能够在正常业务量和高并发情况下稳定运行,满足实际使用中的性能要求。比如,在多个用户同时进行药品查询或销售操作时,系统应能在规定的时间内响应,不出现卡顿或超时现象。

同时,测试还需排查系统是否存在漏洞,包括安全漏洞和逻辑漏洞等。安全漏洞方面,要检查系统是否存在SQL注入、XSS攻击等安全隐患,确保药品信息和用户数据的安全性;逻辑漏洞则关注系统业务逻辑的合理性,例如进货和销售操作中的库存更新逻辑是否正确,避免出现库存数量异常的情况。通过全面的测试,及时发现并解决这些问题,从而提高系统的质量和可靠性,为用户提供稳定、安全、高效的医药管理服务 。

### 6.2 测试方法

本系统主要采用黑盒测试和白盒测试相结合的方法进行测试。黑盒测试是在不考虑系统内部结构和实现细节的情况下,仅依据系统的需求规格说明书,对系统的功能进行测试。例如,在测试药品查询功能时,测试人员只需在前端输入不同的查询条件(如药品名称、功效等),观察系统返回的查询结果是否正确,而无需了解后端的查询实现逻辑。通过黑盒测试,可以验证系统的功能是否符合用户需求,检查系统的输入与输出是否正确对应。

白盒测试则是基于系统内部的代码结构和逻辑,对系统的内部操作进行测试。在本系统中,对于一些关键的业务逻辑方法,如药品库存更新方法、进货和销售业务处理方法等,采用白盒测试。测试人员可以查看代码实现,设计测试用例来覆盖不同的代码路径和分支,确保代码的正确性和健壮性。例如,在测试药品库存更新方法时,通过编写不同的测试数据,验证在各种情况下(如正常进货、销售,以及特殊情况如库存为零、负数等)库存更新逻辑是否正确,以保证系统内部逻辑的准确性。

### 6.3 测试用例设计

#### 6.3.1 药品管理模块

|测试用例编号|测试场景|输入数据|预期输出|测试步骤|

|----|----|----|----|----|

|1|添加药品|药品名称:感冒灵颗粒;规格:10g*9袋;生产厂家:XX制药;生产日期:2024-01-01;有效期:2025-01-01;功效:解热镇痛;用法用量:开水冲服,一次10克,一日3次;价格:15.00;库存数量:100;药品照片:无;药品类型ID:1|提示药品添加成功,数据库中新增一条药品记录|1. 登录系统,进入药品管理模块。2. 点击“添加药品”按钮,填写上述输入数据。3. 点击“保存”按钮|

|2|修改药品|药品ID:1(已存在的药品);修改后价格:16.00|提示药品修改成功,数据库中对应药品记录的价格更新为16.00|1. 进入药品管理模块,查询出ID为1的药品。2. 点击“修改”按钮,修改价格为16.00。3. 点击“保存”按钮|

|3|删除药品|药品ID:1(已存在的药品)|提示药品删除成功,数据库中对应药品记录被删除|1. 进入药品管理模块,查询出ID为1的药品。2. 勾选该药品,点击“删除”按钮。3. 在弹出的确认框中点击“确定”|

|4|查询药品|药品名称:感冒灵|显示名称包含“感冒灵”的药品记录|1. 进入药品管理模块,在查询框中输入“感冒灵”。2. 点击“查询”按钮|

#### 6.3.2 进货管理模块

|测试用例编号|测试场景|输入数据|预期输出|测试步骤|

|----|----|----|----|----|

|5|新增进货|药品ID:1;供应商ID:1;进货日期:2024-05-01;进货数量:50;进货单价:10.00|提示进货信息添加成功,数据库中新增一条进货记录,对应药品库存增加50|1. 登录系统,进入进货管理模块。2. 点击“新增进货”按钮,填写上述输入数据。3. 点击“保存”按钮|

|6|查询进货|进货日期范围:2024-05-01至2024-05-31|显示该时间段内的进货记录|1. 进入进货管理模块,在查询条件中选择进货日期范围为2024-05-01至2024-05-31。2. 点击“查询”按钮|

#### 6.3.3 销售管理模块

|测试用例编号|测试场景|输入数据|预期输出|测试步骤|

|----|----|----|----|----|

|7|新增销售|药品ID:1;销售日期:2024-05-02;销售数量:10;销售单价:20.00;员工ID:1|提示销售信息添加成功,数据库中新增一条销售记录,对应药品库存减少10|1. 登录系统,进入销售管理模块。2. 点击“新增销售”按钮,填写上述输入数据。3. 点击“保存”按钮|

|8|查询销售|销售日期:2024-05-02|显示该日期的销售记录|1. 进入销售管理模块,在查询条件中输入销售日期为2024-05-02。2. 点击“查询”按钮|

### 6.4 测试结果分析

经过对各个功能模块的测试,大部分测试用例都顺利通过,系统的主要功能基本符合设计要求。在药品管理模块中,添加、修改、删除和查询药品功能均能正确执行,数据的保存和查询准确无误;进货管理模块的进货信息添加和查询功能正常,库存更新逻辑正确;销售管理模块的销售信息添加和查询功能也能正常工作,库存更新也符合预期。

然而,在测试过程中也发现了一些问题。例如,在高并发情况下进行进货和销售操作时,偶尔会出现库存数据更新不一致的情况。经过分析,发现是由于并发操作时对数据库的事务处理不当导致的。针对这个问题,通过在相关业务方法上添加事务注解,确保了事务的原子性,解决了库存数据更新不一致的问题。

## 七、总结与展望

### 7.1 系统总结

本基于Spring Boot的医药管理系统,从设计到实现经历了多个关键阶段。在设计阶段,通过全面的需求分析,明确了系统的功能需求、性能需求以及操作流程,为后续的开发工作奠定了坚实基础。采用B/S架构,结合Spring Boot框架、Vue前端技术和MySQL数据库进行系统架构设计,确保了系统的稳定性、可扩展性和高效性。在功能模块设计方面,详细规划了药品管理、进货管理、销售管理等核心模块,每个模块都具备清晰的功能和操作流程,满足了不同用户角色(管理员和员工)的使用需求。

在实现阶段,搭建了完善的开发环境,包括JDK、IDEA、Maven和Tomcat等工具的安装与配置。通过编写后端的Java代码,利用Spring Data JPA实现了与MySQL数据库的交互,完成了各个功能模块的业务逻辑实现;前端使用Vue框架和Axios库,实现了友好的用户界面和数据传输功能。经过全面的系统测试,验证了系统功能的正确性和稳定性,大部分测试用例顺利通过,系统能够满足医药管理的基本业务需求。

系统具有以下特点:功能全面,涵盖了医药管理的各个关键环节,包括药品信息管理、进货销售管理等,能够为医药企业提供一站式的管理服务;操作便捷,界面设计简洁明了,操作流程符合用户习惯,即使是非专业人员也能快速上手使用;数据安全可靠,采用了身份认证、授权管理和数据加密等安全措施,保障了药品信息和用户数据的安全性和完整性;系统扩展性良好,基于Spring Boot框架的设计,方便后续对系统进行功能扩展和升级,以适应不断变化的业务需求。

总体而言,本系统达到了预期目标,实现了对医药信息的高效管理,提高了医药管理的工作效率,降低了管理成本,为医药企业的信息化建设提供了有效的解决方案。

### 7.2 未来展望

随着医疗行业的不断发展和信息技术的持续进步,本医药管理系统还有很大的发展空间。在性能优化方面,可以进一步对系统进行性能测试和调优,采用缓存技术(如Redis)减少数据库的访问次数,提高系统的响应速度;优化数据库查询语句和索引,提升数据查询的效率;对系统进行分布式部署,提高系统的并发处理能力,以满足业务量不断增长的需求。

在功能扩展方面,可以增加药品溯源功能,通过扫码等方式实现药品从生产到销售的全过程追溯,提高药品质量监管水平;引入智能预警功能,根据药品库存、有效期等信息,自动发出预警提醒,避免药品过期和库存不足的情况发生;开发移动端应用,方便员工随时随地进行业务操作,提高工作的灵活性和便捷性;集成数据分析功能,对药品销售数据、进货数据等进行深入分析,为企业的决策提供数据支持,如制定采购计划、优化销售策略等。

在技术更新方面,关注新技术的发展趋势,适时引入新的技术和框架,如微服务架构,将系统拆分成多个独立的微服务,提高系统的可维护性和可扩展性;采用云计算技术,将系统部署到云端,降低硬件成本和运维难度,提高系统的可用性和可靠性。通过不断地优化和升级,使本医药管理系统能够更好地适应医疗行业的发展需求,为医药企业提供更优质、高效的管理服务。

## 致谢

在完成基于Spring Boot的医药管理系统毕业设计的过程中,我得到了许多人的帮助,心中满是感激。

我要衷心感谢我的指导教师。从系统的选题到设计方案的敲定,再到代码实现和论文撰写的每一个环节,老师都给予了我悉心的指导和耐心的帮助。老师严谨的治学态度、渊博的专业知识和丰富的实践经验,使我在遇到问题时总能得到及时且准确的建议,为我指明了前进的方向。在我因技术难题而陷入困境时,老师鼓励我勇于探索,引导我从不同角度思考问题,让我不断突破自我。没有老师的引领,我难以顺利完成这个项目,师恩难忘,我将铭记于心。

同时,我也不会忘记我的同学们。在项目开发过程中,我们相互交流、共同探讨,分享各自的经验和见解。当我在代码编写中遇到逻辑问题时,同学们积极为我出谋划策,帮我理清思路;在系统测试阶段,大家一起进行测试用例的设计和执行,共同找出并解决了许多潜在的问题。我们在学习和实践中相互激励、共同进步,同窗之情让这段经历变得更加珍贵。

我最应该感谢的,还有我的家人。他们一直是我最坚强的后盾,给予我无条件的支持和鼓励。在我为了完成毕业设计而日夜忙碌时,家人默默承担了生活中的琐事,让我能够全身心地投入到学习和工作中。他们的关爱和信任,是我不断前行的动力,每当我遇到困难想要放弃时,想到家人的期望,我便又充满了斗志。

在此,我向所有帮助过我的人表示最诚挚的感谢!感谢你们在我成长道路上的陪伴和支持,这份情谊我将永远珍惜 。

一、引言

在医疗卫生行业持续发展与人们健康意识日益提升的背景下,医药管理在医疗机构和药店运营中占据着愈发关键的地位。传统的医药管理方式,主要依赖人工记录和纸质文件,在实际操作中暴露出众多弊端。比如,手工记录容易出现笔误、数据遗漏等人为失误,导致药品信息的不准确,进而可能影响到患者的治疗效果;数据共享和实时查询困难,不同部门之间难以快速获取所需信息,严重阻碍了工作流程的顺畅进行,降低了工作效率;缺乏统一的管理平台,使得各部门之间协作效率低下,无法形成有效的合力,难以应对复杂多变的业务需求;难以及时掌握药品库存和流向情况,容易造成库存积压或缺货现象,不仅增加了运营成本,还可能延误患者的救治时机。

随着信息技术的飞速发展,开发一套高效、智能的医药管理系统已成为提升医药管理水平的迫切需求。Spring Boot 作为 Java 领域一款优秀的框架,以其快速开发、易于部署及集成多种开源技术的优势,成为构建医药管理系统的理想选择。它能够帮助我们快速搭建稳定、可扩展的 Web 应用,有效解决传统管理方式中的诸多问题,实现药品从采购、库存、销售到患者用药跟踪的全链条信息化管理,提升医药企业的运营效率,增强药品质量追溯能力,为保障患者用药安全提供有力支持。

二、相关技术介绍

2.1 Spring Boot 框架

Spring Boot 是基于 Spring 框架的全新框架,其设计目的是简化 Spring 应用的初始搭建及开发过程。它采用 “约定优于配置” 的理念,大幅减少了项目开发过程中的 XML 配置和代码编写量,开发者能够将更多的精力投入到业务逻辑的实现上 。

在快速开发方面,Spring Boot 提供了丰富的 “开箱即用” 特性,通过一系列的启动器(Starters),可快速集成各种常用功能,如数据库连接、消息传递、缓存等。例如,在本医药管理系统中,使用 Spring Boot 的 Spring Data JPA 启动器,能够轻松实现与 MySQL 数据库的交互,无需繁琐地编写大量的数据库连接和操作代码。

其内嵌服务器(如 Tomcat、Jetty 等)的特性,使得应用程序可以独立运行,无需外部服务器的支持。在部署医药管理系统时,只需使用 “java -jar” 命令即可启动应用,极大地简化了部署流程,提高了部署效率,降低了运维成本。

Spring Boot 拥有庞大且活跃的生态系统,这意味着在开发过程中遇到问题时,能够轻松地在社区中找到解决方案和相关资源。同时,它与众多常用框架和库(如 Spring Security、Spring Data 等)有着良好的集成,为系统的开发和扩展提供了强大的支持,使系统具备更高的稳定性和可维护性。

2.2 Java 语言

Java 是一种高级的面向对象编程语言,由 Sun Microsystems 公司于 1995 年推出。它具有诸多特性,使其非常适合用于开发医药管理系统。

Java 的面向对象特性,允许开发者将现实世界中的实体抽象为类,通过类与类之间的关系来构建复杂的系统。在医药管理系统中,可以将药品、供应商、患者、医护人员等都抽象为类,每个类封装其相关的属性和行为。例如,药品类可以包含药品名称、规格、生产日期、有效期、功效等属性,以及入库、出库、查询库存等行为,这种方式使得代码结构更加清晰,易于理解和维护。

Java 具有 “一次编写,到处运行” 的跨平台特性,这得益于 Java 虚拟机(JVM)。编写好的 Java 程序会被编译成字节码,字节码可以在任何安装了 JVM 的操作系统上运行,无论是 Windows、Linux 还是 Mac OS 等。对于医药管理系统而言,这意味着系统可以轻松地部署在不同的服务器环境中,满足不同医疗机构的多样化需求,而无需针对不同操作系统进行大量的代码修改。

安全性是 Java 语言的重要特性之一。Java 在编译和运行时进行严格的类型检查,消除了许多潜在的类型不匹配问题;它不支持指针,避免了因指针操作不当而导致的内存安全问题;提供了完善的异常处理机制,能够有效地捕获和处理程序运行过程中出现的异常情况,保证系统的稳健运行。在医药管理系统中,涉及大量敏感的医疗数据,Java 的这些安全特性能够确保数据的安全性和完整性,防止数据泄露和非法篡改,为患者的隐私保护提供有力保障。

此外,Java 拥有丰富的类库,涵盖了网络通信、文件处理、图形界面等各个方面,为开发者提供了便捷的开发工具。在开发医药管理系统时,可以直接使用这些类库中的功能,减少重复开发,提高开发效率。

2.3 MySQL 数据库

MySQL 是一款开源的关系型数据库管理系统,凭借其众多优点,在医药数据存储方面展现出显著优势。

开源特性使得 MySQL 的使用成本极低,医疗机构无需支付高昂的软件授权费用,降低了信息化建设的成本。同时,开源社区活跃,开发者可以获取大量的技术支持和资源,方便解决使用过程中遇到的问题。

MySQL 具有高性能和可靠性。它采用了优化的存储引擎,如 InnoDB 和 MyISAM,能够根据不同的应用场景选择最合适的存储方式,提供高效的数据读写性能。在医药管理系统中,需要频繁地对药品信息、患者信息、销售记录等进行查询和更新操作,MySQL 能够快速响应这些请求,确保系统的高效运行。其具备完善的事务处理和数据恢复机制,能够保证数据的完整性和一致性,即使在系统出现故障的情况下,也能最大程度地恢复数据,保障医药业务的连续性。

MySQL 支持多种操作系统,如 Windows、Linux 等,具有良好的兼容性,能够与使用不同操作系统的服务器无缝集成。并且,它可以轻松地进行扩展,无论是增加存储容量还是提升处理能力,都能通过简单的配置调整或硬件升级来实现,以满足医药管理系统随着业务发展而不断增长的数据存储和处理需求。

2.4 其他技术(如前端技术 Vue 等)

在本医药管理系统中,前端采用了 Vue 框架进行开发。Vue 是一款轻量级的 JavaScript 框架,专注于构建用户界面。

Vue 具有简洁易用的特点,其语法简单直观,易于上手,开发者能够快速掌握并运用到项目中。在构建医药管理系统的前端界面时,Vue 的模板语法使得 HTML 和 JavaScript 代码的结合更加自然流畅,能够方便地实现数据的绑定和渲染。例如,通过简单的指令,就可以将从后端获取的药品信息动态地展示在页面上,实现数据与界面的实时同步。

它采用组件化的开发模式,将整个页面拆分成一个个独立的组件,每个组件都有自己的逻辑和样式,提高了代码的复用性和可维护性。在医药管理系统中,像药品列表展示组件、用户登录组件、订单管理组件等,都可以独立开发和维护,当某个组件需要修改或升级时,不会影响到其他组件的正常运行,大大降低了开发和维护的难度。

Vue 还拥有丰富的插件和工具,能够方便地实现各种交互功能。例如,结合 Element – UI 插件,可以快速构建出美观、功能强大的用户界面,提供丰富的组件库,如表格、表单、弹窗等,满足医药管理系统中各种业务场景的交互需求;使用 Axios 库进行数据请求,能够轻松地与后端的 Spring Boot 应用进行数据通信,实现数据的获取、提交和更新等操作,为用户提供流畅的交互体验。

三、系统需求分析

3.1 可行性分析

技术可行性:本系统采用 Spring Boot 框架进行后端开发,利用其强大的依赖管理和自动配置功能,能够快速搭建稳定的后端服务,大大提高开发效率。结合 Java 语言的跨平台性、面向对象特性以及丰富的类库,为系统的功能实现提供了坚实的技术基础。前端使用 Vue 框架,其简洁的语法和组件化开发模式,使得构建交互性强、用户体验良好的界面变得更加容易。MySQL 数据库以其开源、高性能、可靠性以及良好的兼容性,能够满足系统对数据存储和管理的需求。开发团队成员具备相关技术的学习和实践经验,能够熟练运用这些技术进行系统开发,因此在技术层面上,本系统的开发是可行的。

操作可行性:系统在设计时充分考虑了用户体验,界面布局简洁明了,操作流程符合用户的日常习惯。对于管理员和员工角色,系统提供了直观的操作界面,各类功能按钮和菜单易于查找和点击。例如,在药品管理模块,管理员可以通过简单的表单填写完成药品信息的添加、修改和删除操作;员工在进行进货和销售操作时,系统会给出清晰的提示和引导,确保操作的准确性。即使是非专业技术人员,经过简单的培训也能快速上手使用本系统,保证了系统的操作可行性。

经济可行性:开发本医药管理系统主要的成本在于开发人员的人力成本以及开发过程中使用的一些软件工具和服务器资源。Spring Boot、Vue、MySQL 等技术均为开源免费的,无需支付额外的软件授权费用。服务器可以选择租用云服务器,根据实际使用情况灵活选择配置和计费方式,成本相对较低。而系统开发完成后,能够显著提高医药管理的效率,减少人工成本和因管理不善导致的药品损耗,为企业带来更大的经济效益。从长远来看,系统的投入产出比是可观的,因此在经济上是可行的。

法律可行性:在系统开发过程中,所使用的技术和工具均遵循开源协议和相关法律法规,不存在侵权行为。系统开发团队保证所有代码均为自主编写,不存在抄袭和盗用他人代码的情况。同时,系统在设计和实现过程中,严格遵守药品管理相关的法律法规,如药品经营质量管理规范(GSP)等,确保药品信息的安全性、准确性和合规性,保障患者的合法权益。因此,本系统在法律层面是可行的。

3.2 系统性能需求分析

响应时间:系统应具备快速响应能力,对于用户的各类操作请求,如查询药品信息、提交进货或销售订单等,在正常网络环境下,平均响应时间应不超过 3 秒 ,确保用户能够及时获得操作结果,提高工作效率。在高并发情况下,如多个员工同时进行销售操作时,系统的响应时间也应控制在可接受范围内,最大响应时间不超过 5 秒,以避免用户等待时间过长而影响使用体验。

吞吐量:系统需要满足一定的业务吞吐量要求,能够支持同时处理多个并发请求。根据预估的业务量,系统应能够支持至少 50 个并发用户同时在线操作,保证在业务高峰期,如医院或药店的繁忙时段,系统仍能稳定运行,不出现卡顿或崩溃现象。随着业务的发展,系统应具备良好的扩展性,能够方便地进行性能优化和升级,以满足不断增长的吞吐量需求。

可靠性:医药管理系统涉及到大量重要的药品信息和业务数据,因此系统必须具备高度的可靠性。系统应采用可靠的技术架构和设计模式,确保在硬件故障、网络异常等情况下,数据的完整性和一致性不受影响。例如,采用数据库备份和恢复机制,定期对数据进行备份,当出现数据丢失或损坏时,能够及时恢复到最近的可用状态;使用事务处理机制,保证业务操作的原子性,避免因部分操作失败而导致数据不一致的问题。系统的可靠性指标应达到 99.9% 以上,确保业务的连续性和稳定性。

可维护性:为了便于系统的后续维护和升级,系统在设计时应遵循良好的软件设计原则,采用模块化、分层架构,使代码结构清晰,各模块之间的耦合度低。每个模块应具有明确的功能和职责,方便开发人员进行代码的修改和扩展。同时,系统应具备完善的日志记录功能,记录系统运行过程中的关键事件和错误信息,以便在出现问题时能够快速定位和解决。开发过程中应编写详细的技术文档,包括需求文档、设计文档、使用手册等,为系统的维护和升级提供有力支持。

安全性:系统的安全性至关重要,需保障药品信息和用户数据的安全。采用安全的通信协议(如 HTTPS),防止数据在传输过程中被窃取或篡改;对用户进行严格的身份认证和授权管理,只有经过授权的用户才能访问系统的相应功能和数据;对敏感数据(如药品价格、患者信息等)进行加密存储,确保数据的保密性。同时,系统应具备防范常见安全攻击(如 SQL 注入、XSS 攻击等)的能力,定期进行安全漏洞扫描和修复,保障系统的安全稳定运行。

3.3 系统功能需求分析

3.3.1 角色分析

管理员:管理员是系统的最高权限用户,负责系统的整体管理和维护工作。其职责包括对药品信息的全面管理,如添加新药品、修改药品的基本信息(名称、规格、功效、价格等)、删除过期或不再销售的药品,以及实时监控药品库存,当库存低于设定的警戒线时及时进行补货提醒。对供应商信息进行管理,包括添加新供应商、更新供应商的联系方式、信用等级等信息,评估供应商的信誉和供货能力,与优质供应商建立长期合作关系。管理员工信息,如添加新员工、设置员工的账号密码、分配员工的工作权限,对员工的工作表现进行考核和评价。同时,管理员还负责管理药品的进货和销售信息,生成进货和销售报表,以便对业务数据进行分析和决策。

员工:员工在系统中主要负责日常的业务操作。他们可以查看供应商的详细信息,包括供应商的基本资料、供应的药品种类和价格等,以便在进货时做出合理的选择。员工有权查询药品信息,根据药品名称、功效、所治疾病等条件快速检索所需药品,了解药品的库存、进价、售价等信息。在药品进货环节,员工可以新增药品进货记录,填写进货数量、进货时间、供应商等信息,并对进货信息进行查询和核对。在销售环节,员工能够新增药品销售记录,记录销售药品的名称、数量、销售对象等信息,同时可以查询药品的销售历史和销售统计信息,以便更好地了解销售情况,为销售策略的调整提供依据。

3.3.2 功能模块分析

供应商类型管理:该模块允许管理员对供应商类型进行分类管理,如分为药品生产厂家、药品批发商等。管理员可以添加新的供应商类型,设置类型的名称和描述信息,以便更清晰地对供应商进行归类和管理。同时,能够对已有的供应商类型进行修改和删除操作,确保供应商类型信息的准确性和合理性。

供应商信用等级管理:管理员在这个模块中负责对供应商的信用等级进行评定和管理。根据供应商的供货及时性、药品质量、售后服务等多方面因素,为每个供应商设定相应的信用等级,如 A 级(优秀)、B 级(良好)、C 级(合格)、D 级(不合格)等。定期对供应商的信用等级进行更新和调整,对于信用等级高的供应商,可以给予一定的优惠政策或优先合作机会;对于信用等级低的供应商,加强对其供货情况的监督和管理,甚至考虑终止合作关系。

药品类型管理:管理员可以在该模块中对药品类型进行划分和管理,如分为西药、中药、医疗器械等。添加新的药品类型时,填写类型名称、特点、适用范围等详细信息;对现有药品类型进行修改和删除操作,以适应不断变化的药品市场和管理需求。通过合理的药品类型管理,方便对药品进行分类查询和统计分析。

药品管理:此模块是系统的核心功能之一。管理员可以添加药品的详细信息,包括药品名称、规格、生产厂家、生产日期、有效期、功效、用法用量、价格、库存数量、药品照片等。当药品信息发生变化时,如价格调整、库存更新等,管理员能够及时进行修改操作;对于过期、淘汰或因质量问题下架的药品,管理员可以执行删除操作。同时,管理员还可以根据药品的各种属性进行查询,如按药品名称、功效、所治疾病等条件查询,方便快速定位所需药品信息。员工也可以通过该模块查询药品的相关信息,但不具备添加、修改和删除的权限。

进货管理:员工在进货管理模块中,首先可以查看药品的进货详情,包括每次进货的药品名称、进货数量、进货时间、供应商名称、进货价格等信息。当需要进行药品进货时,员工可以新增进货记录,填写相关的进货信息,并提交审核。在进货过程中,系统会自动更新药品的库存数量,确保库存数据的准确性。员工还可以根据进货编号、药品编号、进货时间等条件对进货信息进行查询,以便对进货业务进行跟踪和管理。管理员可以对所有的进货信息进行查看和审核,确保进货流程的合规性和数据的准确性。

销售管理:员工在销售管理模块中,能够查看药品的销售详情,包括销售药品的名称、销售数量、销售时间、销售对象(如患者姓名、医院名称等)、销售价格等信息。员工在进行药品销售时,新增销售记录,记录销售的相关信息,系统会实时更新药品的库存数量和销售统计数据。员工还可以根据销售编号、药品功效、所致疾病等条件查询药品的销售信息,以便分析销售趋势和销售业绩。管理员可以对所有的销售信息进行查看、统计和分析,生成销售报表,为企业的经营决策提供数据支持,同时可以对销售数据进行修改(如因价格调整或销售错误等原因),确保销售数据的准确性。

3.4 系统流程分析

3.4.1 登录流程

用户打开医药管理系统的登录页面,在页面中输入自己的账号和密码。系统接收到用户输入的账号和密码后,将这些信息发送到服务器进行验证。服务器首先在数据库中查询该账号是否存在,如果账号不存在,则返回登录失败的提示信息,告知用户账号错误。如果账号存在,服务器将进一步验证输入的密码是否与数据库中存储的该账号对应的密码一致。若密码正确,系统根据用户账号查询其对应的角色信息(管理员或员工),并根据角色信息为用户分配相应的操作权限,然后跳转到系统的主界面,用户可以根据自己的权限进行相应的操作。若密码错误,系统返回登录失败提示信息,告知用户密码错误,并提示用户重新输入密码,用户最多可尝试输入密码 3 次,若 3 次均输入错误,系统将锁定该账号一段时间,以保障系统的安全性。登录流程如图 1 所示:


@startuml

start

:用户打开登录页面;

:输入账号和密码;

:发送账号和密码到服务器;

if (账号是否存在) then (是)

if (密码是否正确) then (是)

:查询用户角色信息;

:根据角色分配操作权限;

:跳转到系统主界面;

else (否)

:提示密码错误,可重试;

if (重试次数<3) then (是)

:返回登录页面重新输入;

else (否)

:锁定账号一段时间;

endif

endif

else (否)

:提示账号错误;

:返回登录页面重新输入;

endif

stop

@enduml

图 1 登录流程图

3.4.2 业务操作流程(如进货、销售流程)

进货流程:员工在系统中发起进货操作,首先进入进货管理模块,点击 “新增进货” 按钮,系统弹出进货信息录入表单。员工在表单中填写进货的相关信息,包括进货药品的名称(通过下拉菜单选择或手动输入药品编号进行检索)、进货数量、进货时间(系统默认当前时间,可手动修改)、供应商名称(同样通过下拉菜单选择或输入供应商编号检索)、进货价格等信息。填写完成后,员工点击 “提交” 按钮,系统对输入的信息进行合法性校验,如检查药品名称是否存在、进货数量是否为正整数、进货价格是否合理等。若信息校验通过,系统将进货信息保存到数据库中,并自动更新药品的库存数量,即库存数量 = 原有库存数量 + 进货数量。同时,系统生成进货记录的唯一编号,并将该编号显示给员工,以便员工进行后续的查询和跟踪。若信息校验不通过,系统弹出错误提示框,告知员工错误信息,员工根据提示修改信息后重新提交。进货流程如图 2 所示:


@startuml

start

:员工进入进货管理模块,点击新增进货;

:弹出进货信息录入表单;

:员工填写进货信息;

:点击提交;

:系统进行信息合法性校验;

if (校验是否通过) then (是)

:保存进货信息到数据库;

:更新药品库存数量;

:生成进货记录编号并显示;

else (否)

:弹出错误提示框;

:员工修改信息后重新提交;

endif

stop

@enduml

图 2 进货流程图

销售流程:员工在系统中进行销售操作时,进入销售管理模块,点击 “新增销售” 按钮,系统弹出销售信息录入表单。员工首先在表单中选择销售药品的名称(通过搜索或下拉菜单选择),系统自动带出该药品的规格、售价等信息。员工填写销售数量、销售时间(默认当前时间,可修改)、销售对象(如患者姓名、单位名称等)等信息。填写完毕后,点击 “提交” 按钮,系统对销售信息进行校验,检查销售数量是否超过库存数量、销售对象信息是否完整等。若校验通过,系统将销售信息保存到数据库中,更新药品的库存数量,即库存数量 = 原有库存数量 – 销售数量,同时生成销售记录的唯一编号,并显示给员工。若校验不通过,系统弹出错误提示,员工根据提示修改信息后再次提交。销售流程如图 3 所示:


@startuml

start

:员工进入销售管理模块,点击新增销售;

:弹出销售信息录入表单;

:选择销售药品名称,带出药品信息;

:填写销售数量、时间、对象等信息;

:点击提交;

:系统进行信息校验;

if (校验是否通过) then (是)

:保存销售信息到数据库;

:更新药品库存数量;

:生成销售记录编号并显示;

else (否)

:弹出错误提示框;

:员工修改信息后重新提交;

endif

stop

@enduml

图 3 销售流程图

四、系统设计

4.1 系统架构设计

本医药管理系统采用 Browser/Server(B/S)架构,这种架构模式在当今的 Web 应用开发中应用广泛。在 B/S 架构下,用户通过浏览器与系统进行交互,无需在本地安装专门的客户端软件,降低了用户的使用门槛和系统部署成本 。系统的前端负责呈现用户界面,接收用户的操作请求,并将请求发送到后端服务器;后端服务器负责处理业务逻辑,与数据库进行交互,执行数据的查询、更新等操作,然后将处理结果返回给前端;数据库则用于存储系统运行所需的各类数据,如药品信息、供应商信息、员工信息、进货销售记录等。

在前端开发中,使用 Vue 框架构建用户界面。Vue 具有简洁易用、组件化开发的特点,能够快速搭建出交互性强、用户体验良好的页面。通过 Vue 的指令和组件,可以方便地实现数据的绑定、动态渲染以及页面元素的交互效果。例如,在药品列表展示页面,使用 Vue 的 v – for 指令可以快速遍历从后端获取的药品数据,并将其展示在页面上;通过 v – on 指令可以为按钮等元素绑定点击事件,实现查询、添加、修改、删除等操作。同时,结合 Element – UI 组件库,能够快速构建出美观、功能齐全的界面,提供丰富的组件,如表格、表单、弹窗等,满足医药管理系统中各种业务场景的交互需求。

后端基于 Spring Boot 框架进行开发。Spring Boot 框架简化了 Spring 应用的搭建和开发过程,采用 “约定优于配置” 的理念,减少了大量的 XML 配置文件,提高了开发效率。它提供了丰富的 Starters,能够方便地集成各种功能,如数据库连接、数据访问、安全认证等。在本系统中,通过 Spring Data JPA Starter 实现与 MySQL 数据库的无缝连接,利用 Spring Security Starter 实现用户的身份认证和授权管理。后端的业务逻辑层负责处理系统的核心业务,如药品的添加、修改、删除操作,进货和销售业务的处理等。它接收前端传来的请求,调用相应的数据访问层方法与数据库进行交互,然后将处理结果返回给前端。

数据库采用 MySQL,它是一款开源的关系型数据库管理系统,具有高性能、可靠性和良好的兼容性。在本系统中,MySQL 负责存储系统的所有数据,通过合理的表结构设计和索引优化,确保数据的高效存储和快速查询。系统各层次之间通过 HTTP 协议进行通信,前端发送的请求经过网络传输到后端服务器,后端服务器处理请求后将响应数据返回给前端,实现了系统的前后端交互,如图 4 所示:


@startuml

package "前端(Vue)" as front {

component "用户界面" as ui

component "交互逻辑" as logic

ui -- logic : 交互

}

package "后端(Spring Boot)" as back {

component "控制器层(Controller)" as controller

component "业务逻辑层(Service)" as service

component "数据访问层(Repository)" as repository

controller -- service : 调用业务逻辑

service -- repository : 访问数据

}

package "数据库(MySQL)" as db {

component "数据表" as tables

}

front -- back : HTTP请求与响应

back -- db : SQL语句交互

@enduml

图 4 B/S 架构示意图

4.2 系统功能模块设计

本系统主要包含管理员和员工两种角色,不同角色拥有不同的功能权限。下面以药品管理模块为例,详细说明功能模块的设计与实现。

4.2.1 界面设计

药品管理模块的界面设计遵循简洁、易用的原则。在页面布局上,分为查询区域、操作按钮区域和药品信息展示区域。查询区域提供了多个查询条件输入框,如药品名称、功效、所治疾病等,方便用户根据不同需求进行药品查询;操作按钮区域放置了 “添加药品”“修改药品”“删除药品” 等按钮,用户可以通过点击这些按钮执行相应的操作;药品信息展示区域以表格的形式展示查询到的药品信息,每一行代表一条药品记录,包括药品编号、药品名称、规格、生产厂家、生产日期、有效期、功效、用法用量、价格、库存数量等字段,表格的列头清晰地标识了每个字段的含义,方便用户查看和理解。在界面设计过程中,注重了颜色搭配和字体大小的选择,以提供舒适的视觉体验;同时,对按钮和输入框等元素进行了合理的布局,使其符合用户的操作习惯,提高操作的便捷性。

4.2.2 功能操作

添加药品:管理员点击 “添加药品” 按钮,弹出添加药品的表单模态框。在表单中,管理员依次填写药品的各项信息,如药品名称、规格、生产厂家、生产日期(通过日期选择器选择)、有效期(同样通过日期选择器选择,且系统会自动校验有效期是否大于生产日期)、功效、用法用量、价格、库存数量、药品照片(支持文件上传功能,限制上传文件的格式为常见的图片格式,如 jpg、png 等)等。填写完成后,点击 “保存” 按钮,系统会对输入的信息进行合法性校验,如检查药品名称是否为空、价格是否为正数、库存数量是否为非负整数等。若信息校验通过,系统将药品信息发送到后端服务器进行保存;若校验不通过,系统弹出提示框,告知管理员错误信息,管理员根据提示修改信息后重新提交。

修改药品:在药品信息展示表格中,管理员找到需要修改的药品记录,点击该行对应的 “修改” 按钮,弹出修改药品信息的表单模态框,表单中已经填充了该药品的当前信息。管理员可以对需要修改的字段进行编辑,如修改药品价格、库存数量等。修改完成后,点击 “保存” 按钮,系统同样会进行信息校验,校验通过后将修改后的信息发送到后端服务器进行更新操作;若校验不通过,提示管理员修改错误信息。

删除药品:管理员在药品信息展示表格中勾选需要删除的药品记录,然后点击 “删除” 按钮,系统弹出确认删除的提示框,提示管理员确认是否真的要删除所选药品,以防止误操作。管理员点击 “确定” 按钮后,系统将选中的药品信息发送到后端服务器进行删除操作;若点击 “取消” 按钮,则取消删除操作。

查询药品:用户在查询区域输入查询条件,如在 “药品名称” 输入框中输入药品的部分名称,然后点击 “查询” 按钮。系统将用户输入的查询条件发送到后端服务器,后端服务器根据这些条件在数据库中进行查询,将查询到的药品信息返回给前端,前端将查询结果展示在药品信息展示区域的表格中。同时,系统支持模糊查询,即用户输入的部分名称只要包含在药品名称中,就能查询到相关药品记录。

4.2.3 数据处理

在后端,药品管理模块的数据处理主要通过 Spring Data JPA 实现。Spring Data JPA 是 Spring 框架中用于简化数据库访问的模块,它基于 JPA 规范,提供了统一的接口和实现,使得数据库操作更加方便和高效。

添加药品数据处理:当后端接收到前端发送的添加药品请求时,首先解析请求中的药品信息,将其封装成药品对象(如 Drug 类)。然后,通过 Spring Data JPA 的 Repository 接口将药品对象保存到数据库中。例如,在 DrugRepository 接口中定义了 save 方法,用于保存药品对象,代码示例如下:


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

public interface DrugRepository extends JpaRepository<Drug, Long> {

}

在业务逻辑层(Service 层)中,调用 DrugRepository 的 save 方法将药品信息保存到数据库,代码示例如下:


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Drug;

import com.example.medicals.repository.DrugRepository;

@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public Drug addDrug(Drug drug) {

return drugRepository.save(drug);

}

}

修改药品数据处理:后端接收到修改药品请求后,同样先解析请求中的修改后药品信息,封装成药品对象。然后,根据药品对象的主键(如药品编号)从数据库中查询出原有的药品记录,将修改后的信息更新到原记录中,最后通过 DrugRepository 的 save 方法将更新后的药品对象保存回数据库,实现药品信息的修改。代码示例如下:


@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public Drug updateDrug(Drug drug) {

Drug existingDrug = drugRepository.findById(drug.getId()).orElse(null);

if (existingDrug != null) {

// 更新药品信息

existingDrug.setName(drug.getName());

existingDrug.setSpecification(drug.getSpecification());

// 其他字段更新...

return drugRepository.save(existingDrug);

}

return null;

}

}

删除药品数据处理:当后端接收到删除药品请求时,根据请求中包含的药品主键(如药品编号),通过 DrugRepository 的 deleteById 方法从数据库中删除对应的药品记录。代码示例如下:


@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public void deleteDrug(Long id) {

drugRepository.deleteById(id);

}

}

查询药品数据处理:后端接收到查询药品请求后,根据请求中的查询条件构建查询语句。例如,若用户通过药品名称进行查询,后端会使用 Spring Data JPA 的方法命名查询或自定义查询语句来实现查询功能。若使用方法命名查询,在 DrugRepository 接口中定义如下方法:


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

public interface DrugRepository extends JpaRepository<Drug, Long> {

List<Drug> findByNameContaining(String name);

}

在业务逻辑层中调用该方法进行查询,代码示例如下:


@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public List<Drug> searchDrugs(String name) {

return drugRepository.findByNameContaining(name);

}

}

通过上述界面设计、功能操作和数据处理的协同工作,实现了药品管理模块的增删改查功能,满足了系统对药品信息管理的需求。其他功能模块,如进货管理、销售管理等,也采用类似的设计思路和实现方式,通过合理的界面设计、便捷的功能操作和高效的数据处理,为用户提供了完善的医药管理功能。

4.3 数据库设计

4.3.1 数据库表结构设计

本系统设计了多个数据表,用于存储不同类型的数据,各数据表的结构如下:

药品表(drug):用于存储药品的详细信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 药品唯一标识,自增长 | 主键 |

|name|varchar (100)| 药品名称 | |

|specification|varchar (50)| 药品规格 | |

|manufacturer|varchar (100)| 生产厂家 | |

|production_date|date | 生产日期 | |

|expiry_date|date | 有效期 | |

|efficacy|text | 功效 | |

|usage|text | 用法用量 | |

|price|decimal (10, 2)| 价格 | |

|stock|int | 库存数量 | |

|photo|varchar (200)| 药品照片路径 | |

|drug_type_id|bigint | 药品类型 ID | 外键,关联 drug_type 表的 id 字段 |

供应商表(supplier):存储供应商的相关信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 供应商唯一标识,自增长 | 主键 |

|name|varchar (100)| 供应商名称 | |

|contact_person|varchar (50)| 联系人 | |

|contact_number|varchar (20)| 联系电话 | |

|address|varchar (200)| 地址 | |

|credit_level|varchar (20)| 信用等级 | |

|supplier_type_id|bigint | 供应商类型 ID | 外键,关联 supplier_type 表的 id 字段 |

员工表(employee):记录员工的个人和工作相关信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 员工唯一标识,自增长 | 主键 |

|name|varchar (50)| 员工姓名 | |

|gender|varchar (10)| 性别 | |

|phone|varchar (20)| 手机号码 | |

|position|varchar (50)| 职位 | |

|username|varchar (50)| 登录账号 | |

|password|varchar (100)| 登录密码 | |

进货表(purchase):用于存储药品的进货记录。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 进货记录唯一标识,自增长 | 主键 |

|drug_id|bigint | 药品 ID | 外键,关联 drug 表的 id 字段 |

|supplier_id|bigint | 供应商 ID | 外键,关联 supplier 表的 id 字段 |

|purchase_date|date | 进货日期 | |

|quantity|int | 进货数量 | |

|unit_price|decimal (10, 2)| 进货单价 | |

销售表(sale):记录药品的销售信息。

| 字段名 | 数据类型 | 说明 | 主键 / 外键 |

|—-|—-|—-|—-|

|id|bigint | 销售记录唯一标识,自增长 | 主键 |

|drug_id|bigint | 药品 ID | 外键,关联 drug 表的 id 字段 |

|sale_date|date | 销售日期 | |

|quantity|int | 销售数量 | |

|unit_price|decimal (10, 2)| 销售单价 | |

|employee_id|bigint | 销售人员 ID | 外键,关联 employee 表的 id 字段 |

4.3.2 数据库关系设计

通过绘制 E-R 图(Entity – Relationship Diagram)来展示各数据表之间的关系,如图 5 所示:


@startuml

entity "药品(drug)" as drug {

*id : bigint

name : varchar(100)

specification : varchar(50)

manufacturer : varchar(100)

production_date : date

expiry_date : date

efficacy : text

usage : text

price : decimal(10, 2)

stock : int

photo : varchar(200)

-- 外键

*drug_type_id : bigint

}

entity "供应商(supplier)" as supplier {

*id : bigint

name : varchar(100)

contact_person : varchar(50)

contact_number : varchar(20)

address : varchar(200)

credit_level : varchar(20)

-- 外键

*supplier_type_id : bigint

}

entity "员工(employee)" as employee {

*id : bigint

name : varchar(50)

gender : varchar(10)

phone : varchar(20)

position : varchar(50)

username : varchar(50)

password : varchar(100)

}

entity "进货(purchase)" as purchase {

*id : bigint

-- 外键

*drug_id : bigint

-- 外键

*supplier_id : bigint

purchase_date : date

quantity : int

unit_price : decimal(10, 2)

}

entity "销售(sale)" as sale {

*id : bigint

-- 外键

*drug_id : bigint

sale_date : date

quantity : int

unit_price : decimal(10, 2)

-- 外键

*employee_id : bigint

}

drug "1" -- "n" purchase : 一种药品有多次进货记录

supplier "1" -- "n" purchase : 一个供应商供应多种药品的进货

drug "1" -- "n" sale : 一种药品有多次销售记录

employee "1" -- "n" sale : 一个员工进行多次销售操作

@enduml

图 5 数据库 E-R 图

在 E-R 图中,药品与供应商通过进货表建立关联关系,一个供应商可以供应多种药品的进货,一种药品也可以从多个供应商进货;药品与销售表存在一对多的关系,即一种药品可以有多次销售记录;员工与销售表同样是一对多的关系,一个员工可以进行多次销售操作。通过这种关系设计,能够准确地反映医药管理业务中的数据关联,为系统的功能实现提供了坚实的数据基础,确保了数据的完整性和一致性 。在实际数据库操作中,通过外键约束来维护这些关系,保证数据的正确性和可靠性。例如,在进货表中,drug_id 和 supplier_id 作为外键,分别关联药品表和供应商表的主键,当进行进货操作时,系统会校验关联的药品和供应商是否存在,若不存在则不允许进行进货记录的插入,从而避免了数据的不一致性问题。

五、系统实现

5.1 开发环境搭建

JDK 安装与配置:首先,从 Oracle 官方网站下载适合系统的 JDK 安装包,例如对于 Windows 系统,下载对应的 Windows x64 Installer。下载完成后,双击安装包进行安装,安装过程中可以选择默认安装路径,也可自定义安装目录。安装完成后,需要配置环境变量。在系统环境变量中,新建一个名为 “JAVA_HOME” 的变量,变量值为 JDK 的安装路径,如 “C:Program FilesJavajdk1.8.0_361”。然后,在 “Path” 变量中添加 “% JAVA_HOME%in” 和 “% JAVA_HOME%jrein”,确保系统能够找到 Java 的可执行文件。最后,打开命令提示符,输入 “java -version”,若能正确显示 JDK 版本信息,则说明 JDK 安装与配置成功。

开发工具 IDEA 安装与配置:从 JetBrains 官网下载 IntelliJ IDEA 安装包,根据系统选择对应的版本,如 Windows 系统下载.exe 格式的安装包。下载后,双击安装包开始安装,安装过程中按照提示逐步进行操作,可选择安装路径、关联文件类型等。安装完成后,首次启动 IDEA,会进行一些初始化设置,如选择主题、配置插件等。在配置插件时,可以根据项目需求安装相关插件,如 Maven Helper、Lombok 等。接着,需要配置 JDK 路径,在 “File” -> “Project Structure” 中,找到 “SDKs” 选项,点击 “+” 按钮,选择之前安装的 JDK 目录,完成 JDK 配置。

Maven 安装与配置:从 Maven 官网(https://maven.apache.org/download.cgi)下载 Maven 的二进制压缩包,下载完成后解压到指定目录,如 “D:apache-maven-3.9.6”。解压完成后,配置环境变量,在系统环境变量中新建 “MAVEN_HOME” 变量,变量值为 Maven 的解压路径 “D:apache-maven-3.9.6”。然后,在 “Path” 变量中添加 “% MAVEN_HOME%in”,使系统能够识别 Maven 命令。接下来,打开 Maven 安装目录下的 “conf” 文件夹,编辑 “settings.xml” 文件,配置本地仓库路径,例如在 “settings.xml” 文件中找到 “localRepository” 标签,修改其值为 “D:maven
epository”(自定义的本地仓库路径)。同时,为了加快依赖下载速度,可以配置镜像,在 “mirrors” 标签内添加阿里云镜像配置:


<mirror>

<id>aliyunmaven</id>

<mirrorOf>central</mirrorOf>

<name>阿里云公共仓库</name>

<url>https://maven.aliyun.com/repository/central</url>

</mirror>

配置完成后,打开命令提示符,输入 “mvn -version”,若能正确显示 Maven 版本信息,则说明 Maven 安装与配置成功。

Tomcat 安装与配置:从 Apache Tomcat 官网(https://tomcat.apache.org/download-90.cgi)下载 Tomcat 安装包,选择合适的版本,如 Tomcat 9。对于 Windows 系统,可下载.zip 格式的免安装版。下载完成后,解压到指定目录,如 “D:apache-tomcat-9.0.75”。解压完成后,配置环境变量,在系统环境变量中新建 “CATALINA_HOME” 变量,变量值为 Tomcat 的解压路径 “D:apache-tomcat-9.0.75”。然后,在 “Path” 变量中添加 “% CATALINA_HOME%in”。配置完成后,打开命令提示符,进入 Tomcat 的 “bin” 目录,输入 “startup.bat” 启动 Tomcat,若能成功启动,并在浏览器中访问 “http://localhost:8080/” 出现 Tomcat 欢迎页面,则说明 Tomcat 安装与配置成功。若端口号 8080 被占用,可以修改 Tomcat 的端口号,在 Tomcat 安装目录下的 “conf” 文件夹中,找到 “server.xml” 文件,修改其中的 “Connector” 标签的 “port” 属性值,如将其改为 “8081”。

5.2 关键功能模块的代码实现

5.2.1 药品管理模块

添加药品功能代码实现:在后端,通过 Spring Data JPA 实现药品信息的保存。首先,定义药品实体类 Drug,使用 JPA 的注解标注实体和字段映射关系。


import javax.persistence.Entity;

import javax.persistence.GeneratedValue;

import javax.persistence.GenerationType;

import javax.persistence.Id;

@Entity

public class Drug {

@Id

@GeneratedValue(strategy = GenerationType.IDENTITY)

private Long id;

private String name;

private String specification;

private String manufacturer;

private String productionDate;

private String expiryDate;

private String efficacy;

private String usage;

private BigDecimal price;

private Integer stock;

private String photo;

// 其他属性及getter、setter方法

}

然后,定义 DrugRepository 接口,继承自 JpaRepository,利用 Spring Data JPA 的自动实现功能。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

public interface DrugRepository extends JpaRepository<Drug, Long> {

}

在 DrugService 中实现添加药品的业务逻辑,调用 DrugRepository 的 save 方法保存药品信息。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Drug;

import com.example.medicals.repository.DrugRepository;

@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public Drug addDrug(Drug drug) {

return drugRepository.save(drug);

}

}

在前端,使用 Vue 组件实现添加药品的界面交互。通过表单收集用户输入的药品信息,利用 Axios 库将数据发送到后端。


<template>

<div>

<h2>添加药品</h2>

<form @submit.prevent="addDrug">

<label>药品名称:</label>

<input v-model="drug.name" type="text" required><br>

<!-- 其他表单字段 -->

<button type="submit">保存</button>

</form>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

drug: {

name: '',

specification: '',

// 其他属性初始值

}

};

},

methods: {

addDrug() {

axios.post('/drugs', this.drug)

.then(response => {

console.log('药品添加成功', response.data);

// 其他操作,如清空表单、提示用户等

})

.catch(error => {

console.error('药品添加失败', error);

});

}

}

};

</script>

查询药品功能代码实现:在后端,DrugRepository 中定义根据药品名称模糊查询的方法。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Drug;

import java.util.List;

public interface DrugRepository extends JpaRepository<Drug, Long> {

List<Drug> findByNameContaining(String name);

}

在 DrugService 中调用该方法实现查询逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Drug;

import com.example.medicals.repository.DrugRepository;

import java.util.List;

@Service

public class DrugService {

@Autowired

private DrugRepository drugRepository;

public List<Drug> searchDrugs(String name) {

return drugRepository.findByNameContaining(name);

}

}

在前端,通过表单输入查询条件,调用后端接口获取查询结果并展示。


<template>

<div>

<h2>查询药品</h2>

<form @submit.prevent="searchDrugs">

<label>药品名称:</label>

<input v-model="searchName" type="text"><br>

<button type="submit">查询</button>

</form>

<table>

<thead>

<tr>

<th>药品名称</th>

<th>规格</th>

<!-- 其他表头字段 -->

</tr>

</thead>

<tbody>

<tr v-for="drug in drugs" :key="drug.id">

<td>{
{ drug.name }}</td>

<td>{
{ drug.specification }}</td>

<!-- 其他表格数据 -->

</tr>

</tbody>

</table>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

searchName: '',

drugs: []

};

},

methods: {

searchDrugs() {

axios.get('/drugs/search', { params: { name: this.searchName } })

.then(response => {

this.drugs = response.data;

})

.catch(error => {

console.error('查询药品失败', error);

});

}

}

};

</script>

修改和删除药品功能的实现思路与上述类似,在后端通过 DrugRepository 和 DrugService 实现业务逻辑,在前端通过 Vue 组件和 Axios 库实现用户交互和数据传输。

5.2.2 进货管理模块

进货信息录入功能代码实现:在后端,定义进货实体类 Purchase,映射进货表结构。


import javax.persistence.Entity;

import javax.persistence.GeneratedValue;

import javax.persistence.GenerationType;

import javax.persistence.Id;

import javax.persistence.ManyToOne;

@Entity

public class Purchase {

@Id

@GeneratedValue(strategy = GenerationType.IDENTITY)

private Long id;

@ManyToOne

private Drug drug;

@ManyToOne

private Supplier supplier;

private String purchaseDate;

private Integer quantity;

private BigDecimal unitPrice;

// 其他属性及getter、setter方法

}

定义 PurchaseRepository 接口继承 JpaRepository。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Purchase;

public interface PurchaseRepository extends JpaRepository<Purchase, Long> {

}

在 PurchaseService 中实现进货信息保存逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Purchase;

import com.example.medicals.repository.PurchaseRepository;

@Service

public class PurchaseService {

@Autowired

private PurchaseRepository purchaseRepository;

public Purchase addPurchase(Purchase purchase) {

return purchaseRepository.save(purchase);

}

}

在前端,通过 Vue 组件的表单收集进货信息,发送到后端。


<template>

<div>

<h2>新增进货</h2>

<form @submit.prevent="addPurchase">

<label>药品:</label>

<select v-model="purchase.drug.id" required>

<option v-for="drug in drugs" :value="drug.id">{
{ drug.name }}</option>

</select><br>

<!-- 其他表单字段,如供应商、进货日期、数量、单价等 -->

<button type="submit">保存</button>

</form>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

purchase: {

drug: {},

supplier: {},

purchaseDate: '',

quantity: 0,

unitPrice: 0

},

drugs: []

};

},

created() {

this.getDrugs();

},

methods: {

getDrugs() {

axios.get('/drugs')

.then(response => {

this.drugs = response.data;

})

.catch(error => {

console.error('获取药品列表失败', error);

});

},

addPurchase() {

axios.post('/purchases', this.purchase)

.then(response => {

console.log('进货信息添加成功', response.data);

// 其他操作,如清空表单、提示用户等

})

.catch(error => {

console.error('进货信息添加失败', error);

});

}

}

};

</script>

进货信息查询功能代码实现:在后端,PurchaseRepository 中可定义根据进货日期范围查询进货信息的方法。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Purchase;

import java.util.List;

public interface PurchaseRepository extends JpaRepository<Purchase, Long> {

List<Purchase> findByPurchaseDateBetween(String startDate, String endDate);

}

在 PurchaseService 中调用该方法实现查询逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Purchase;

import com.example.medicals.repository.PurchaseRepository;

import java.util.List;

@Service

public class PurchaseService {

@Autowired

private PurchaseRepository purchaseRepository;

public List<Purchase> searchPurchases(String startDate, String endDate) {

return purchaseRepository.findByPurchaseDateBetween(startDate, endDate);

}

}

在前端,通过表单输入查询条件,调用后端接口获取查询结果并展示。


<template>

<div>

<h2>查询进货信息</h2>

<form @submit.prevent="searchPurchases">

<label>开始日期:</label>

<input v-model="startDate" type="date"><br>

<label>结束日期:</label>

<input v-model="endDate" type="date"><br>

<button type="submit">查询</button>

</form>

<table>

<thead>

<tr>

<th>药品名称</th>

<th>供应商</th>

<th>进货日期</th>

<th>数量</th>

<th>单价</th>

</tr>

</thead>

<tbody>

<tr v-for="purchase in purchases" :key="purchase.id">

<td>{
{ purchase.drug.name }}</td>

<td>{
{ purchase.supplier.name }}</td>

<td>{
{ purchase.purchaseDate }}</td>

<td>{
{ purchase.quantity }}</td>

<td>{
{ purchase.unitPrice }}</td>

</tr>

</tbody>

</table>

</div>

</template>

<script>

import axios from 'axios';

export default {

data() {

return {

startDate: '',

endDate: '',

purchases: []

};

},

methods: {

searchPurchases() {

axios.get('/purchases/search', { params: { startDate: this.startDate, endDate: this.endDate } })

.then(response => {

this.purchases = response.data;

})

.catch(error => {

console.error('查询进货信息失败', error);

});

}

}

};

</script>

进货信息审核功能可通过在 Purchase 实体类中添加审核状态字段,在后端实现审核逻辑,前端实现审核操作的交互。

5.2.3 销售管理模块

销售信息录入功能代码实现:在后端,定义销售实体类 Sale,映射销售表结构。


import javax.persistence.Entity;

import javax.persistence.GeneratedValue;

import javax.persistence.GenerationType;

import javax.persistence.Id;

import javax.persistence.ManyToOne;

@Entity

public class Sale {

@Id

@GeneratedValue(strategy = GenerationType.IDENTITY)

private Long id;

@ManyToOne

private Drug drug;

private String saleDate;

private Integer quantity;

private BigDecimal unitPrice;

@ManyToOne

private Employee employee;

// 其他属性及getter、setter方法

}

定义 SaleRepository 接口继承 JpaRepository。


import org.springframework.data.jpa.repository.JpaRepository;

import com.example.medicals.model.Sale;

public interface SaleRepository extends JpaRepository<Sale, Long> {

}

在 SaleService 中实现销售信息保存逻辑。


import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.stereotype.Service;

import com.example.medicals.model.Sale;

import com.example.medicals.repository.SaleRepository;

@Service

public class SaleService {

@Autowired

private SaleRepository saleRepository;

public Sale addSale(Sale sale) {

return saleRepository.save(sale);

}

}

在前端,通过 Vue 组件的表单收集销售信息,发送到后端。


<template>

<div>

<h2>新增销售</h2>

<form @submit.prevent="addSale">

<label>药品:</label>

<select v-model="sale.drug.id" required>

<option v-for="drug in drugs" :value="drug.id">{
{ drug.name }}</option>

</select><br>

<!-- 其他表单字段,如销售日期、数量、单价、销售人员等 -->

<button type="submit">保存</button>

</form>

</div>

</

## 六、系统测试

### 6.1 测试目的

系统测试是软件开发过程中的重要环节,对于基于Spring Boot的医药管理系统而言,其测试目的具有多方面的重要性。首要目标是验证系统功能的正确性,确保系统实现了需求分析阶段所确定的各项功能。例如,在药品管理模块,要确认添加药品功能能够准确无误地将药品信息保存到数据库中,修改和删除功能也能按照预期对药品数据进行相应操作;进货管理和销售管理模块中的进货和销售记录添加、查询等功能也需准确实现,保证业务流程的顺畅进行。

性能方面,测试系统是否满足性能需求是关键。要检测系统在不同负载情况下的响应时间、吞吐量等指标,以确定系统是否能够在正常业务量和高并发情况下稳定运行,满足实际使用中的性能要求。比如,在多个用户同时进行药品查询或销售操作时,系统应能在规定的时间内响应,不出现卡顿或超时现象。

同时,测试还需排查系统是否存在漏洞,包括安全漏洞和逻辑漏洞等。安全漏洞方面,要检查系统是否存在SQL注入、XSS攻击等安全隐患,确保药品信息和用户数据的安全性;逻辑漏洞则关注系统业务逻辑的合理性,例如进货和销售操作中的库存更新逻辑是否正确,避免出现库存数量异常的情况。通过全面的测试,及时发现并解决这些问题,从而提高系统的质量和可靠性,为用户提供稳定、安全、高效的医药管理服务 。

### 6.2 测试方法

本系统主要采用黑盒测试和白盒测试相结合的方法进行测试。黑盒测试是在不考虑系统内部结构和实现细节的情况下,仅依据系统的需求规格说明书,对系统的功能进行测试。例如,在测试药品查询功能时,测试人员只需在前端输入不同的查询条件(如药品名称、功效等),观察系统返回的查询结果是否正确,而无需了解后端的查询实现逻辑。通过黑盒测试,可以验证系统的功能是否符合用户需求,检查系统的输入与输出是否正确对应。

白盒测试则是基于系统内部的代码结构和逻辑,对系统的内部操作进行测试。在本系统中,对于一些关键的业务逻辑方法,如药品库存更新方法、进货和销售业务处理方法等,采用白盒测试。测试人员可以查看代码实现,设计测试用例来覆盖不同的代码路径和分支,确保代码的正确性和健壮性。例如,在测试药品库存更新方法时,通过编写不同的测试数据,验证在各种情况下(如正常进货、销售,以及特殊情况如库存为零、负数等)库存更新逻辑是否正确,以保证系统内部逻辑的准确性。

### 6.3 测试用例设计

#### 6.3.1 药品管理模块

|测试用例编号|测试场景|输入数据|预期输出|测试步骤|

|----|----|----|----|----|

|1|添加药品|药品名称:感冒灵颗粒;规格:10g*9袋;生产厂家:XX制药;生产日期:2024-01-01;有效期:2025-01-01;功效:解热镇痛;用法用量:开水冲服,一次10克,一日3次;价格:15.00;库存数量:100;药品照片:无;药品类型ID:1|提示药品添加成功,数据库中新增一条药品记录|1. 登录系统,进入药品管理模块。2. 点击“添加药品”按钮,填写上述输入数据。3. 点击“保存”按钮|

|2|修改药品|药品ID:1(已存在的药品);修改后价格:16.00|提示药品修改成功,数据库中对应药品记录的价格更新为16.00|1. 进入药品管理模块,查询出ID为1的药品。2. 点击“修改”按钮,修改价格为16.00。3. 点击“保存”按钮|

|3|删除药品|药品ID:1(已存在的药品)|提示药品删除成功,数据库中对应药品记录被删除|1. 进入药品管理模块,查询出ID为1的药品。2. 勾选该药品,点击“删除”按钮。3. 在弹出的确认框中点击“确定”|

|4|查询药品|药品名称:感冒灵|显示名称包含“感冒灵”的药品记录|1. 进入药品管理模块,在查询框中输入“感冒灵”。2. 点击“查询”按钮|

#### 6.3.2 进货管理模块

|测试用例编号|测试场景|输入数据|预期输出|测试步骤|

|----|----|----|----|----|

|5|新增进货|药品ID:1;供应商ID:1;进货日期:2024-05-01;进货数量:50;进货单价:10.00|提示进货信息添加成功,数据库中新增一条进货记录,对应药品库存增加50|1. 登录系统,进入进货管理模块。2. 点击“新增进货”按钮,填写上述输入数据。3. 点击“保存”按钮|

|6|查询进货|进货日期范围:2024-05-01至2024-05-31|显示该时间段内的进货记录|1. 进入进货管理模块,在查询条件中选择进货日期范围为2024-05-01至2024-05-31。2. 点击“查询”按钮|

#### 6.3.3 销售管理模块

|测试用例编号|测试场景|输入数据|预期输出|测试步骤|

|----|----|----|----|----|

|7|新增销售|药品ID:1;销售日期:2024-05-02;销售数量:10;销售单价:20.00;员工ID:1|提示销售信息添加成功,数据库中新增一条销售记录,对应药品库存减少10|1. 登录系统,进入销售管理模块。2. 点击“新增销售”按钮,填写上述输入数据。3. 点击“保存”按钮|

|8|查询销售|销售日期:2024-05-02|显示该日期的销售记录|1. 进入销售管理模块,在查询条件中输入销售日期为2024-05-02。2. 点击“查询”按钮|

### 6.4 测试结果分析

经过对各个功能模块的测试,大部分测试用例都顺利通过,系统的主要功能基本符合设计要求。在药品管理模块中,添加、修改、删除和查询药品功能均能正确执行,数据的保存和查询准确无误;进货管理模块的进货信息添加和查询功能正常,库存更新逻辑正确;销售管理模块的销售信息添加和查询功能也能正常工作,库存更新也符合预期。

然而,在测试过程中也发现了一些问题。例如,在高并发情况下进行进货和销售操作时,偶尔会出现库存数据更新不一致的情况。经过分析,发现是由于并发操作时对数据库的事务处理不当导致的。针对这个问题,通过在相关业务方法上添加事务注解,确保了事务的原子性,解决了库存数据更新不一致的问题。

## 七、总结与展望

### 7.1 系统总结

本基于Spring Boot的医药管理系统,从设计到实现经历了多个关键阶段。在设计阶段,通过全面的需求分析,明确了系统的功能需求、性能需求以及操作流程,为后续的开发工作奠定了坚实基础。采用B/S架构,结合Spring Boot框架、Vue前端技术和MySQL数据库进行系统架构设计,确保了系统的稳定性、可扩展性和高效性。在功能模块设计方面,详细规划了药品管理、进货管理、销售管理等核心模块,每个模块都具备清晰的功能和操作流程,满足了不同用户角色(管理员和员工)的使用需求。

在实现阶段,搭建了完善的开发环境,包括JDK、IDEA、Maven和Tomcat等工具的安装与配置。通过编写后端的Java代码,利用Spring Data JPA实现了与MySQL数据库的交互,完成了各个功能模块的业务逻辑实现;前端使用Vue框架和Axios库,实现了友好的用户界面和数据传输功能。经过全面的系统测试,验证了系统功能的正确性和稳定性,大部分测试用例顺利通过,系统能够满足医药管理的基本业务需求。

系统具有以下特点:功能全面,涵盖了医药管理的各个关键环节,包括药品信息管理、进货销售管理等,能够为医药企业提供一站式的管理服务;操作便捷,界面设计简洁明了,操作流程符合用户习惯,即使是非专业人员也能快速上手使用;数据安全可靠,采用了身份认证、授权管理和数据加密等安全措施,保障了药品信息和用户数据的安全性和完整性;系统扩展性良好,基于Spring Boot框架的设计,方便后续对系统进行功能扩展和升级,以适应不断变化的业务需求。

总体而言,本系统达到了预期目标,实现了对医药信息的高效管理,提高了医药管理的工作效率,降低了管理成本,为医药企业的信息化建设提供了有效的解决方案。

### 7.2 未来展望

随着医疗行业的不断发展和信息技术的持续进步,本医药管理系统还有很大的发展空间。在性能优化方面,可以进一步对系统进行性能测试和调优,采用缓存技术(如Redis)减少数据库的访问次数,提高系统的响应速度;优化数据库查询语句和索引,提升数据查询的效率;对系统进行分布式部署,提高系统的并发处理能力,以满足业务量不断增长的需求。

在功能扩展方面,可以增加药品溯源功能,通过扫码等方式实现药品从生产到销售的全过程追溯,提高药品质量监管水平;引入智能预警功能,根据药品库存、有效期等信息,自动发出预警提醒,避免药品过期和库存不足的情况发生;开发移动端应用,方便员工随时随地进行业务操作,提高工作的灵活性和便捷性;集成数据分析功能,对药品销售数据、进货数据等进行深入分析,为企业的决策提供数据支持,如制定采购计划、优化销售策略等。

在技术更新方面,关注新技术的发展趋势,适时引入新的技术和框架,如微服务架构,将系统拆分成多个独立的微服务,提高系统的可维护性和可扩展性;采用云计算技术,将系统部署到云端,降低硬件成本和运维难度,提高系统的可用性和可靠性。通过不断地优化和升级,使本医药管理系统能够更好地适应医疗行业的发展需求,为医药企业提供更优质、高效的管理服务。

## 致谢

在完成基于Spring Boot的医药管理系统毕业设计的过程中,我得到了许多人的帮助,心中满是感激。

我要衷心感谢我的指导教师。从系统的选题到设计方案的敲定,再到代码实现和论文撰写的每一个环节,老师都给予了我悉心的指导和耐心的帮助。老师严谨的治学态度、渊博的专业知识和丰富的实践经验,使我在遇到问题时总能得到及时且准确的建议,为我指明了前进的方向。在我因技术难题而陷入困境时,老师鼓励我勇于探索,引导我从不同角度思考问题,让我不断突破自我。没有老师的引领,我难以顺利完成这个项目,师恩难忘,我将铭记于心。

同时,我也不会忘记我的同学们。在项目开发过程中,我们相互交流、共同探讨,分享各自的经验和见解。当我在代码编写中遇到逻辑问题时,同学们积极为我出谋划策,帮我理清思路;在系统测试阶段,大家一起进行测试用例的设计和执行,共同找出并解决了许多潜在的问题。我们在学习和实践中相互激励、共同进步,同窗之情让这段经历变得更加珍贵。

我最应该感谢的,还有我的家人。他们一直是我最坚强的后盾,给予我无条件的支持和鼓励。在我为了完成毕业设计而日夜忙碌时,家人默默承担了生活中的琐事,让我能够全身心地投入到学习和工作中。他们的关爱和信任,是我不断前行的动力,每当我遇到困难想要放弃时,想到家人的期望,我便又充满了斗志。

在此,我向所有帮助过我的人表示最诚挚的感谢!感谢你们在我成长道路上的陪伴和支持,这份情谊我将永远珍惜 。

© 版权声明
THE END
如果内容对您有所帮助,就支持一下吧!
点赞0 分享
评论 抢沙发

请登录后发表评论

    暂无评论内容