• SpringBoot+Mybatis+Thymeleaf实现垃圾分类系统


    🍅程序员小王的博客:程序员小王的博客
    🍅 欢迎点赞 👍 收藏 ⭐留言 📝
    🍅 如有编辑错误联系作者,如果有比较好的文章欢迎分享给我,我会取其精华去其糟粕
    😊 如果需要源码,扫描主页左侧二维码,加我微信 一起学习、一起进步
    🍅java自学的学习路线:java自学的学习路线

    一、前言

    垃圾分类系统是我帮助一位同学实现毕业设计的时候完成的一个项目,我采用SpringBoot+Mysql+Thymeleaf 模板引擎实现的垃圾分类查询管理系统,系统主要实现的功能有:实现前端垃圾分类的查询功能,采用bootstrap框架,能够自适应浏览设备。实现后台菜单管理、垃圾分类管理,搜索管理,贡献管理,数据分析,公告管理等模块等功能。

    二、具体实现功能及使用技术

    1、实现功能

    #垃圾分类查询管理系统。
    共分为两种角色,系统管理员,还有用户
    
    #管理员角色具有功能:
    系统设置-用户管理、页面管理、角色管理;
    
    我的-首页、搜索记录、我的收益;
    
    贡献管理-贡献管理、随机数据、每日垃圾、贡献记录;
    
    垃圾管理-垃圾管理、分类管理、分类列表、垃圾列表、修改奖励;
    
    数据分析-全国统计、分类统计、投放统计;
    
    公告管理-公告管理、公告列表、必布公告;
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    2、所需要的技术

    1.运行环境:java jdk 1.8
    
    2.IDE环境:IDEA
    
    3.tomcat环境:Tomcat 7.x
    
    4.硬件环境:windows 7/8/10 1G内存以上;
    
    5.是否Maven项目: 是
    
    6.数据库:MySql 8.0版本;
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    3、开发内容

    本作品的研发内容是通过SpringBoot的技术去实现一个符合需求的垃圾分类系统。《垃圾分类查询管理系统》采用B/S架构,该系统的功能主要包括用户对生活垃圾所属分类的查询功能和管理员对于系统及系统内的垃圾和垃圾分类的管理功能。本系统在系统的设计与开发过程中严格遵守软件工程的规范,运用软件设计模式,从而减少系统模块间的偶合,力求做到系统的稳定性、可重用性和可扩充性。

    《垃圾分类查询管理系统》主要功能如下:

    1.用户:

    查询垃圾所属分类:用户可以通过输入相应的垃圾名称来查询该垃圾所属的垃圾分类类别;

    2.管理员功能:

    A. 系统设置-用户管理、页面管理、角色管理;

    B. 我的-首页、搜索记录、我的收益;

    C. 贡献管理-贡献管理、随机数据、每日垃圾、贡献记录;

    D. 垃圾管理-垃圾管理、分类管理、分类列表、垃圾列表、修改奖励;

    E. 数据分析-全国统计、分类统计、投放统计;

    F. 公告管理-公告管理、公告列表、必布公告;

    三、开发工具及相关技术

    1、 开发工具

    IntelliJ IDEA简称IDEA,它是 JetBrains 公司下的Java集成开发环境,在业界被公认为是最好的Java开发工具之一;JetBrains是捷克的一家软件公司,该公司总部位于捷克共和国的首都布拉格,开发人员以严谨著称的东欧程序员为主,旗下开发了多款软件开发工具;官方网站:https://www.jetbrains.com/Intellij IDEA工具已经有很长的历史了,2001年1月发布IntelliJ IDEA 1.0版本,只是一直没有被大量使用;IntelliJ IDEA以前是收费软件,不过在2009年以后开始推出了免费的社区开源版本;目前IntelliJ IDEA有免费的社区版(功能相对较少),和收费的旗舰版(功能比较全面);是java编程语言开发的集成环境。IntelliJ在业界被公认为最好的java开发工具,尤其在智能代码助手、代码自动提示、重构、JavaEE支持、各类版本工具(gitsvn等)、JUnit、CVS整合、代码分析、 创新的GUI设计等方面的功能可以说是超常的[1]。IDEA是JetBrains公司的产品,这家公司总部位于捷克共和国的首都布拉格,开发人员以严谨著称的东欧程序员为主。它的旗舰版本还支持HTML,CSS,PHP,MySQL,Python等。免费版只支持Java,Kotlin等少数语言[3]。

    2、 Maven自动化构建工具

    Maven是一个项目管理和综合工具。在实际项目中Web工程除了Java程序、jsp页面等资源外,往往需要导入各种各样的框架的jar包和配置文件。所有这些资源都部署到服务器上才能运行。而maven作为自动化构建工具,只需在配置文件中写出需要导入的包名称和版本号,在联网环境下将直接从国际Maven仓库下载到本地仓库中。实际编程环境中自动构建的产生的影响如图所示。

    3、作品的技术栈

    基于JavaWeb技术体系,MySQL数据库,Tomcat服务器,以及maven搭建技术;应用SpringBoot开源框架搭建系统;应用Ajax及bootStrap等前端框架还有thymeleaf模板引擎技术实现了前端网页;使用了拦截器实现了用户权限管理和登录状态的判断来实现锁屏模块的实现。还使用Photoshop、Flash等网站建设辅助软件。

    4、相关技术

    (1) SpringBoot框架

    Spring框架功能很强大,但是就算是一个很简单的项目,我们也要配置很多东西。因此就有了Spring Boot框架,它的作用很简单,就是帮我们自动配置。Spring Boot框架的核心就是自动配置,只要存在相应的jar包,Spring就帮我们自动配置。如果默认配置不能满足需求,我们还可以替换掉自动配置类,使用我们自己的配置。另外,Spring Boot还集成了嵌入式的Web服务器,系统监控等很多有用的功,让我们快速构建企业及应用程序。

    (2)MySQL

    MySQL是一个开放源码的小型关联式数据库管理系统,开发者为瑞典MySQL AB公司。MySQL被广泛地应用在Internet上的中小型网站中。由于其体积小、速度快、总体拥有成本低,尤其是开放源码这一特点,许多中小型网站为了降低网站总体拥有成本而选择了MySQL作为网站数据库。

    自从Oracle公司收购了MySQL后不久,就发行了MySQL的企业版(不再免费)!

    (3)MVC

    MVC即模型-视图-控制器,是Xerox PARC在八十年代为编程语言Smalltalk-80发明的一种软件设计模式,至今已被广泛使用。最近几年被推荐为Sun公司J2EE平台的设计模式,并且受到越来越多的使用ColdFusion和PHP的开发者的欢迎。

    MVC是一种设计模式,它强制性的使应用程序的输入、处理和输出分开。使用MVC应用程序被分成三个核心部件:模型、视图、控制器。它们各自处理自己的任务.

    (1)模型

    模型表示企业数据和业务规则。在MVC的三个部件中,模型拥有最多的处理任务。例如它可能用象EJBs和ColdFusion Components这样的构件对象来处理数据库。被模型返回的数据是中立的,就是说模型与数据格式无关,这样一个模型能为多个视图提供数据。由于应用于模型的代码只需写一次就可以被多个视图重用,所以减少了代码的重复性。

    (2)视图

    视图是用户看到并与之交互的界面。对老式的Web应用程序来说,视图就是由HTML元素组成的界面,在新式的Web应用程序中,HTML依旧在视图中扮演着重要的角色,但一些新的技术已层出不穷,它们包括Macromedia Flash和象XHTML,XML/XSL,WML等一些标识语言和Web services.如何处理应用程序的界面变得越来越有挑战性。MVC一个大的好处是它能为你的应用程序处理很多不同的视图。在视图中其实没有真正的处理发生,不管这些数据是联机存储的还是一个雇员列表,作为视图来讲,它只是作为一种输出数据并允许用户操纵的方式。

    (3)控制器

    控制器接受用户的输入并调用模型和视图去完成用户的需求。所以当单击Web页面中的超链接和发送HTML表单时,控制器本身不输出任何东西和做任何的处理。它只是接收请求并决定调用哪个模型构件去处理请求,然后确定用哪个视图来显示模型处理返回的数据。

    综上所述,MVC的处理过程是首先控制器接收用户的请求,并决定应该调用哪个模型来进行处理,然后模型用业务逻辑来处理用户的请求并返回数据,最后控制器用相应的视图格式化模型返回的数据,并通过表示层呈现给用户。

    5、 系统开发平台及运行环境

    1、 系统开发平台

    系统的开发是在Tomcat环境下进行的。Tomcat是一个免费的开源的Servlet容器,它是Apache基金会的Jakarta项目中的一个核心项目,由Apache,Sun和其它一些公司及个人共同开发而成。由于有了Sun的参与和支持,最新的Servlet和Jsp规范总能在Tomcat中得到体现。Tomcat被Java World杂志的编辑选为2001年度最具创新的Java产品,可见其在业界的地位。

    Tomcat的环境主要有以下几方面技术优势:

    1.Tomcat中的应用程序是一个WAR(Web Archive)文件。WAR是Sun提出的一种Web应用程序格式,与JAR类似,也是许多文件的一个压缩包。

    2.在Tomcat中,应用程序的部署很简单,你只需将你的WAR放到Tomcat的webapp目录下,Tomcat会自动检测到这个文件,并将其解压。

    3.Tomcat不仅仅是一个Servlet容器,它也具有传统的Web服务器的功能:处理html页面。

    4.Tomcat也可以与其它一些软件集成起来实现更多的功能。

    2、 运行环境

    1. 操作系统:Windowswindos10以上版本。

    2. 服务器软件:apache-tomcat-8.5.71版本。

    3. 浏览器:IE、Fire Fox、Google Chrome。

    4. 运行环境:java jdk 1.8 2.

    5. IDE环境:IDEA

    6. 是否Maven项目: 是

    7. 数据库:MySql 8.0版本;

    四、系统总体设计

    1、项目概述

    一个完整的系统离不开前端页面和数据库,本章主要介绍在基于web技术实现的的垃圾分类系统的设计目录结构,主要界面设计和数据库设计,为实现系统做准备。

    如图所示,我的文件目录一共有三大模块,分别是java、resource、webapp三大板块,首先先说第一个板块,它撰写的内容是后端java代码,里面又细分了五大类,分别是控制器(处理器代码)、持久层接口Dao、实例化对象domain、业务层模块service、还有测试模块test。

    2、 系统功能模块概述和分析

    《垃圾分类管理系统》采用B/S架构,该系统的功能主要包括用户对生活垃圾所属分类的查询功能和管理员对于系统及系统内的垃圾和垃圾分类的管理功能。本系统在系统的设计与开发过程中严格遵守软件工程的规范,运用软件设计模式,从而减少系统模块间的偶合,力求做到系统的稳定性、可重用性和可扩充性。

    《垃圾分类查询管理系统》主要功能如下:

    1. 用户:

    查询垃圾所属分类:用户可以通过输入相应的垃圾名称来查询该垃圾所属的垃圾分类类别;

    1. 管理员功能:

    2. 系统设置-用户管理、页面管理、角色管理;

    3. 我的-首页、搜索记录、我的收益;

    4. 贡献管理-贡献管理、随机数据、每日垃圾、贡献记录;

    5. 垃圾管理-垃圾管理、分类管理、分类列表、垃圾列表、修改奖励;

    6. 数据分析-全国统计、分类统计、投放统计;

    7. 公告管理-公告管理、公告列表、必布公告;

    用例图是进行需求分析的很好的手段,它是从用户的角度来考虑,可以深入分析出系统的功能和动态行为,该系统的用例图如下所示:

    游客用例图:

    3、主要界面设计

    登录页面采用的bootStrap,然后点击红色圆圈的加号就是注册页面了

    垃圾分类查询分为我们可以输入苹果之类的物品,然后系统就会显示这是有害垃圾还是无害垃圾,比如输入苹果:系统显示苹果是可回收垃圾

    输入废旧电池,显示没收入数据库:

    纸张属于回收垃圾

    垃圾分类:

    查询的物品,会自动记录,并且保存

    做垃圾回收也会有收益

    页面会记录你为社区垃圾回收做了多少贡献

    垃圾管理页面有垃圾分类详细列表:

    序号垃圾分类简介主要包含投放要求
    1有害垃圾废电池、废灯管、废药品、废油漆及其容器等对人体健康或者自然环境造成直接或者潜在危害的生活废弃物废电池、油漆桶、荧光灯管、废药品及其包装物等投放时请注意轻放 易破损的请连带包装或包裹后轻放 如易挥发,请密封后投放
    2湿垃圾日常生活垃圾产生的容易腐烂的生物质废弃物剩菜剩饭、瓜皮果核、花芬绿植、过期食品等纯流质的食物垃圾、如牛奶等,应直接倒进下水口 有包装物的湿垃圾应将包装物去除后分类投放、包装物请投放到对应的可回收物或干垃圾容器
    3干垃圾即其他垃圾,是指除可回收物、有害垃圾、湿垃圾以外的其它生活废弃物餐盒、餐巾纸、湿纸巾、卫生间用纸、塑料袋、食品包装袋、污染严重的纸、烟蒂、纸尿裤、一次性杯子、大骨头、贝壳、花盆、陶瓷等尽量沥干水分 难以辨识类别的生活垃圾投入干垃圾容器内
    4可回收垃圾废纸张、废塑料、废玻璃制品、废金属、废织物等适宜回收、可循环利用的生活废弃物酱油瓶、玻璃瓶、平板玻璃、易拉罐、饮料瓶、洗发水瓶、塑料玩具、书本、报纸、广告单、纸板箱、衣服、床上用品等轻投轻放 清洁干燥,避免污染,费纸尽量平整 立体包装物请清空内容物,清洁后压扁投放 有尖锐边角的、应包裹后投放

    垃圾列表

    垃圾分类统计

    全国垃圾投放统计

    关于垃圾分类的公告

    垃圾分类问题文件

    4、 业务流程分析

    因为整个系统的功能会以用户角色加以区分,及不同的角色间的功能是相对独立的,所以整个业务流程的设计基本也是可以按角色分为两类,一类是游客的流程,另一类就是管理员管理系统的流程。

    游客的流程图如下所示:

    管理员管理系统的流程图如下所示:

    5 、系统功能模块分析

    根据系统功能分析,将整个系统的功能模块规划为如下的功能模块图。

    6、 数据库分析

    数据库表如图所示:

    信息系统的主要任务是通过大量数据获得管理所需要的信息,这就要求系统本身能够存储和管理大量的数据,而这一功能的实现必须借助大型数据库系统。本系统的开发选择MySQL作为后台数据库开发工具。

    (1)概念模型设计

    概念模型用于信息世界的建模,与具体的DBMS无关。为了把现实世界中的具体事物抽象、组织为某一DBMS支持的数据模型。人们常常首先将现实世界抽象为信息世界,然后再将信息世界转换为机器世界。也就是说,首先把现实世界中的客观对象抽象为某一种信息结构,这种信息结构并不依赖于具体的计算机系统和具体的DBMS,而是概念级的模型,然后再把模型转换为计算机上某一个DBMS支持的数据模型。实际上,概念模型是现实世界到机器世界的一个中间层次。

    信息世界中包含的基本概念有实体和联系。

    (1) 实体 (entity)

    客观存在并可相互区别的事物称为实体。实体可以是具体的人、事、物,也可以是抽象的概念或联系。例如,一个学生、一门课、一个供应商、一个部门、一本 书、一位读者等都是实体。

    (2) 联系 (relationship)

    在现实世界中,事物内部以及事物之间是有联系的,这些联系在信息世界中反映为实体内部的联系和实体之间的联系。实体内部的联系通常是组成实体的各属性之间的联系。两个实体型之间的联系可以分为3类,一对一联系,(1:1);一对多联系(1 : n);多对多联系(m : n)。

    概念模型是对信息世界建模,所以概念模型应该能够方便、准确地表示信息世界中的常用概念。概念模型的表示方法很多,其中最为常用的是P.P.S.Chen于1976年提出的实体,联系方法(Entity-Relationship Approach)简记为E-R表示法)。该方法用E-R图来描述现实世界的概念模型,称为实体-联系模型,简称E-R模型。

    • 用户实体

    • 角色实体

    • 菜单实体

    • 垃圾实体

    • 圾分类实体

    (2)数据表设计

    数据库表设计主要是把概念结构设计时设计好的基本E-R图转换为与选用DBMS产品所支持的数据模型相符合的逻辑结构。它包括数据项、记录及记录间的联系、安全性和一致性约束等等。导出的逻辑结构是否与概念模式一致,从功能和性能上是否满足用户的要求,要进行模式评价。

    本系统数据库表如下:

    表admin (管理员表)

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY管理员id
    2usernamevarchar500YN用户名
    3passwordvarchar500YN密码

    表appointment

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2user_idbigint200YN
    3handle_user_idbigint200YN
    4phonevarchar2550YN
    5addressvarchar2550YN
    6app_timedatetime190YN
    7infovarchar2550YN
    8create_timedatetime190YN
    9statusint100YN
    10provincevarchar2550YN
    11areavarchar2550YN
    12cityvarchar2550YN

    表cart (购物车表)

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY
    2userIdint100YN
    3allPricedouble230YN商品总价

    表categorization

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2contentvarchar2550YN
    3typeint100YN
    4view_countbigint200YN0
    5valuedouble112YN
    6harmint100YN
    7infovarchar2550YN

    表childorder (子订单表(关联Order表和cart表))

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY子订单id
    2orderIdint100YN订单id(包含购物车和环保商城订单)
    3childOrderTypeint100YN子订单类型(1购物车 2环保商城订单)
    4goodsIdint100YN商品id

    表garbage_type

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY
    2tipvarchar2550YN
    3Includevarchar2550YN
    4askvarchar2550YN
    5typevarchar2550YN
    6create_timedatetime190YN

    表garbageorder (垃圾回收订单表)

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY
    2userIdint100YN用户id
    3addressIdint100YN地址id
    4garbageNamevarchar500YN垃圾名称
    5garbageTypeIdint100YN垃圾类型id
    6weightdouble230YN重量
    7moneydouble230YN价值积分(用户端看不到,管理员确认)
    8appointmentTimedatetime190YN预约上门时间
    9startTimedatetime190YN下单时间
    10endTimedatetime190YN取货时间
    11statusint100YN订单状态(1待取货 2已完成)

    表garbagetype (垃圾类型表)

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY垃圾类型id
    2garbageTypeNamevarchar500YN垃圾类型名称
    3garbageTipvarchar2550YN投放建议

    表goods (商品表)

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY商品id
    2goodsNamevarchar500YN商品名称
    3goodsTypeint100YN商品类型(1垃圾桶 2垃圾袋)
    4goodsDescvarchar2000YN商品描述
    5imageUrlvarchar2000YN商品图片url
    6pricedouble230YN商品单价
    7numberint100YN库存数量

    表notice

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2contentvarchar50000YN
    3view_countbigint200YN
    4create_timedatetime190YN
    5titlevarchar2550YN

    表order (环保商城订单表)

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idint100NY订单id
    2totalPricedouble170YN商品总价
    3userIdint100YN用户id
    4addressIdint100YN地址id
    5startTimedatetime190YN下单时间
    6endTimedatetime190YN到货时间
    7isStatusint100YN订单状态(1待付款 2待收货 3已完成)

    表page

    编号名称数据类型长度小数位允许空值主键默认值说明
    1page_idint100NY自增主键
    2parent_idint100YN父页面id
    3namevarchar2550YN页面名称
    4urlvarchar2550YN页面地址
    5level_typeint100YN页面层级
    6level_indexint100YN页面索引
    7delete_flagint100NN0是否删除
    8descvarchar2550YN描述

    表role

    编号名称数据类型长度小数位允许空值主键默认值说明
    1role_idint100NY自增主键
    2namevarchar500YN类型名称
    3descvarchar2550YN描述

    表role_page

    编号名称数据类型长度小数位允许空值主键默认值说明
    1rp_idint100NY主键自增
    2role_idint100YN角色id
    3page_idint100YN页面id

    表search

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2contentvarchar2550YN
    3user_idbigint200YN
    4view_countbigint200YN0
    5create_timedatetime190YN

    表user

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2ageint100YN
    3namevarchar2550YN
    4passwordvarchar2550YN
    5emailvarchar2550YN
    6infovarchar2550YN
    7imgvarchar2550YN
    8provincevarchar2550YN
    9phonevarchar2550YN
    10cityvarchar2550YN
    11addressvarchar2550YN
    12create_timedatetime190YN
    13areavarchar2550YN

    表user_garbage

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2user_idbigint200YN
    3gramdouble112YN
    4typeint100YN
    5cityvarchar2550YN
    6create_timedatetime190YN
    7provincevarchar2550YN
    8areavarchar2550YN
    9titlevarchar2550YN垃圾名
    10moneydouble122YN

    表user_rank

    编号名称数据类型长度小数位允许空值主键默认值说明
    1idbigint200NY
    2user_idvarchar2550YN
    3recyclable_gramdouble112YN
    4dry_gramdouble112YN
    5wet_gramdouble112YN
    6harmful_gramdouble112YN
    7recyclable_rankdouble112YN
    8dry_rankint100YN
    9wet_rankint100YN
    10harmful_rankint100YN
    11rankint100YN
    12city_rankint100YN
    13create_timedatetime190YN

    表user_role

    编号名称数据类型长度小数位允许空值主键默认值说明
    1ur_idint100NY自增主键
    2user_idvarchar1000YN用户id
    3role_idint100YN角色id

    第5章 系统详细实现

    5.1 配置文件

    图5-1 resource目录

    如上图所示,首先第一个文件是application文件,这个文件里面撰写的主要是Springboot框架的一些配置

    server.port=8080
    debug=true
    ##锟斤拷sql执锟斤拷锟斤拷锟斤拷印锟斤拷志
    logging.level.com.gcms.mapper=debug
    ###############################MySQL锟斤拷锟捷匡拷锟斤拷锟斤拷###############################
    spring.datasource.name=test
    spring.datasource.url=jdbc:mysql://localhost:3306/garbage?characterEncoding=UTF-8&serverTimezone=GMT%2b8&useSSL=false
    spring.datasource.username=root
    spring.datasource.password=root
    spring.datasource.driverClassName=com.mysql.cj.jdbc.Driver
    spring.datasource.type=com.alibaba.druid.pool.DruidDataSource
    ###########################Mapper锟斤拷锟斤拷###############################
    logging.level.org.springframework.web=DEBUG
    #Mybatis
    mybatis.type-aliases-package=com.gcms
    mybatis.mapper-locations=classpath:mapper/*.xml
    ###########################Mybatis锟斤拷锟斤拷###############################
    spring.datasource.druid.initial-size=10
    spring.datasource.druid.min-idle=10
    spring.datasource.druid.max-active=200
    spring.datasource.druid.max-wait=60000
    spring.datasource.druid.time-between-eviction-runs-millis=60000
    spring.datasource.druid.min-evictable-idle-time-millis=300000
    spring.datasource.druid.validation-query=SELECT 1 FROM DUAL
    spring.datasource.druid.test-while-idle=true
    spring.datasource.druid.test-on-borrow=false
    spring.datasource.druid.test-on-return=false
    spring.datasource.druid.pool-prepared-statements=true
    spring.datasource.druid.max-pool-prepared-statement-per-connection-size=20
    spring.datasource.druid.filters=stat,wall,log4j
    #spring.profiles.active=prod
    #锟斤拷锟絀E 锟斤拷示锟斤拷锟斤拷为NaN
    spring.jackson.date-format=yyyy/MM/dd HH:mm:ss
    logging.level.org.springframework.boot.autoconfigure=ERROR
    #spring.jackson.time-zone=GMT+8
    # Freemarker 模锟斤拷锟斤拷锟斤拷
    #锟斤拷示锟斤拷锟叫的凤拷锟绞讹拷锟斤拷锟斤拷锟斤拷态锟斤拷源路锟斤拷锟斤拷
    spring.mvc.static-path-pattern=/**
    #锟斤拷锟斤拷锟斤拷锟绞撅拷锟斤拷镁锟教拷锟皆达拷锟铰凤拷锟?spring.resources.static-locations=classpath:/static/
    spring.thymeleaf.cache=false
    spring.thymeleaf.prefix=classpath:/html/
    spring.thymeleaf.suffix=.html
    spring.thymeleaf.mode=HTML
    spring.thymeleaf.encoding=UTF-8
    spring.thymeleaf.servlet.content-type=text/html
    
    #config page 锟斤拷锟矫凤拷页锟斤拷锟?pagehelper.helperDialect=mysql
    pagehelper.reasonable=true
    pagehelper.supportMethodsArguments=true
    pagehelper.params = count=countSql
    pagehelper.pageSize=10
    
    #锟较达拷锟侥硷拷锟斤拷锟斤拷
    spring.servlet.multipart.maxFileSize=10MB
    spring.servlet.multipart.maxRequestSize=10MB
    
    ###锟斤拷示SQL锟斤拷洳匡拷锟?log4j.logger.com.ibatis=DEBUG
    log4j.logger.com.ibatis.common.jdbc.SimpleDataSource=DEBUG
    log4j.logger.com.ibatis.common.jdbc.ScriptRunner=DEBUG
    log4j.logger.com.ibatis.sqlmap.engine.impl.SqlMapClientDelegate=DEBUG
    log4j.logger.Java.sql.Connection=DEBUG
    log4j.logger.java.sql.Statement=DEBUG
    log4j.logger.java.sql.PreparedStatement=DEBUG
    
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65

    。然后是加载config.properties文件的数据库文件,这个文件主要写的是存储的路径

    而在加载配置文件开始,就是logback-spring.xml,这个文件是日志生成的配置文件,用撰写日志生成的格式和存放的位置,这样就不多赘述。

    5.2 登录界面

    在登录界面,主要实现的功能是拦截器和判断,下面我会从这两个部分去介绍登录界面,最终的效果图如下图所示。

    图5-7 登录界面

    首先从判断方面介绍,这个登录界面的大致流程就是用户在用户名文本框和密码文本框中输入自己的编号和对应的密码,然后填写正确的验证码,填写完毕以后点击下面的登录按钮,如果全部的信息正确就可以显示登录成功,然后通过后端处理器的判断,可以知道登录的身份是管理员还是用户,如果是管理员,则进入管理系统,用户则进入用户系统。

    $.ajax({
       type:"POST",
       async:true,  //默认true,异步
       data:param,
       dataType:'json',
       url:"/login",
       success:function(data){
          if(data.result == "success"){
             window.location.href = "/main";
          }else if(data.message == "PASSWORD_ERR" || data.message == "USERNAME_NOT_EXIST"){
             layer.alert('用户名或密码错误', {icon: 2});
             $("#name").val("");
             $("#password").val("")
          }else{
             layer.alert('登陆失败!请找管理员授权!', {icon: 2});
          }
        },
        error:function() {
           layer.alert('系统错误,服务器正忙!', {icon: 2});
        }
    });
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21

    验证密码是否正确:

    /**
     *      Description: 登录server <BR>
     *      Remark: <BR>
     * @param username 用户名
     * @param password 密码
     * @return <BR>
     */
    @Override
    public ResultMap login(String username, String password) {
       // 从SecurityUtils里边创建一个 subject
       Subject subject = SecurityUtils.getSubject();
       // 在认证提交前准备 token(令牌)
       UsernamePasswordToken token = new UsernamePasswordToken(username, MD5.md5(password));
       // 执行认证登陆
       try {
          subject.login(token);
       }catch (Exception e) {
          return resultMap.fail().message(e.getMessage());
       }
       User user = (User) subject.getPrincipal();
       // 根据权限,指定返回数据
       List<String> role = userRoleMapper.getRoles(user.getId()+"");
       if (!role.isEmpty()) {
          logger.info("欢迎登录------您的权限是{}", role);
          return resultMap.success().message("欢迎登陆");
       }
       return resultMap.fail().message("权限错误!");
    }
    
    /**
     *      Description: 检测用户旧密码是否正确 <BR>
     *      Remark: <BR>
     * @param password
     * @return <BR>
     */
    @Override
    public boolean checkUserPassword(String password) {
       Subject subject = SecurityUtils.getSubject();
       User user = (User) subject.getPrincipal();
       // 防止session失效报错
       if (null != user) {
          String pass = user.getPassword();
          if (pass != null && pass.equals(MD5.md5(password))) {
             return true;
          }
       }
       return false;
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49

    5.3 垃圾分类查询页面

    《垃圾分类查询管理系统》的垃圾分类查询页面如下图所示,有一个搜索栏提供浏览者搜索自己所要查询的垃圾所属的分类。在搜索栏的下方为所有垃圾分类名称、图标及描述的展示,供浏览者快速了解个垃圾分类的具体含义。

    下图为搜索“车厘子核”对应的搜索结果,页面明确显示了“车厘子核”所属的垃圾分类,并且对该分类进行了进一步描述,例举了属该分类的常见垃圾以及该类垃圾的投放要求。

    下面以代码为例来说明该功能的具体实现。下面代码为该功能的控制器代码实现,接受用户请求并响应的controller实现如下。

    @Controller
    @RequestMapping("/home")
    public class HomeController {
      
      @Autowired
      private RubbishCategoryService rubbishCategoryService;
      
      @Autowired
      private RubbishService rubbishService;
      
      /**
       * 访问网站主页
       * @param model
       * @return
       */
      @RequestMapping(value="/index",method=RequestMethod.GET)
      public ModelAndView index(ModelAndView model){
        model.setViewName("home/index");
        return model;//WEB-INF/views/+system/index+.jsp = WEB-INF/views/system/index.jsp
      }
      /**
       * 搜索垃圾分类处理
       * @param model
       * @return
       */
      @RequestMapping(value="/search",method=RequestMethod.GET)
      public ModelAndView search(@RequestParam(name="k",required=false,defaultValue="") String name,ModelAndView model){
        RubbishCategory rubbishCategory = null;
        if(!StringUtils.isEmpty(name)){
          //先查询垃圾表
          List<Rubbish> rubbishList = rubbishService.findByName(name);
          if(rubbishList != null && rubbishList.size() > 0){
            rubbishCategory = rubbishList.get(0).getRubbishCategory();
          }else{
            //若垃圾表未查询到,再查询分类表内的common中是否有
            List<RubbishCategory> rubbishCategoryList = rubbishCategoryService.findByCommon(name);
            if(rubbishCategoryList != null && rubbishCategoryList.size() > 0)
              rubbishCategory = rubbishCategoryList.get(0);
          }
        }
        model.addObject("k", name);
        model.addObject("rubbishCategory", rubbishCategory);
        model.setViewName("home/search");
        return model;
      }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46

    垃圾分类对应的实体类如下:

    @Component
    public class RubbishCategory {
      private Long id;//id,设置自增
      private String name;//垃圾分类名称
      private String explain;//解释说明
      private String require;//处置要求
      private String common;//常见垃圾
      public Long getId() {
        return id;
      }
      public void setId(Long id) {
        this.id = id;
      }
      public String getName() {
        return name;
      }
      public void setName(String name) {
        this.name = name;
      }
      public String getExplain() {
        return explain;
      }
      public void setExplain(String explain) {
        this.explain = explain;
      }
      public String getRequire() {
        return require;
      }
      public void setRequire(String require) {
        this.require = require;
      }
      public String getCommon() {
        return common;
      }
      public void setCommon(String common) {
        this.common = common;
      }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38

    垃圾分类的Dao层及对应的mybati配置对应如下,通过下面配置实现了垃圾分类实体持久化的各种方法:

    // “垃圾分类”支持的所有方法
    @Repository
    public interface RubbishCategoryDao {
      public RubbishCategory findByName(String name);
      public int add(RubbishCategory rubbishCategory);
      public int edit(RubbishCategory rubbishCategory);
      public int delete(Long id);
      public List<RubbishCategory> findList(Map<String, Object> queryMap);
      public int getTotal(Map<String, Object> queryMap);
      public List<RubbishCategory> findByCommon(String name);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    <?xml version="1.0" encoding="UTF-8"?>
    <!DOCTYPE mapper
    PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
    "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
    <mapper namespace="com.ischoolbar.programmer.dao.admin.RubbishCategoryDao">
      <!-- 根据垃圾分类名查找垃圾分类 -->
      <select id="findByName" parameterType="String" resultType="RubbishCategory">
        select * from rubbish_category where name = #{name}
      </select>
      <!-- 根据常见垃圾分类名查找垃圾分类 -->
      <select id="findByCommon" parameterType="String" resultType="RubbishCategory">
        select * from rubbish_category where common like '%${value}%'
      </select>
      <!-- 添加垃圾分类 -->
      <insert id="add" parameterType="RubbishCategory">
        insert into rubbish_category(id,`name`,`explain`,`require`,`common`) values(null,#{name},#{explain},#{require},#{common})
      </insert>
      <!-- 修改垃圾分类 -->
      <update id="edit" parameterType="RubbishCategory">
        update rubbish_category set `name` = #{name},`explain` = #{explain},`require` = #{require},`common` = #{common} where id = #{id}
      </update>
      <!-- 删除垃圾分类 -->
      <delete id="delete" parameterType="Long">
        delete from rubbish_category where id = ${value}
      </delete>
      <!-- 分页获取垃圾分类列表 -->
      <select id="findList" parameterType="Map" resultType="RubbishCategory">
        select * from rubbish_category where 1 = 1 
        <if test="name != null">
          and `name` like '%${name}%' 
        </if>
        <if test="offset != null and pageSize != null">
          limit #{offset},#{pageSize}
        </if>
      </select>
      <!-- 获取符合结果的总记录数 -->
      <select id="getTotal" parameterType="Map" resultType="Integer">
        select count(*) from rubbish_category where 1 = 1 
        <if test="name != null">
          and `name` like '%${name}%' 
        </if>
      </select>
    </mapper>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43

    service层在将Dao层的方法进行进一步的封装:

    @Service
    public class RubbishCategoryServiceImpl implements RubbishCategoryService {
      @Autowired
      private RubbishCategoryDao rubbishCategoryDao;
    
      @Override
      public RubbishCategory findByName(String name) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.findByName(name);
      }
    
      @Override
      public int add(RubbishCategory rubbishCategory) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.add(rubbishCategory);
      }
    
      @Override
      public int edit(RubbishCategory rubbishCategory) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.edit(rubbishCategory);
      }
    
      @Override
      public int delete(Long id) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.delete(id);
      }
    
      @Override
      public List<RubbishCategory> findList(Map<String, Object> queryMap) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.findList(queryMap);
      }
    
      @Override
      public int getTotal(Map<String, Object> queryMap) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.getTotal(queryMap);
      }
    
      @Override
      public List<RubbishCategory> findByCommon(String name) {
        // TODO Auto-generated method stub
        return rubbishCategoryDao.findByCommon(name);
      }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47

    通过html将分类信息展示给用户的前端代码如下,下面的代码仅展示了显示查询返回分类信息部分的ht实现,其它一些部分为减少篇幅而省略:以上便是用户浏览网页并查询对应垃圾所有分类的具体代码实现。

    <c:if test="${not empty k}">
    <c:if test="${empty rubbishCategory }">
    <div class="row"><div class="col-md-1 col-xs-0"></div><div class="col-md-9 col-xs-12"><div class="row"><div class="col-md-12 col-xs-12" style="color:red;">未查到完全匹配字段。</div></div></div></div>
    <br>
    </c:if>
    </c:if>
    <c:if test="${not empty rubbishCategory }">  
      <div class="row">
        <div class="col-md-1 col-xs-0"></div>
        <div class="col-md-9 col-xs-12">
          <h1 style="text-align: left;">
            <span style="color:#D42121;">${k }</span>
            <span style="color:#FBbC28;">&nbsp;属于&nbsp;</span>
            <span style="#2e2a2b">${rubbishCategory.name }</span>
          </h1>
        </div>
      </div>
    <br>
    <div class="row">
        <div class="col-md-1 col-xs-0"></div>
        <div class="col-md-9 col-xs-12">
          <div class="row">
            <div class="col-md-12 col-xs-12"><h3 style="text-align: left;">${rubbishCategory.name }是指</h3></div>
            <div class="col-md-12 col-xs-12">${rubbishCategory.explain }</div>
          </div>
        </div>
    </div>
    <br>
    <div class="row">
        <div class="col-md-1 col-xs-0"></div>
        <div class="col-md-9 col-xs-12">
          <div class="row">
            <div class="col-md-12 col-xs-12"><h3 style="text-align: left;">${rubbishCategory.name }主要包括</h3></div>
            <div class="col-md-12 col-xs-12">${rubbishCategory.common }</div>
          </div>
        </div>
    </div>
    <div class="row">
        <div class="col-md-1 col-xs-0"></div>
        <div class="col-md-9 col-xs-12">
          <div class="row">
            <div class="col-md-12 col-xs-12"><h3 style="text-align: left;">${rubbishCategory.name }投放要求</h3></div>
            <ul>
              <li>${rubbishCategory.require }</li>
            </ul>
          </div>
        </div>
      </div>
      <br>
    </c:if>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50

    5.4 后台主页面

    图为后台主页面的实现,左边为供用户选择的操作种类,右边为进行具体操作的工作台,可以看到用户可以进行系统设置-用户管理、页面管理、角色管理; 我的-首页、搜索记录、我的收益; 贡献管理-贡献管理、随机数据、每日垃圾、贡献记录; 垃圾管理-垃圾管理、分类管理、分类列表、垃圾列表、修改奖励; 数据分析-全国统计、分类统计、投放统计; 公告管理-公告管理、公告列表、必布公告;

    第6章 系统测试

    6.1测试意义

      在此系统进行初步实现之后,开始进行对系统进行测试,找出系统中存在的Bug,通过测试,用提交的Bug报告来为以后软件的改进提供标准和参考,能够在以后的系统改进中找到依据。

    测试后的软件各模块基本功能可以顺利进行,尽可能的提高软件的健壮性。

    6.2 测试方法

    • 从是否关心软件内部结构和具体实现的角度划分:黑盒测试和白盒测试;

    • 从是否执行程序的角度:静态测试和动态测试;

    • 从软件开发的过程按阶段划分有:单元测试、集成测试、确认测试、系统测试、验收测试、回归测试、Alpha测试、Beta测试;

    单元测试又称模块测试,是针对软件设计的最小单位 ─ 程序模块(这里所说的程序模块在Java中一个模块就是一个方法),进行正确性检验的测试工作。其目的在于发现各模块内部可能存在的各种差错。单元测试需要从程序的内部结构出发设计测试用例。多个模块可以平行地独立进行单元测试。

    功能特性管理员登入验证
    测试目的验证是否输入合法的信息
    测试数据用户名称:admin 密码:123456 验证码:1851
    测试内容操作描述数据期望结果实际结果测试状态
    1输入用户姓名和验证码,按“登陆”按钮。用户姓名:admin,密码为空验证码:1851显示警告信息“用户名或密码为空!”显示警告信息“用户名或密码为空!”与期望结果相同
    2输入密码和验证码,按“登陆”按钮。用户姓名为空,密码:123456验证码:1851显示警告信息“用户名或密码为空!”显示警告信息“用户名或密码为空!”与期望结果相同
    3输入用户姓名和密码以及验证码,按“登陆”按钮。用户姓名:xxxxxx,密 码:1111111验证码:1851显示警告信息“用户名或密码误!”显示警告信息“用户名或密码误”与期望结果相同
    4输入用户姓名和密码以及验证码,按“登陆”按钮。用户姓名:admin,密 码:123456验证码:1111显示警告信息“验证码错误!”显示警告信息“验证码错误”与期望结果相同
    5输入用户姓名和密码和验证码,按“登陆”按钮。用户名:admin,密 码:123456验证码:1851正确登入到会员操作界面正确登入到会员操作界面与期望结果相同

    🧐 微信公众号:搜索《程序员小王》
    📒原创不易,如果觉得不错请给我一个,三连、收藏、加关注,需要资料的同学可以私聊我!
    😉 有问题可以点击下方私信交流 😆
    如果我的博客对您有帮助 再次希望大家点赞 👍 收藏 ⭐留言 📝 啦 、感谢大家对我支持,让我有了更多的创作动力,希望我的博客能帮助到你

    • 如果需要项目源码可以私聊我获取!
  • 相关阅读:
    总结网络中的一些基本概念——javaee
    SpringCloud学习(七)----- 使用Feign调用别的微服务的方法
    C# 图像灰化处理方法及速度对比
    UI自动化测试 | Jenkins配置优化
    在 Git Bash 中为 vim 设置 Dracula 配色
    FastAPI+aiohttp+uvicorn快速搭建个人服务
    02_SpingBoot 入门案例
    家政服务APP
    一起学docker系列之二深入理解Docker:基本概念、工作原理与架构
    被生活、房贷车贷压得喘不过气的35岁程序员,拿什么去谈追求~
  • 原文地址:https://blog.csdn.net/weixin_44385486/article/details/125283681