基于java的企业人事管理系统的设计与实现(含源文件)

欢迎添加微信互相交流学习哦!

二维码

项目源码:https://gitee.com/oklongmm/biye

企业人事管理系统的设计与实现
摘    要

人事管理实施的好坏关系到企业的生存与长远发展。传统的人事管理,繁琐而且效率低下,对于企业的人事管理部门来说,非常需要一个操作方便、功能实用、能够满足本企业对员工信息管理的系统。
企业人事管理系统是一个面向企业人事部门工作人员,为其提供服务的综合信息系统,管理人员通过本系统可以完成相关的日常工作。系统采用了面向对象的分析与设计,开发采用Grails架构。系统主要功能有:奖惩管理、工资管理、请假管理、考勤管理、员工管理、系统管理和招聘管理等。
本系统可以减少传统人力资源管理带来的诸多弊端,大大节约人力资源管理的成本。它可以应用于中小型企业的管理,具有一定的应用价值。系统界面友好,易于操作。
关键词: 企业;人事管理;Grails;MVC
 
Design and Implementation of Enterprise
Personnel Management System

Abstract

 The quality of the implementation of personnel management related to the survival and long-term development. Traditional personnel management is cumbersome and inefficient, so a system operates easily and meets the practical function of enterprise information management to employee is needed for personnel management department.
The enterprise personnel management system is the system which is to provide an integrated information system services for the Enterprise personnel department. Managers can do their daily work through the system. The object-oriented analysis and design is used by the system, the Grails framework is used in development. The main function of the system: rewards and punishments management, salary management, leave management, attendance management, staff management, system management and Recruitment management.
The problem which the traditional human resource management brings was reduced and the cost of human resource management can be saved by using this system. The system which has a certain value can be applied to small business management. It has a friendly interface and easy operation. 
Keywords:Enterprise; Personnel Management; Grails; MVC
 
目  录

引  言    1
第1章 绪论    2
1.1课题研究的背景    2
1.2课题研究的意义    2
1.3课题研究的发展趋势    3
1.4开发工具及相关技术介绍    4
1.4.1开发技术    4
1.4.2开发环境    4
1.4.3开发方案    4
第2章 需求分析    6
2.1编写目的    6
2.2企业人事管理系统的定义    6
2.3环境需求    6
2.4可行性分析    6
2.4.1经济可行性    6
2.4.2技术可行性    6
2.4.3操作可行性    7
2.5功能需求    7
2.5.1部门管理需求    7
2.5.2招聘管理需求    7
2.5.3员工管理需求    7
2.5.4考勤管理需求    7
2.5.5奖惩管理需求    7
2.5.6系统管理需求    7
2.5.7薪资管理需求    8
2.5.8请假管理需求    8
2.6用例图    8
2.7数字字典定义    11
第3章 概要设计    12
3.1设计目的    12
3.2系统功能结构图    12
3.3数据库设计    13
3.3.1数据库分析    13
3.3.2系统E-R图    14
第4章 详细设计    22
4.1设计目的    22
4.2模块设计    22
4.2.1验证用户功能模块    22
4.2.2管理员导航主页面功能模块    23
4.2.3员工导航主页面功能模块    24
4.2.4部门管理模块    25
4.2.5添加模块    26
4.2.6编辑模块    27
4.2.7添加员工模块    28
4.2.8修改密码模块    29
4.2.9自动生成工资模块    30
4.2.10自动生成月出勤记录模块    31
第5章 系统实现    33
5.1数据库配置的实现    33
5.2登录的实现    33
5.3搜索功能实现    34
5.4修改密码的实现    36
5.5自动生成工资的实现    37
5.6权限设置的实现    38
第6章 测试    41
6.1测试策略说明    41
6.2测试用例    41
6.2.1系统登录管理模块    41
6.2.2系统管理模块    42
6.2.3部门管理模块    43
6.2.4招聘管理模块    44
6.2.5员工管理模块    45
6.2.6薪资管理模块    46
6.2.7考勤管理模块    47
6.2.8修改密码模块    48
6.3测试结果    49
结论与展望    50
致  谢    51
参考文献    52
附录A:外文文献及译文    53
附录B:主要参考文献的题录及摘要    58
附录C:部分源代码    61

 
插图清单

图1-1 B/S层次结构图    5
图2-1 职工的用例图    9
图2-2 管理员的用例图    10
图3-1 系统功能模块总图    12
图3-2 管理员子系统结构图    13
图3-3 职工子系统结构图    13
图3-4 管理员的实体E-R图    14
图3-5 部门的实体E-R图    14
图3-6 职位的实体E-R图    15
图3-7 出勤信息表的实体E-R图    15
图3-8 奖惩表的实体E-R图    16
图3-9 薪资管理信息表的实体E-R图    16
图3-10 请假信息表的实体E-R图    17
图3-11 招聘信息表实体E-R图    17
图3-12 系统总的E-R图    18
图4-1用户验证图    23
图4-2管理员导航主页面    24
图4-4部门管理页面    26
图4-5添加模块页面    27
图4-6编辑模块页面    28
图4-7添加员工的信息页面    29
图4-8修改密码信息页面    30
图4-9自动生成工资页面    31
图4-10自动生成月出勤表页面    32
图6-1 企业人事管理系统登陆错误界面    42
图6-2 用户详情显示    43
图6-3 部门显示列表页面    44
图6-4 部门显示详情页    44
图6-5 应聘人员显示列表页面    45
图6-6 员工查询结果页面    46
图6-7 薪资查询结果列表    46
图6-8 自动生成薪资详情列表界面    47
图6-9 自动生成月考勤表    48
图6-10 友好提示页面1    49
图6-11 友好提示页面2    49

 
插表清单

表3-1 管理员表    18
表3-2 部门表    19
表3-3 员工表    19
表3-4 出勤信息表    19
表3-5 惩罚信息表    19
表3-6 请假信息表    20
表3-7 薪资信息表    20
表3-8 招聘信息表    21
表4-1 验证用户功能模块的IPO    22
表4-2 管理员导航主界面功能模块IPO    23
表4-3 员工导航主界面的功能模块IPO    24
表4-4 部门管理模块的IPO    25
表4-5 添加模块的IPO    26
表4-6 编辑模块的IPO    27
表4-7 添加员工模块的IPO    28
表4-8 修改密码模块的IPO    29
表4-9 自动生成工资模块的IPO    30
表4-10 自动生成考勤记录模块的IPO    31
 
引  言
 
我们国家一些中小型企业还是用传统的人工方式管理文件档案,这种管理方式存在着效率低、保密性差等的缺点。另外时间一长,将产生大量的文件和数据,这对于查找、更新和维护都带来了不少的困难。作为计算机应用的一部分,使用计算机对人事档案信息进行管理,具有手工管理所无法比拟的优点。所以建立人事管理系统,使人事管理自动化,提高信息处理的速度和准确性十分必要。
人事管理的对象是一个单位或若干单位中员工的基本信息,这些信息是在变化的。人事部门要为本单位、上级部门提供准确的统计数据。由于人员众多、数据源复杂、统计管理工作闲难,以往每做一项工作,都需要花费很多的精力和时间。传统的人工管理方式存有诸如效率低,保密性差,查找、更新、维护困难等各种各样的缺点。因此,人事管理系统能够为用户提供充足的信息和快捷的查询手段。使用计算机对人事资料进行管理,会给应用者带来很多方便,例如检索迅速、查找方便、可靠性高、存储量大、保密性好、寿命长、成本低等。这些优点能够降低了企业人事管理的人力和成本,并提高了企业人事管理的效率,使企业管理真正实现人力资源的网络化、系统化、科学化。从而提高了企业内部的管理水平,提高了企业在市场竞争中的综合竞争力。同时,这也是企业与世界先进管理技术接轨的重要条件。
我们针对如此,设计了一套企业人事管理系统。企业人事管理系统采用的是计算机化管理,系统做的尽量人性化,使用者会感到操作非常方便,管理人员需要做的就是将数据输入到系统的数据库中去。由于数据库的存储容量相当大,而且比较稳定,适合较长时间的保存,也不容易丢失。
 
第1章 绪论
1.1课题研究的背景
据统计,目前美国在财务会计上占有90%的工作由计算机完成,人事管理中80-100%的信息处理由计算机完成,计划管理是80—90%,在计算机应用发展较快的国家中,计算机应用于经济管理的占80%,由此可以看出,在国外经济管理是计算机应用的主要领域。因此,信息资源的开发和利用已被确立为国民经济信息的核心内容,信息数字化,传输的网络化是缩小发展中国家与发达国家差距的捷径。
近些年,一些较大的企业经常自行开发人力资源管理软件,这样做有一定的好处,如成本低廉,上级单位一次开发,基层单位可以重复利用,而且一定程度上能满足个性化需求。但是实践证明,这种开放方式一般难以成功。一方面,企业内部开发人员往往缺乏项目经验,导致与最终用户的需求相悖;另一方面,这种形式的软件开发不参与市场竞争,仅仅是供给内部使用,有可能导致开发人员敷衍了事,开发的系统不能真正起到作用。
与此同时,由于我国正处在由传统管理方式向人力资源管理过渡的转型时期,企业中的管理方法从思想到行动都发生着巨大的变化,处于摸索中的人力资源管理随时都可能发生这样那样的变革,这就对人力资源管理软件提出了巨大的挑战,软件如果不能够随着变革而自行适应,那么,这个软件就没有生命力。
国外人力资源管理系统与国内的相比,优势主要体现为:具有雄厚的实力,在技术力量的培养、研发、市场推广等方面大力投入;具有一定包括硬件厂商、数据库公司、咨询公司在内的合作伙伴,形成强强联手的格局。国外人力资源管理系统伴随着管理理论的发展,其设计思路蕴涵了先进的管理理念;国外人力资源管理系统起步较早,完整性和成熟度高,开发出了适用于不同行业的解决方案。西方发达国家已广泛使用人力资源管理系统,其他一些软件系统如ERP(企业资源计划)、WFM(工作流管理)等在开发过程中预留了与人力资源管理系统的接口,使得国外的人力资源管理系统今后的扩展难度降低。国外人力资源管理系统对于基于互联网技术的研究和支持不遗余力,以PeopleSoft为例,其最新版本是完全基于互联网架构的版本,使得其易用性大大加强。
从某种意义上来说,国外虽然有着较为成熟的产品,在成熟度、先进性上都要优于大多数的国内产品,但在我国大多数公司人力资源管理制度并不规范,这就导致了国外的产品实用性、有效性大打折扣,而且其价格过于昂贵,让国内企业难以接受。另一方面来说,我国企业受中华民族源远流长的文化影响,人力资源管理上比西方企业更强调人性化,而非制度化。这也是的国外软件开发商很难开发出符合中国企业需要的产品。
1.2课题研究的意义
中国是世界上人口最多的国家,目前有近14亿人口,劳动力人口有近8亿,约占世界劳动人口的25%(《中国统计年鉴》2008数据)。而对于如此庞大的劳动力人口,企业人事管理信息数字化已经成为趋势。
而我们国家中小型企业大多使用传统人工的方式管理文件档案,这种管理方式存在着效率低、保密性差等的缺点。另外时间一长,将产生大量的文件和数据,这对于查找、更新和维护都带来了不少的困难。作为计算机应用的一部分,使用计算机对人事档案信息进行管理,具有手工管理所无法比拟的优点。所以建立人事管理系统,使人事管理自动化,提高信息处理的速度和准确性十分必要。
当代社会已经进入了信息时代,随着企业规模的扩大,企业管理组织会变得越来越庞大和困难,而信息的处理与使用也变得越来越重要,它对于企业的决策者和管理者来说都至关重要,所以人事管理系统应该能够为用户提供充足的信息和快捷的查询手段。建立一套人事管理信息系统能够加快物资的周转速度,提高生产效率,加强管理的信息化手段,提高本单位的经济效益。从宏观上讲,顺应了社会的信息化、社会化潮流,缩短了整个社会化大生产的周期[13]。
人事管理的对象是一个单位或若干单位中员工的基本信息,这些信息是在变化的。人事部门要为本单位、上级部门提供准确的统计数据。由于人员众多、数据源复杂、统计管理工作闲难,以往每做一项工作,都需要花费很多的精力和时间。传统的人工管理方式存有诸如效率低,保密性差,查找、更新、维护困难等各种各样的缺点。因此,人事管理系统能够为用户提供充足的信息和快捷的查询手段。使用计算机对人事资料进行管理,会给应用者带来很多方便,例如检索迅速、查找方便、可靠性高、存储量大、保密性好、寿命长、成本低等。这些优点能够降低了企业人事管理的人力和成本,并提高了企业人事管理的效率,使企业管理真正实现人力资源的网络化、系统化、科学化。从而提高了企业内部的管理水平,提高了企业在市场竞争中的综合竞争力。同时,这也是企业与世界先进管理技术接轨的重要条件。
开发这样一套人事管理系统的主要意义是:
大幅度提高工作效率,使公司的人事干部从繁重琐碎的人事工作中解脱出来,把主要精力投入到日常工作中。
 用计算机数据库管理代替手工统计工作,并且对数据库中的各数据自动进行逻辑验证,使数据统计过程中的错漏减少到最低程度。
使各管理部门的信息管理工作规范化、高效化,大大简化数据汇总的工作量[11]。
1.3课题研究的发展趋势
世界经济发达国家的大中企业都拥有比较完备的企业信息系统,经济发达国家都是将经济信息服务于国民经济并取得辉煌成就的国家。随着经济体制的快速发展,国外有许多大型企业,设置首席信息经理(chief information officer.简称CIO)的高级职位,专门负责企业信息工作。据对美国500家大型企业的抽样调查,已有半数公司设立了CIO职位。CIO的出现标志着企业的经营管理和信息工作进入了一个新阶段。
在市场需求的推动下,我国企业信息管理工作这些年得到了很大的发展,对于企事业单位的人事管理部门来说,非常需要一个操作方便、功能实用、能够满足本企业对员工信息管理及需求的系统。企业人事管理系统逐步向能够满足以下的功能方向发展:
    可以真正地实现对企业人事的管理;
    系统的功能要符合本企业的实际情况;
    系统的功能操作要方便、易懂,不要有多余或复杂的操作;
    可以方便地对人事进行管理;
    具有检索迅速、查找方便、可靠性高、存储量大、保密性好、成本低等优点;
    可以帮助企业管理朝着科学化、规范化和信息化的发展。

1.4开发工具及相关技术介绍
1.4.1 开发技术
(1)Grails框架
    Grails采用动态方法减小了Java平台上进行Web开发的复杂度,不过与那些框架不同的是,Grails是构建在Spring和Hibernate等Java已有的技术之上的[7]。Grails是一个full-stack框架,它借助于核心技术与相关的插件来解决Web开发中方方面面的问题,其中包括:易于使用的基于Hibernate的对象-关系映射层;称为Groovy Server Pages的表现层技术;基于Spring MVC的控制器层,构建于Gant 上的命令行脚本运行环境;内置Jetty服务器,不用重新启动服务器就可以进行重新加载 利用内置的Spring 容器实现依赖注入;基于Spring的MessageSource核心概念,提供了对国际化的支持;基于Spring事务抽象概念,实现事务服务层 借助于功能强大的Groovy动态语言和领域特定语言,以上那些特性变得非常易用。
(2)JavaScript
JavaScript是一种基于对象和事件驱动并具有相对安全性的客户端脚本语言。同时也是一种广泛用于客户端Web开发的脚本语言,常用来给HTML网页添加动态功能,比如响应用户的各种操作。它最初由网景公司的Brendan Eich设计,是一种动态、弱类型、基于原型的语言,内置支持类。JavaScript是Sun公司的注册商标。JavaScript也可以用于其他场合,如服务器端编程。完整的JavaScript实现包含三个部分:ECMAScript,文档对象模型,字节顺序记号[1]。
1.4.2 开发环境
开发模式: 系统基于Browser/Server模式进行设计
开发工具:SpringSource Tool Suit9.2、JDK6.0
开发语言:Java、Groovy、Html、Javascript
开发系统:Linux
后台数据库:Mysql
服务器:采用Tomcat 6.0服务器
1.4.3 开发方案
 本系统选择B/S结构,B/S(Browser/Server)结构即浏览器和服务器结构,它是随着Internet技术的兴起,对C/S(Client/Server)结构的一种改进,如今主流的管理系统大都采用B/S结构。在这种结构下,用户工作界面是通过WWW浏览器来实现,极少部分事务逻辑在前端(Browser)实现,主要事务逻辑在服务器端(Server)实现[14],形成所谓三层3-tier结构。这样就大大简化了客户端电脑载荷,减轻了系统维护与升级的成本和工作量,降低了用户的总体成本(TCO)。其层次结构如图1-1所示:
 
图1-1 B/S层次结构图
 
 第2章 需求分析
2.1编写目的
软件需求是指用户对目标系统在功能、性能、行为、设计约束方面的期望,这种期望可能是原始的、笼统的,也可能是抽象的细节化的。软件需求分析工作主要目的是:在综合分析用户对系统提出的一组需求的基础上,构造一个从抽象到具体的逻辑模型表达软件将要实现的需求。其作为整个软件开发过程的指南,也是软件开发人员开发出符合用户要求的软件的基础。编制目的是为了使用户和软件开发者双方对该软件的初始规定有一个共同的理解,使之成为整个软件开发的基础。
2.2企业人事管理系统的定义
企业人事管理系统是一个面向企业人事部门工作人员,为其提供服务的综合信息管理系统人员通过本系统完成相关的日常工作,这些工作也是平常较为繁重的工作。员工的个人信息等等都记录在人事系统里进行管理。高效的人事管理可以提高企业的市场竞争力,使企业具有更强的凝聚力和活力。
企业人事部门主要工作:根据公司需要,对现有人才进行继续教育,加强公司的人力资源;对员工的信息管理,包括新员工的录入,员工信息的修改等;记录员工的奖惩、考勤等信息;处理员工的调动等。 
企业人事管理系统的主要任务是对人事档案进行整理,使得管理员能方便、快捷地对人事档案进行查询、统计、更新。通过该系统,使企业的人事管理工作系统化、规范化、自动化,从而提高企业人事管理的效率商务的发展,改变了传统市场经济的结构,形成了一个供给与需求信息完全透明化的自由竞争市场。市场分为产业市场和消费者市场,任何企业都与市场进行着物质、劳动力、信息的交换。
2.3环境需求
系统的名称:企业人事管理系统的设计与实现
操作系统:Linux
内存:建议512MB以上
硬盘空间:至少有50MB以上的磁盘空间来安装所需的组件
2.4可行性分析
2.4.1经济可行性
从该系统的开发和效益关系上讲,该系统的开发不需要花费太多的经费.因为设备费用可在原有局域网的基础上组织建成; 在国内,Grails所需要的平台SpringSource Tool Suit是一个免费的软件,同时该系统所使用的数据库软件 Mysql也完全不需要经济上的耗费。
2.4.2技术可行性
Java是目前国内比较流行的软件,具有高效、功能强大的特点。而本系统所用的Groovy是一种新兴的Java 2平台语言,Groovy代码能和Java代码很好的结合到一块去,同时Groovy语言在编写软件方面也有很强大的优势,首先是快速开发。再就是它是一个新的面向对象的语言,高效且安全,和Xml能很好的协作,强大的面向组件的开发。

2.4.3操作可行性
该系统的使用并不困难,具有友好的操作界面使用系统的工作人员,除了需要具备在Microsoft Windows平台上使用个人电脑的知识,并不需要特别的技术能力,只需要花费较少的时间去了解学习它,即可做到熟练操作使用。所以系统在操作上是可行的。
综上所述,通过技术、经济、操作的可行性研究与分析,我们得出开发“企业人事管理系统”是可行的。
2.5功能需求
企业人事管理系统通过计算机网络将客户端与服务器的数据库相连,将从客户端得到的信息进行处理,实现部门管理、员工管理、招聘管理、考勤管理、奖惩管理、薪资管理、系统管理、个人信息浏览等功能。以计算机为中心,实现企业人事管理的计算机自动化,为企业降低成本、提高工作效率、为人事部的经营决策提供及时精确的依据。
2.5.1部门管理需求
部门管理主要是实现四种功能:对部门的添加、删除、编辑和查询。添加信息包括部门编号、部门名称、部门描述和部门人数等信息。查询按部门名称和编号进行查询。
2.5.2招聘管理需求
招聘管理共实现两种功能:查看招聘人员,决定是否录用招聘人员。查看招聘人员时刻按照招聘人员的性别、年龄和应聘部门进行高级删选,如果决定录用人员,则在选项中进行修改。 
2.5.3员工管理需求
员工管理主要实现四种功能:添加、删除、编辑和查看员工。添加员工主要包括以下信息,员工账号、员工姓名、员工性别、员工年龄、员工身份证号、出生日期、联系电话、联系地址、部门、登记时间等,查看员工可以根据部门和员工姓名、编号进行删选。
2.5.4考勤管理需求
考勤管理主要有五个功能:添加编辑、删除每天的考勤信息,生成个人每月的考勤信息,考勤信息与工资相挂钩,考勤信息主要包括:出勤,缺勤、加班、迟到早退、出差和日期。根据日期可生成个人每月的考勤情况。
2.5.5奖惩管理需求
奖惩管理主要有三个功能:添加、删除和查看奖惩。奖惩包括一下信息,奖惩性质、奖惩项名称、原因、奖惩人员、奖惩日期和奖罚金额。奖惩金额与工资中的奖金想联系。
2.5.6系统管理需求
系统管理主要包括:添加,删除管理员和修改登录密码。添加管理员信息主要包括:管理员账号、管理员密码、管理员级别。

2.5.7薪资管理需求
薪资管理主要包括三个功能:添加员工薪资、删除员工薪资、自动生成工资和查看员工薪资。添加员工薪资主要有以下信息,员工编号、员工姓名、发放工资时间、基本工资、加班费、工龄、考勤费、奖惩金额等。查看员工薪资可以按照员工和发放时间进行查询。只要输入员工号便能自动生成所对应的工资,工资里面的加班费和考勤费等根据考勤表得出,而惩罚奖金根据奖惩表得到[12]。
2.5.8请假管理需求
请假管理主要有三个:申请请假、批准请假和查询请假记录。请假申请信息主要包括,请假起始时间、结束时间、请假原因、申请人编号和申请人信息。管理员看到请假申请后可以做出处理:是否批准请假。员工和管理员都可以查看请假记录,可进行请假。管理员可根据员工名字,编号和请假时间范围进行查询,而员工则只能查看自己的。
2.6用例图
用例是系统参与者与系统交互过程中需要完成的事务,识别用例最好的方法是从参与者开始,看他们是如何使用系统的。本系统有2个参与者,考虑到系统的功能,可将系统分为如下用例:职工用例和管理员用例[6]。
职工用例:职工是系统里面权限最低的,他可以使用的权限如下:
    职工登陆后浏览个人基本的信息;
    职工登陆后修改个人基本的信息;
    职工可以修改个人密码;
    职工还可以浏览个人考勤记录;
    职工还可以浏览个人奖惩记录;
    职工还可以浏览个人的薪资信息;
    职工可以浏览个人请假信息;
    职工可以请假。
职工的用例图如图2-1所示:
 
图2-1 职工的用例图
管理员用例:管理员权限是系统里面最高的,他所使用的权限如下
    部门管理:添加、编辑、查看和删除部门;
    招聘管理:录用招聘人员,查询招聘人员;
    员工管理:添加、编辑、删除、查看员工;
    出勤管理:添加、编辑、删除、查看出勤,统计创建月出勤;
    奖惩管理:添加、删除、查看奖惩;
    系统管理:添加、删除管理员,修改登录密码;
    薪资管理:添加、删除、查看员工薪资,自动生成薪资;
    请假管理:是否批准请假,请假记录查询。
例图如图2-2所示:
 
图2-2 管理员的用例图
2.7数字字典定义
数据字典是系统中各类数据描述的集合,是进行详细的数据收集和数据分析所获得的主要成果。
数据流条目:
管理员表=管理员账号+管理员密码+管理员级别   
员工表=员工编号+员工姓名+员工性别+员工年龄+员工身份证号+出生日期+联系电话+联系地址+部门+登记时间
部门信息表=部门编号+部门名称+部门描述+部门人数
出勤信息表=出勤编号+出勤+缺勤+出差+加班+迟到早退+性质+时间+员工编号+员工姓名
奖惩信息表=序号+奖惩性质+奖惩项名称+原因+奖罚金额+时间
薪资管理表=序号+员工编号+员工姓名+发放工资时间+基本工资+加班费+考勤费+出差补贴费+奖惩金额+应发工资
请假表=序号+请假起始时间+结束时间+请假原因+申请人编号+申请人姓名+状态+时间+请假天数
招聘信息表=序号+应聘人姓名+性别+年龄+员工身份证号+出生日期+联系电话+联系地址+应聘部门+应聘时间+是否录用

 
第3章 概要设计
3.1设计目的
通过企业人事管理系统可以使管理员快速高效地完成企业日常事务中的人事工作,降低人力资源管理的成本,使管理者能集中精力实现企业战略目标。企业人事管理系统的具体目标如下:
(1)界面设计美观友好、信息查询灵活、方便、快捷、准确、数据存储安全可靠;
(2)对企业人力资源管理的基本信息进行管理;
(3)管理企业的员工信息;
(4)实现企业招聘信息的管理功能;
(5)实现企业员工考勤的一系列相关信息的管理;
(6)员工薪酬信息的管理;
(7)系统用户信息的管理;
(8)系统运行稳定、安全可靠。
3.2系统功能结构图
企业人事管理系统满足管理员和普通员工两种角色的需求,不同的角色进入不同功能操作,它共分成两个子系统:管理员子系统和员工子系统。它的功能模块图如3-1所示:
 
图3-1 系统功能模块总图
根据对人事管理系统主要业务流程的分析可知,系统需要满足系统管理员应该具有的部门管理(添加、编辑、查看和删除部门),招聘管理(录用、查看招聘人员),员工管理(添加、编辑、删除和查看员工)、出勤管理(添加、查看、删除出勤记录、统计生成月出勤)、奖惩信息管理(添加、删除和查看奖惩信息),系统管理(添加、删除管理员,修改登录密码),请假管理(提交请假、请假审批、请假记录查询),薪资管理(添加、删除、查看薪资和自动生成薪资)[5]。系统的管理员子系统如图3-2所示:
 
图3-2 管理员子系统结构图
作为职工,系统需要满足他们具有员工管理(修改个人资料、删除员工和浏览个人资料)、出勤管理(浏览个人出勤信息录)、奖惩信息管理(查询个人奖惩信息)、请假管理(提交请假、个人请假信息浏览)、薪资管理(浏览个人薪资记录)。职工的子系统结构如图3-3所示:
 
图3-3 职工子系统结构图
3.3数据库设计
在开发应用程序时,对数据库的操作是必不可少的,数据库设计是根据程序的需求及其实现功能所制定的,数据库设计的合理性将直接影响到程序的开发过程[2]。
3.3.1数据库分析
企业人事管理系统主要用来记录一个企业中所有员工的基本信息,以及每个员工的请假记录、奖惩记录、出勤记录等,数据量是根据企业员工的多少来决定的,本系统使用Mysql作为后台数据库。数据库命名为pms,其中包含了8张数据表,用于存储不同的信息。
3.3.2系统E-R图
为了使前台在录入信息时更加简单、快捷,可以将基本表中的一些特定字段值在数据库中以表的形式进行记录。
管理员实体E-R图如图3-4所示:
 
图3-4 管理员的实体E-R图
部门的实体E-R图如图3-5所示:
 
图3-5 部门的实体E-R图
职工实体E-R图如图3-6所示:
 
图3-6 职位的实体E-R图
在企业中,职工出勤管理是必不可少的,为了能够信息地记录统计出勤情况,在数据库中创建出勤信息表。出勤信息表的实体E-R图如图所示:
 
图3-7 出勤信息表的实体E-R图
在企业中,职工受到奖励和惩罚必不可少的,为了能够清晰的记录职工的奖惩情况,在数据库中创建奖惩表。奖惩表的实体E-R图如图3-8所示:
 
图3-8 奖惩表的实体E-R图
在企业中,工资是必须的,为了能够方便了解工资情况,在数据库中创建薪资管理表。薪资管理信息表的实体E-R图如3-9所示: 
图3-9 薪资管理信息表的实体E-R图
在企业中,职工进行请假是必不可少的,为了能及时提交请假信息、审批请假请求、查询请假结果,在数据库中创建请假信息表。请假信息表的实体E-R图如图3-10所示:
 
图3-10 请假信息表的实体E-R图
  在企业中,招聘人员是比不可少的。为了能够了解招聘的信息和处理应聘人员,在数据中创建了招聘信息表。招聘信息表的实体E-R图,如图3-11所示:

 
图3-11 招聘信息表实体E-R图
系统总的E-R图如图3-12所示:
 
图3-12 系统总的E-R图

3.4数据库逻辑结构设计
根据上一节设计好的E-R图,可以在数据库中创建相应的数据表,企业人事管理系统中各个数据表的结构如下[10]:
(1)管理员表3-1如下
表3-1 管理员表
字段名    数据类型    是否为空    是否是主键    描述
adminId    String(4)    No    Yes    账号
adminPasswor    String(20)    No    No    密码
purview    String(1)    No    No    权限(1表示管理员,2表示普通员工)
(2)部门表3-2如下
表3-2 部门表
字段名    数据类型    是否为空    是否是主键    描述
branchId    String(4)    No    Yes    部门编号
branchName    String(20)    No    No    部门名称
branchDescribe    String(255)    No    No    部门简介
branchNember    String(4)    No    No    部门人数
(3)员工表3-3如下所示
表3-3 员工表
字段名    数据类型    是否为空    是否是主键    描述
employeeId    String(4)    No    Yes    员工编号
employeeName    String(20)    No    No    员工姓名
employeeSex    String(2)    No    No    性别
employeeAge    Int(4)    No    No    年龄
employeeIdCard    String(30)    No    No    身份证
employeeBirth    Date    Yes    No    出生日期
employeePhone    String(50)    Yes    No    电话
employeeAddress    String(255)    Yes    No    地址
employeeBranchName    String(20)    Yes    No    所属部门
employeeTime    Date    Yes    No    登记时间
(4)出勤信息表3-4如下
表3-4 出勤信息表
字段名    数据类型    是否为空    是否为主键    描述
absenceId    String(4)    No    Yes    序号
absece    Int(20)    Yse    No    出勤次数
disAbsece    Int(20)    Yes    No    缺勤次数
absenceTime    Date    No    No    时间
evection    Int(20)    Yes    No    出差次数
late    Int(20)    Yes    No    迟到早退次数
add    Int(20)    Yes    No    加班
type    Int(4)    No    No    性质(1表示日表,2表示月表)
(5)奖惩信息表3-5如下
表3-5 惩罚信息表
字段名    数据类型    是否为空    是否为主键    描述
preId    String(4)    No    Yes    奖惩编号
preName    String(20)    No    No    奖惩名称
preType    String(2)    No    No    奖惩类型(1表示奖励,2表示惩罚)
preReason    String(255)    No    No    奖惩原因
preMoney    Int(4)    No    No    奖惩金额
PreTime    Data    No    No    时间
(6)请假信息表3-6如下
表3-6 请假信息表
字段名    数据类型    是否为空    是否为主键    描述
leaveId    String(4)    No    Yes    请假编号
leaveStart    Date    No    No    请假开始时间
leaveEnd    Date    No    No    结束时间
leaveName    String(20)    No    No    请假姓名
leaveEmployeeId    String(4)    No    No    请假人编号
leaveReason    String(255)    Yes    No    请假理由
leaveType    String(2)    Yes    No    请假状态(1表示为操作,2表示批准,3表示未批准)
(7)薪资管理信息表3-7如下
表3-7 薪资信息表
字段名    数据类型    是否为空    是否为主键    描述
payId    String(4)    No    Yes    序号
payEmployeeName    String(20)    No    No    员工姓名
payEmployeeId    String(4)    No    No    员工编号
payTime    date    No    No    发工资时间
payAdd    Int(6)    Yes    No    加班费
payPresent    Int(6)    Yes    No    出勤费
payEvecation    Int(6)    Yes    No    出差补助
preMoney    Int(6)    Yes    No    惩罚金额
payBase    Int(6)    No    No    基本工资
payOffer    Int(6)    No    No    应发工资

(8)招聘信息表3-8如下
表3-8 招聘信息表
字段名    数据类型    是否为空    是否是主键    描述
employedId    String(4)    No    Yes    序号
employedName    String(20)    No    No    应聘姓名
employedSex    String (2)    No    No    性别
employedAge    String(4)    No    No    年龄
employedIdCard    String(30)    No    No    身份证
employedBirth    Date    Yes    No    出生日期
employedPhone    String(50)    Yes    No    电话
employedAddress    String(255)    Yes    No    地址
enployedBranchId    String(4)    Yes    No    应聘部门
employedTime    Date    Yes    No    应聘时间
employedtpte    String(2)    Yes    No    状态(1表示未操作,2表示录用,3表示未录用)

 
第4章 详细设计
4.1 设计目的
 详细设计阶段的任务是要设计出程序的“蓝图”,以后程序员将根据这个蓝图写出实际的程序代码。因此,详细设计的目标是在逻辑上正确的实现每个模块的功能。进行界面设计时候按照以下几个原则:
(1)    简单性:设计必须简单,这既是对实现的要求,也是对接口的要求。用户最好一目了然知道自己该如何操作。
(2)    完整性:设计必须覆盖到实际应用的各种重要场景。所有可预料到得情况都必须覆盖到,简单性不能过度的损害完整性[16]。
(3)    美观性:由于考虑到本系统作为企业内部使用,又考虑到员工应本着严谨、负责的态度对待工作,所以本系统采用大理石为背景,以绿色为点缀,展示了一种冷艳的效果。
4.2模块设计
4.2.1验证用户功能模块
(1)功能描述
本系统的所有功能模按块都必须调用“验证用户”子模块进行身份验证,此模块是所有用户进入系统时都必须调用的模块,用户可以选择管理员或者普通员工进行登录,点击系统用户登录界面中的【登录】按钮触发。
(2)模块IPO表
验证用户身份功能模块的IPO表4-1如下所示:
表4-1 验证用户功能模块的IPO
系统名称    企业人事管理系统
模块名称    验证用户身份
模块简述    用于对登陆系统的用户进行身份验证
调用模块    系统的主控制模块
输入    项目    用户账号,密码
    格式    用户账号:6-20位的字符串
处理    <1>访问数据库的管理员表;
<2>验证用户输入的验证账号和密码,若未查询到或不匹配,返回结果到登录窗口,提示错误,相反登录成功,转到相应的处理页面
输出    提示信息:用户名或密码错误
注释    涉及的表:管理员表
(3)界面设计
验证用户身份的系统登录界面设计如图4-1所示:
 
图4-1用户验证图
4.2.2管理员导航主页面功能模块
(1)功能描述
不同的用户在导航主页面上看得的内容是不一样的,职工和管理员对自己所要的需要进行选择
(2)模块IP0表
管理员导航主界面功能模块IPO表4-2如下所示:
表4-2 管理员导航主界面功能模块IPO
系统名称    企业人事管理系统
模块名称    管理员导航主页面
模块简述    用于登录系统的用户进行相关操作的选择
调用模块    进行选择后入相应的模块,有部门,招聘,员工,出勤,奖惩,系统,请假,薪资管理八部分的功能
被调用模块    用户登录系统时都调用此模块
输入    触发界面相应按钮进行选择操作
处理    点击不同的功能键得到相应的功能
输出    通过选择进入相应模块
注释    涉及的表:管理员表
(3)界面设计
管理员导航主界面设计如图4-2所示

 
图4-2管理员导航主页面
4.2.3员工导航主页面功能模块
(1)功能描述
不同的用户在导航主页面上看得的内容是不一样的,职工和管理员对自己所要的需要进行选择
(2)模块IP0表
员工导航主界面功能模块IPO表4-3如下所示:
表4-3 员工导航主界面的功能模块IPO
系统名称    企业人事管理系统
模块名称    员工导航主页面
模块简述    用于登录系统的用户进行相关操作的选择
调用模块    进行选择后入相应的模块,有员工,出勤,奖惩,薪资查看,请假管理
被调用模块    用户登录系统时都调用此模块
输入    触发界面相应按钮进行选择操作
处理    点击不同的功能键得到相应的功能
输出    通过选择进入相应模块
注释    涉及的表:管理员表
(3)界面设计
普通员工导航主界面设计如图4-3所示
 图4-3员工导航页面
4.2.4部门管理模块
(1)功能描述
部门管理有四个功能添加、编辑和查询,查询可以按照部门编码的精确查询和部门名称的模糊查询。
(2)模块IPO表
添加界面的IPO表4-4如下所示:
表4-4 部门管理模块的IPO
系统名称    企业人事管理系统
模块名称    部门管理模块
模块简述    供管理员查找、删除、增加、编辑部门信息
被调用模块    用户通过主界面可以调用查找、删除、增加、编辑改模块
输入    触发界面相应按钮进行选择操作以及输入部门编号,部门名称,部门信息
处理    <1>点击【查看详情】进入详情页
<2>点击【添加部门】进入添加部门的页面
<3>在编辑框里输入关键词点击【搜索】可进行相应的查询
<4>点击【编辑】进入相应的编辑页面
输出    显示数据
注释    涉及的表:部门信息表 管理员表
(3)界面设计
部门管理模块的界面如图4-4所示
图4-4部门管理页面
4.2.5添加模块
(1)功能描述
 添加功能模块是供整个企业管理系统添加信息的一个功能。
(2)模块IPO表
添加模块模块的IPO表4-5如下所示:
表4-5 添加模块的IPO
系统名称    企业人事管理系统
模块名称    添加模块
模块简述    用来添加系统所需要的信息
被调用模块    添加模块
处理    <1>点击【创建】数据保存
输出    进入显示主页面
(3)界面设计
添加模块的界面如图4-5所示
 
 
图4-5添加模块页面
4.2.6编辑模块
(1)功能描述
编辑功能主要是对信息进行编辑和删除。
(2)模块IPO表
编辑模块的IPO表4-6如下所示:
表4-6 编辑模块的IPO
系统名称    企业人事管理系统
模块名称    编辑模块
模块简述    对信息进行编辑更新和删除
被调用模块    保存模块 删除
输入    编辑信息
处理    <1>点击【更新】后对信息进行更新并进入详情显示页
<2>点击【删除】对信息删除并进入主显示页面
输出    不同的触发对应不同的显示页面
(3)界面设计
编辑模块的界面如图4-6所示
 
图4-6编辑模块页面
4.2.7添加员工模块
(1)功能描述
添加员工时,有个部门下拉框,下拉框中的部门是从数据库中取得的部门
(2)模块IPO表
添加员工模块的IPO表4-7如下所示:
表4-7 添加员工模块的IPO
系统名称    企业人事管理系统
模块名称    添加员工
模块简述    添加员工
被调用模块    保存模块 
输入    添加员工信息
处理    <1>点击【创建】后保存信息
输出    进入上级菜单
    (3)界面设计
添加员工的界面如图4-7所示
 
图4-7添加员工的信息页面
4.2.8修改密码模块
(1)功能描述
进行原密码和验证图片的验证,在进行两次密码的匹对,如果相同,增修改数据库表中的数据
(2)模块IPO表
修改密码模块的IPO表4-8如下所示:
表4-8 修改密码模块的IPO
系统名称    企业人事管理系统
模块名称    修改密码
模块简述    对原密码,新密码和验证图片进行匹对,如果成功。则修改
被调用模块    跟新模块 
输入    输入密码和验证信息
处理    <1>点击【提交】后判断,如果成功则保存,如果不成功则有提示信息
<2>点击验证图片,可以异步改变图片

输出    进入上级菜单

(3)界面设计
修改密码的界面如图4-8所示:
 
图4-8修改密码信息页面
4.2.9自动生成工资模块
(1)功能描述
输入员工编号,点击【自动生成】则将奖惩表的奖金和员工姓名显示到本页面上面
(2)模块IPO表
生成工资模块的IPO表4-9如下所示:
表4-9 自动生成工资模块的IPO
系统名称    企业人事管理系统
模块名称    自动生成工资
模块简述    输入员工编号,则出来相应的工资
输入    员工编号
处理    <1>点击【自动生成】后,条用自动生成模块,则出现自动生成的工资信息
输出    本菜单
涉及的表    奖惩表,薪资表,出勤表
(3)界面设计
生成工资的界面如图4-9所示:
 
图4-9自动生成工资页面
4.2.10自动生成月出勤记录模块
(1)功能描述
输入员工编号,选择月出勤表,再填入月份,点击【自动生成月出勤】则将自动本月出勤记录
(2)模块IPO表
生成出勤记录模块的IPO表4-9如下所示:
表4-10 自动生成考勤记录模块的IPO
系统名称    企业人事管理系统
模块名称    自动生成月出勤记录
模块简述    输入员工编号,选择月份,则生成相应的月出勤记录
输入    员工编号,月份
处理    <1>点击【自动生成月出勤记录】后,条用自动生成模块,则出现自动生成的月出勤记录
输出    本菜单
涉及的表    出勤表
(3)界面设计
生成出勤记录的界面如图4-10所示:
 
图4-10自动生成月出勤表页面


 
第5章 系统实现
5.1 数据库配置的实现
实现sts与mysql的连接,要配置DateSource.groovy文件 ,系统与数据库的配置文件[8]。
我的数据库是pms,用户名root,密码12345,在dateSource.groovy文件中主要改以下几个地方:
dataSource {
    pooled = true
    driverClassName = "com.mysql.jdbc.Driver"
    username = "root"
    password = "12345"
    }
    environments {
    development {
       dataSource {
            logsql = false
             username="root"
             password ="12345"
            dbCreate = "update"
            url = "jdbc:mysql://127.0.0.1:3306/pms?autoReconnect=true&useUnicode=true&characterEncoding=UTF8"[4]
        }
    }
5.2 登录的实现
   输入用户名和密码,根据用户的权限进入不同的主页面[9]。代码如下:
def check{
      def user=Manerge.findByAdminIdAndAdminPassword(params.username,params.password)
       if(user){
          session.user=user
          render 'success'
          
       }
       else{
           render 'error'
       }
    }
调用action后,引用check的js,如果信息正确则进入相应的主页面,如果信息错误则反馈错误信息[3]。
function check(){
                        var param ={
                            username:$("#username").val(),
                            password:$("#password").val()
                        }
                        $.ajax({
                            url:"/login/check",
                            data:param,
                            success:function(result){
                                if(result=="success"){
                                    window.location.href="/login/top"
                                }
                                if(result=="error"){
                                    alert('密码或者用户名错误')
                                }
                            }    
                        });
                    }
5.3 搜索功能实现
进入不同的功能模块有不同的搜索功能。部门页面、招聘页面、员工页面、薪资页面和请假页面都有进行关键字的搜索功能,以下是薪资页面的搜索功能的代码。
def search(def name,def date,def dateEnd,int offset,int max){
    def results
    if(name&&date&&dateEnd) {
        def date1=dateUtil.parseToDate(date)
        def dateEnd1=dateUtil.parseToDate(dateEnd)
        def c=Pay.createCriteria()
        results=c.list{
            between("payTime",date1,dateEnd1)
            or{
                ilike("payEmployeeName","%"+name+"%")
                ilike("payEmployeeId","%"+name+"%")
            }
            firstResult(offset)
            maxResults(max)
        }
    }
    else if(!name) {
        def date1=dateUtil.parseToDate(date)
        def dateEnd1=dateUtil.parseToDate(dateEnd)
        def c=Pay.createCriteria()
        results=c.list{
            between("payTime",date1,dateEnd1)
            firstResult(offset)
            maxResults(max)
        }
    }
    else if(!date&&!dateEnd) {
        def c=Pay.createCriteria()
        results=c.list{
            or{
                ilike("payEmployeeName","%"+name+"%")
                ilike("payEmployeeId","%"+name+"%")
            }
            firstResult(offset)
            maxResults(max)
        }
    }

    return results
}
进行时间搜索的时候要对时间进行规范化,将时间的时分秒去掉的代码如下:
    /**
    * 将时间的时分秒去掉
    *
    * @param date
    * @return
    */
    public static Date parseToDate(String str) {
        String[] patters = new String[1];
        patters[0] = "yyyy-MM-dd HH:mm:ss";
        Date date = null;
        try {
            date = parseDate(str, patters);
        } catch (ParseException e) {
            // ignore
        }
        return date;
    }
5.4 修改密码的实现
用户登录后可以修改自己的密码,输入原始密码,两遍新密码,再加上验证图片,如果匹配成功,进入主页面,如果不成功,则有反馈信息。以下是修改密码的代码[15]:
   def change={
        if(session.user.adminPassword.equals(params.old) && params.news.equals(params.renews)&&session.checkCode.equalsIgnoreCase(params.valicode)){
            Manerge.executeUpdate("update Manerge b set b.adminPassword="+"'"+params.news+"'"+" where b.adminId="+"'"+session.user.adminId+"'")
            session.user.adminPassword=params.news
            render "success"
            return
        }
        else if(!params.news.equals(params.renews)){
            render "noMatch"
            return
        }
        else if(!session.checkCode.equalsIgnoreCase(params.valicode)){
            println(session.checkCode)
            render "noMatch1"
            return
        }
        render  "error"
    }
进行验证码反馈的js代码如下:
function check(){
//    alert("fdsflkdjkls");
    var param ={
        old:$("#old").val(),
        news:$("#news").val(),
        renews:$("#renews").val(),
        valicode:$("#valicode").val()
        }
        $.ajax({
            url:"/manerge/change",
            data:param,
            success:function(result){
                if(result=="success"){
                    alert('修改成功')
                    window.location.href="/login/top"
                }
                else if(result=="noMatch")
                {
                    alert('两次密码不一样')
                }
                else if(result=="noMatch1")    {
                    alert('验证码不正确')
                }
                else{
                        alert('原始密码错误')

                        }
                }    
            });
        }
异步加载图片的js代码如下:
function changeCode()
{
    var verify=document.getElementById('codeImg');
    verify.setAttribute('src','/checkCode/index?r='+Math.random() );
}
5.5自动生成工资的实现
在进行工资创建的时候,相应的员工记录中也会有相应的工资,代码如下:
    def add={
        def payInstance = new Pay()
        int add=0
        def employee=Employee.findByEmployeeId(params.payEmployeeId)
       def absence=Absence.search(params.payEmployee,params.payTime,2)
        def results=payService.getPre(params.payEmployeeId)
        if(results.size()>0){
            for(int i=0;i<results.size();i++){
                if(results[i].preType.equals("1")){
                   add=results[i].preMoney+add
                }
               else if(results[i].preType.equals("2"))
               {
                   add=add-results[i].preMoney
                   }
            }
        } 
        payInstance.payBase=2000
        payInstance.payAbsence=absence.absence*10-absence.disAbsence*10
        payInstance.payAdd=absence.add*20
        payInstance.payId=params.payId
        payInstance.payEmployeeName=employee.employeeName
        payInstance.payEmployeeId=params.payEmployeeId
        payInstance.payTime=params.payTime
        payInstance.payPreMoney=add
        payInstance.payOffer=2000+add+ absence.absence*10-absence.disAbsence*10+ absence.add*20
        render(view: "create", model: [payInstance: payInstance])
        
    }

5.6权限设置的实现
整个系统必须在登录的状态下访问,如果不等陆则出现友好的错误页面,普通用户的权限比管理员的权限底,有些功能不能使用,虽然在页面上没有功能的链接,但是可以在链接框里面输入路径进行操作[17],代码如下:
class LoginFilters {
    def filters = {
        def needLogin=[

                    "department":"*",
                    "course":"*",
                    "education":"*",
                    "employed":"*",
                    "employee":"*",
                    "leave":"*",
                    "pay":"*",
                    "login":["top", "logout"]]
        def userRole=[
                    "manerge":"*",
                    "department":"*",
                    "employed":"*",
                    "employee":["create", "delete"],
                    "education":[
                        "create",
                        "edit",
                        "save",
                        "update",
                        "delete"]
                    ,
                    "premium":[
                        "create",
                        "edit",
                        "save",
                        "update",
                        "delete"
                    ],
                    "pay":[
                        "create",
                        "edit",
                        "save",
                        "update",
                        "delete"]
                ]

        all(controller:'*', action:'*') {
            before = {
                for(Entry<String, String> entry : needLogin.iterator()){

                    if(controllerName.equals(entry.getKey()) && (entry.getValue().equals("*") || entry.getValue().equals(actionName) || entry.getValue().contains(actionName))) {
                        if(!session.user){
                            redirect(controller:"login",action:"login")
                            return false
                        }

                    }
                }
                for(Entry<String, String> entry :userRole.iterator()){
                    if(controllerName.equals(entry.getKey()) && (entry.getValue().equals("*") || entry.getValue().equals(actionName) || entry.getValue().contains(actionName))) {
                        if(session.user.purview.equals('2')) {
                            redirect(controller:"login",action:"top")
                            return false
                        }
                        else{
                            
                            return true
                            }
                    }
                }
            }
            after = {
            }
            afterView = {
            }
        }
 
第6章  测试
软件测试是软件开发过程的重要组成部分,是用来确认一个程序的品质或性能是否符合开发之前所提出的一些要求。软件测试就是在软件投入运行前,对软件需求分析、设计规格说明和编码的最终复审,是软件质量保证的关键步骤。软件测试是为了发现错误而执行程序的过程。软件测试在软件生存期中横跨两个阶段:通常在编写出每一个模块之后就对它做必要的测试(称为单元测试)。编码和单元测试属于软件生存期中的同一个阶段。在结束这个阶段后对软件系统还要进行各种综合测试,这是软件生存期的另一个独立阶段,即测试阶段。
6.1 测试策略说明
(1)整个系统界面窗体的项目
有关的下拉菜单、工具条、对话框、按钮图标和其他控制窗口是否正常。
业务流程是否合理,是否符合用户的操作。
(2)数据项测试条目
能否识别输入的数据的类型、长度。数据库在大量的数据输入输出时间能否正常运行。
(3)系统测试的方法采用的是黑盒测试法。
该方法是已知系统应该具有的功能,通过测试检验每个功能是否都能正常使用,黑盒测试完全不考虑程序的内部结构和处理过程,测试仅在程序界面上进行。
6.2测试用例
由于篇幅过长,下面仅给出了部分用例的测试过程,其中重复的功能未写出。
6.2.1 系统登录管理模块
功能说明:本模块用于对用户的密码及权限进行验证,如输入正确才能进入系统。
测试项目:登录。
输入数据:输入用户名及密码,单击“确定”按钮。
测试数据:用户名:0001用户密码:111111
输出数据:无。
附加说明:用户输入密码错误,系统会自动提示用户名或者密码错误,如图6-1所示


图6-1 企业人事管理系统登陆错误界面
6.2.2系统管理模块
功能说明:本模块是给管理员查看、编辑、删除和增加用户的功能。
(1)查看用户列表功能
测试项目:查看用户列表
输入数据:点击菜单栏里面的【查看用户列表】
输出数据:用户列表
(2)增加用户功能
测试项目:增加用户
输入数据:员工信息
测试数据:员工编码:0001,密码:111111,权限:1
输出数据:如图6-2
 
图6-2 用户详情显示
(3)编辑用户功能
测试项目:编辑用户
输入数据:密码信息
测试数据:输入密码:222222
输出数据:页面如上图6-2,其中密码为222222
(4)删除用户功能
测试项目:删除用户
输入数据:点击【删除】
输出数据:用户列表页,删除数据已经删除
6.2.3部门管理模块
功能说明:本模块是给管理员查看、编辑、删除和增加部门的功能。
(1)查询功能
测试项目:查询功能
输入数据:选择模糊查询方式作为查询的关键字。
测试数据:输入模糊部门名称:技术部。
输出数据:如图6-3所示
图6-3 部门显示列表页面
(2)编辑功能
测试项目:编辑部分
输入数据:点击【编辑】,描述:人事部
输出数据:用户列表详情页,描述:人事部
(3)增加功能
测试项目:部门创建 。
输入数据:部门数据。
测试数据:0022 研发部 4 研发新产品 
输出数据:如图6-4所示。
图6-4 部门显示详情页
(4)删除功能
测试项目:删除部门 。
输入数据:点击【删除】。
输出数据:部门列表页
6.2.4招聘管理模块
功能说明:本模块是给管理员查看、是否录用应聘人员和删除应聘人员的功能。

(1)查询功能
输入数据:部门:技术部,年龄阶段:0-20。
输出数据:如图6-5所示:
 
图6-5 应聘人员显示列表页面
(2) 编辑功能
测试项目:录用应聘人
输入数据:点击【编辑】,选择录用
输出数据:显示应聘人员信息详情页
6.2.5员工管理模块
功能说明:本模块是给管理员查看、编辑、增加和删除员工信息。
(1)查询功能
测试项目:按部门和员共姓名进行查找
输入数据:查找关键字
测试数据:部门:技术部,员工编号或者姓名:00
输出数据:如图6-6
 
图6-6 员工查询结果页面
6.2.6薪资管理模块
功能说明:管理员可以添加、编辑、查询和删除薪资,添加薪资中有自动生成薪资的功能。
(1)查询薪资
测试项目:查询薪资
输入数据:查询关键字
测试数据:员工编号或者名字:000,时间:2012-05-05 2012-06-01
输出数据:如图6-7所示
 
图6-7 薪资查询结果列表

(2)自动生成薪资功能
输入数据:员工编号
测试数据:员工编号0001,点击【自动生成薪资】
输出数据:如图6-8所示
 
图6-8 自动生成薪资详情列表界面
6.2.7考勤管理模块
功能说明:管理员可以添加、编辑、查询和删除考勤记录,添加考勤中有自动生成月考勤记录的功能。
(1)自动生成考勤记录
测试项目:自动生成考勤记录
输入数据:员工编号,月份
测试数据:员工编号:0001,月份:6,点击【自动生成月考勤表】
输出数据:如图6-9所示:
 
图6-9 自动生成月考勤表
6.2.8修改密码模块
功能说明:进行密码修改时,如果密码正确,则提示正确,并进入主页面,如果输入信息错误,则返回错误信息。
测试项目:密码修改 。
输入数据:密码信息
测试数据:111111 111111 1111112 cbfm 
输出数据:如图6-10 所示。
图6-10 友好提示页面1
测试数据:111111 111111 111111 cf63 
输出数据:如图6-11所示。
图6-11 友好提示页面2
6.3测试结果
各个模块经过测试后,没有发现问题,符合设计要求。
 
结论与展望

经过一段时间的努力,毕业设计终于接近尾声了,答辩即将开始,我们的大学生活也就要划上结束符号。在设计和实习过程中,我学到了许多在书本学不到东西,并且通过自己的努力,解决了许多技术上的难题,锻炼了我的实际操作能力,提高了查阅文献资料、设计手册、设计规范以及编程能力和规范等其他专业能力水平,这些对将来的学习和工作都提供了一笔宝贵的财富。
课题的要求基本实现了,在不断的摸索中提高了自己动手编程的能力,同时熟悉了一些基本工具的使用和一些手册的使用,理解了一些基本原理。毕业设计的内容繁多,随着设计的不断深入,自己查找资料,逐个问题解决,和老师的沟通使得自己的思路更加的开阔。
在设计的过程中也遇到很多棘手的问题,例如数据库查询时时间的格式需要进行转换,否则出现字符类型不能匹配的问题,数据库乱码,由于数据库默认的字符类型与实际所使用到的字符类型不同等问题。由于考虑到安全问题,所以里面用到了过滤器,当没有登录时,输入地址链接,直接跳转到登录页面。同时,由于管理员和普通用户的权限不一样,所以当普通用户在地址栏中输入管理员才能使用的地址时,将跳转到导航页。
回顾自己做的系统,里面存在这一些不足,比如说:日考勤表,需要每个人一张一张去创建,这样需要花费很大时间。所以想到另一个实现功能是,先一键自动生成所有员工的出勤列表,默认都出勤,在显示所有员工出勤列表上进行修改未出勤或者出差的,这样一定程度上减少劳动力;在修改密码时有验证图片的生成,其实在企业内部中使用,这个功能不是很重要。在系统实现过程中,应该考虑到数据为空的情况,这样可以避免系统出错。
在这大学的最后时间里,回忆起这四年的时间,很多感慨,有好多知识我只是学了个一知半解,现在发现懂得太少,却发现没有时间可以留给自己了,懊悔是没用的,只能以后努力了。现在的遗憾和不足是我前进的动力,鞭策我潜行,相信走向社会后,只要朝着自己的目标一直努力,不放弃任何机会,梦想终会成真的!

 
致  谢

本次毕业设计历尽数月,在论文完成之际,我首先要感谢的是我的导师刘涛老师。刚开始是我主动要求刘老师带我的毕业设计,从她这学期负责指导我的毕业设计开始,就对我毕业设计中的每一个环节都不遗余力地给予帮助,从最初的开题报告,到毕业设计中期检查,到后期的系统和论文修改,刘老师一直在为我提供许多宝贵的、建设性的意见,使我的毕业设计不断地走向完善。在此期间她同时还任教于其他非毕业班,但是她对于自己的每一项工作都很认真负责,在我实习期间通过邮件和电话的方式对我的作业进行督促并及时给予虚心指导。在毕业设计这三个多月的时间里,刘老师的深厚的学术修养、严谨的治学精神、强烈的责任心和对学生的无私关怀,将使我受益终生。
同时,在这里我还要感谢四年以来所有教我知识的任课教师们,在母校学习的四年时间里给我提供了良好的学习和成长的氛围,让我学习到丰富的专业知识和严谨的工作态度,进一步提高了我的自学能力、分析问题和解决问题的能力。在此,我对他们表示忠心的感谢!
另外,我还要感谢我的同学和室友,在论文撰写的过程中,他们给我提供了许多值得借鉴的资料,在系统开发过程中也伸出了援助之手,没有他们热心的帮助,我就不可能顺利地完成本次毕业设计。在此我也一并表示感谢!


                                                         作者: 
                                                         年   月   日
 
参考文献

[1]吴以欣,陈小宁. JavaScript 脚本程序设计[M]. 人民邮电出版社,2011
[2]萨师煊,王珊. 数据库系统概论. 高等教育出版社[M],2007
[3]冯曼菲. Ajax基础概念、核心技术与典型案例[M].人民邮电出版社,2008
[4]郭真,王国辉. Java应用中的汉字乱码问题分析[M].人民邮电出版社.2008
[5]栗菊民. Java Web 应用程序设计[M].机械工业出版社.2010
[6]齐治昌,谭庆平,宁洪.软件工程[M].高等教育出版社.2008
[7]唐权,田绍军. DWR Spring Hibernate框架应用研究[J]. 四川职业技术学院学报,2011,02:120-122
[8]孙东卫,张冀红,李声利.数据库访问技术研究[J].现代电子技术.2002,18:20-34.
[9]张俊.利用DES和RSA加密算法实现JAVA软件的注册授权策略[J].青岛远洋船员学院学报,2006,02:68-71
[10]苟凌怡,魏生民. SQL Server 中索引的有效选取[J]. 计算机工程与应用,2006,02:44-48
[11]叶宾.人力资源管理系统的分析和研究[J].信息技术报,2006,03:146-147
[12]孙莹.人事工资查询系统[J].黑龙江科技信息,2009,02:100-101
[13]徐芳,范志勤.基于JSP的人事管理平台的设计[J].科技经济市场,2011,04:88-89
[14]孟琼.基于Spring JavaBean的Web Serveice服务[J].计算机与现代化,2012,01:197-199
[15]吴俊杰. Ajax和Spring的比较分析[J].太原师范学院报(自然科学版),2011,04:83-86
[16]包云岗.系统设计黄金法则——简单之美[J]. 计算机协会通讯,2012,05:45
[17]James Turner,Kevin Bedell. Struts Kick Start[M]. SAMS,2004
[18] Kong Michael. An environment for secure SQL/Server computing [M].Oxford University Press Inc., 1993: 149
[19] Jon Titus. ECN Technical Editor:The Eclipse of stand[J]. Journal of Zhongkai Agrotechnical College,Vol.19,No.2,2006:32-35


 
附录A:外文文献及译文
Grails application frameworks
What are application frameworks:
A framework is a reusable, semi-complete application that can be specialized to
produce custom applications [Johnson]. Like people, software applications are more alike than they are different. They run on the same computers, expect input from the same devices, output to the same displays, and save data to the same hard disks. Developers working on conventional desktop applications are accustomed to toolkits and development environments that leverage the sameness between applications. Application frameworks build on this common ground to provide developers with a reusable structure that can serve as the foundation for their own products.
A framework provides developers with a set of backbone components that have the following characteristics:
1.They are known to work well in other applications.
2. They are ready to use with the next project.
3. They can also be used by other teams in the organization.
Some frameworks have been linked to a proprietary development environment. This is not the case with Struts or any of the other frameworks shown in this book. You can use any development environment with Struts: Visual Age for Java, JBuilder, Eclipse, Emacs, and Textpad are all popular choices among Struts developers. If you can use it with Java, you can use it with Struts.
Hypertext Transfer Protocol (HTTP):
When mediating talks between nations, diplomats often follow a formal protocol.
When computers need to talk, they also follow a formal protocol. The protocol defines how data is transmitted and how to decode it once it arrives. Web applications use the Hypertext Transfer Protocol (HTTP) to move data between the browser running on your computer and the application running on the server.
Many server applications communicate using protocols other than HTTP. Some of these maintain an ongoing connection between the computers. The application server knows exactly who is connected at all times and can tell when a connection is dropped. Because they know the state of each connection and the identity of each person using it, these are known as stateful protocols.
By contrast, HTTP is known as a stateless protocol. An HTTP server will accept any request from any client and will always provide some type of response, even if the response is just to say no. Without the overhead of negotiating and retaining a connection, stateless protocols can handle a large volume of requests. This is one reason why the Internet has been able to scale to millions of computers.
Another reason HTTP has become the universal standard is its simplicity. An HTTP request looks like an ordinary text document. This has made it easy for applications to make HTTP requests. You can even send an HTTP request by hand using a standard utility such as Telnet. When the HTTP response comes back, it is also in plain text that developers can read.
The first line in the HTTP request contains the method, followed by the location
of the requested resource and the version of HTTP. Zero or more HTTP request headers follow the initial line. The HTTP headers provide additional information to the server. This can include the browser type and version, acceptable document types, and the browser’s cookies, just to name a few. Of the seven request methods, GET and POST are by far the most popular.
Once the server has received and serviced the request, it will issue an HTTP response. The first line in the response is called the status line and carries the HTTP protocol version, a numeric status, and a brief description of the status. Following the status line, the server will return a set of HTTP response headers that work in a way similar to the request headers.
As we mentioned, HTTP does not preserve state information between requests.The server logs the request, sends the response, and goes blissfully on to the next request. While simple and efficient, a stateless protocol is problematic for dynamic applications that need to keep track of their users. (Ignorance is not always bliss.
Grails framework: 
Grails dynamic method reduces the Java platform the complexity of the Web development, but with the framework of different is that Grails in Spring and Hibernate is the building of the existing technologies such as Java on. Grails is a full-stack frame, with the help of the core technology and related plug-in to solve the problems in Chinese Web development, Including: easy to use based on Hibernate object-relational mapping layer called Groovy Server Pagesperformance based on Spring MVC layer technology of building controller layer in Gant the command of the lines in the script on the line environment Jetty built-in Server, Don't restart the server can be used the built-in container loading Spring based on the Spring into realize rely on MessageSource core concept, provide the international (i18n) based on the support of the Spring affairs abstract concepts, realize the affairs of service by powerful Groovy dynamic Language and Language Specific field, those properties become very easy to use.
MVC mode:
MVC pattern is the software engineering is a software architecture model, the software system is divided into three basic parts: model, view and controller.
Model: data model for packaging and application of the business logic of the relevant data and the data processing method. The mode has direct access to the data of the power, such as access to database. The model doesn't rely on the view and controller, that is, model not care it will be how to display or how to be operating. But the model of data changes usually through a refresh mechanism is announced. In order to achieve this mechanism, and those who used to monitor the model views on this model must register, thereby, view can understand in data model changes.
Views: view layer can realize data show with a purpose. In the view of general no program logic. In order to realize the view of renovatesthe function, and view need access to the data model of monitoring it, therefore, should be in be it in advance of the surveillance data registered there.
Controller: controller has different levels of role between organizations, for the control of the application process. It handles events and responds. "Events" include user behavior and data model of change.

 
Grails应用框架
什么是应用框架:
框架(framework)是可重用的,半成品的应用程序,可以用来产生专门的定制程序。像人一样,软件应用的相似性比不同点要多。它们运行在相似的机器上,期望从相同的设备输入信息,输出到相同的显示设备,并且将数据存储到相同的硬盘设备。开发传统桌面应用的开发人员更习惯于那些可以涵盖应用开发同一性的工具包和开发环境。构架在这些公共基础上的应用框架可以为开发人员提供可以为他们的产品提供可重用服务的基础架构。
框架向开发人员提供一系列具有以下特征的骨架组件:
1.已经知道它们在其它程序上工作得很好;
2.它们随时可以在下一个项目中使用;
3.它们可以被组织的其它团队使用;
超文本传输协议 (HTTP):
当计算机间需要对话,它们也遵循一个正式的协议。这个协议定义数据是如何传输,以及它们到达后如何进行解码。Web应用程序就是使用HTTP协议在运行浏览器的计算机和运行的服务器的程序间传输数据。
很多服务器应用程序使用HTTP之外的其他协议。他们在计算机之间维护一个持久性的连接。应用服务器可以清楚的知道是谁连接上来,而且何时中断连接。因为它们知道每一个连接的状态,以及每一个使用它的人。这称之为状态协议。
相反, HTTP是一个无状态协议。HTTP Server 可以接受来自于各种客户的各种请求,并提供各种响应,即使是这个响应仅仅是说No。没有大量的协商和连接持久性,无状态协议可以处理大量的请求。这也是Internet 可以扩展到很多计算机的原因。
HTTP 成为通用标准的原因是其简单性。HTTP请求看起来就像一个平常的文本文档。这使应用程序很容易创建HTTP请求。你甚至可以通过标准的程序如Telnet来手动传递一个HTTP请求。当HTTP响应返回时,它也是一个开发者可以直接阅读的平面文本。HTTP请求的第一行包含方法,其后是请求的来源地址和HTTP版本。HTTP请求头跟在首行后面,可以没有也可以有多个。HTTP头向服务器提供额外的信息。可以包括浏览器的种类和版本,可接受的文档类型,浏览器的cookies等等。7 种请求方法中, GET和 POST是用得最多的。
Grails框架:
Grails采用动态方法减小了Java平台上进行Web开发的复杂度,不过与那些框架不同的是,Grails是构建在Spring和Hibernate等Java已有的技术之上的。Grails是一个full-stack框架,它借助于核心技术与相关的插件(plug-in)来解决Web开发中方方面面的问题,其中包括: 易于使用的基于Hibernate的对象-关系映射(ORM)层 称为Groovy Server Pages (GSP)的表现层技术 基于Spring MVC的控制器层 构建于Gant 上的命令行脚本运 行环境 内置Jetty服务器,不用重新启动服务器就可以进行重新加载 利用内置的Spring 容器实现依赖注入 基于Spring的MessageSource核心概念,提供了对国际化(i18n)的支持 基于Spring事务抽象概念,实现事务服务层 借助于功能强大的Groovy动态语言和领域特定语言(Domain Specific Language,DSL),以上那些特性变得非常易用。
MVC模式:
MVC模式是软件工程中的一种软件架构模式,把软件系统分为三个基本部分:模型、视图和控制器。
模型:数据模型用于封装与应用程序的业务逻辑相关的数据以及对数据的处理方法。模型有对数据直接访问的权力,例如对数据库的访问。模型不依赖视图和控制器,也就是说,模型不关心它会被如何显示或是如何被操作。但是模型中数据的变化一般会通过一种刷新机制被公布。为了实现这种机制,那些用于监视此模型的视图必须事先在此模型上注册,从而,视图可以了解在数据模型上发生的改变。
视图:视图层能够实现数据有目的的显示。在视图中一般没有程序上的逻辑。为了实现视图上的刷新功能,视图需要访问它监视的数据模型,因此应该事先在被它监视的数据那里注册。
控制器:控制器起到不同层面间的组织作用,用于控制应用程序的流程。它处理事件并作出响应。事件包括用户的行为和数据模型上的改变。

 
附录B:主要参考文献的题录及摘要

题录[1]:JavaScript 脚本程序设计
【作  者】吴以欣,陈小宁
【题  目】JavaScript 脚本程序设计
【出版社】人民邮电出版社
【关键字】JavaScript;程序语言-程序设计-高等教育-教材
【摘  要】本书全面系统地介绍了用JavaScript语言制作网页的客户端编程技术方法。主要分为4大部分:JavaScript的特点及基本编程方法,JavaScript用于处理浏览器对象,JavaScript实用技巧,JavaScript综合实训项目。读者通过本书的学习,可以制作出自己的动态网页,全面提高自己网页设计的基本知识和基本技能。

题录[2]:数据库系统概论
【作  者】萨师煊,王珊
【题  目】数据库系统概论
【出版社】高等教育出版社
【关键字】数据库;SQL 
【摘  要】本书系统全面地阐述数据库系统的基础理论、基本技术和基本方法。全书内容包括:数据库模型,数据库系统结构,关系数据库系统,SQL语言,复杂数据理论,数据库维护,数据库设计,关系数据库管理系统,数据库技术新进展,面向对象数据库系统,分布式数据库系统,并行数据库系统等。

题录[3]:Java应用中的汉字乱码问题分析
【作  者】刘长生,谢强,丁秋林
【题  目】Java应用中的汉字乱码问题分析
【刊  名】计算机技术与发展
【关键字】Java ;字符集; 中文乱码 
【摘  要】根据Java应用中乱码出现的原因将问题分成了4类:由于编译不当导致的乱码、Web应用中的乱码、数据库读写中的乱码和I/O读写中的乱码。在各个类别中,先给出出现乱码时的现象,然后对现象进行原因分析,再给出解决的办法。最后,根据做项目的实践经验,给出了一些解决汉字乱码问题的心得。

题录[4]:Tomcat与Java Web开发技术详解
【作  者】孙卫琴、李洪成    
【题  目】Tomcat与Java Web开发技术详解
【刊  名】电子工业出版社
【关键字】Tomcat;WEB开发
【摘  要】Tomcat是Apache 软件基金会(Apache Software Foundation)的Jakarta 项目中的一个核心项目,由Apache、Sun 和其他一些公司及个人共同开发而成。由于有了Sun 的参与和支持,最新的Servlet 和JSP 规范总是能在Tomcat 中得到体现,Tomcat 5 支持最新的Servlet 2.4 和JSP 2.0 规范。因为Tomcat 技术先进、性能稳定,而且免费,因而深受Java 爱好者的喜爱并得到了部分软件开发商的认可,成为目前比较流行的Web 应用服务器。目前最新版本是6.0

题录[5]:软件工程
【作  者】齐治昌,谭庆平,宁洪
【题  目】软件工程
【出版社】高等教育出版社
【关键字】软件工程;软件工程方法
【摘  要】本书结合目前软件工程教学的需要,特别介绍了统一建摸语言UML,并依次为基础讨论面向对象的需求分析与软件设计方法;介绍集成化CASE环境,java与internet环境下的软件开发技术;介绍支持软件过程改进的“软件能力成熟度模型”(cmm).

题录[6]:利用DES和RSA加密算法实现JAVA软件的注册授权策略
【作  者】张俊
【题  目】利用DES和RSA加密算法实现JAVA软件的注册授权策略
【刊  名】青岛远洋船员学院学报
【关键字】JVM; 反编译 ;加密算法 ;DES;RSA 
【摘  要】通过JNI接口调用本地应用程序读取用户主机的硬盘序列号作为用户唯一性依据,利用RSA加密算法实现用户信息和注册信息的加密保护盒验证。本文介绍了在商用JAVA软件开发中可以使用的一种注册验证策略的实现方法。

题录[7]:SQL Server 中索引的有效选取
【作  者】苟凌怡,魏生民
【题  目】SQL Server 中索引的有效选取
【刊  名】计算机工程与应用
【关键字】SQLServer 索引; 聚集索引 ;非聚集索引 ;填充因子;复合索引
【摘  要】该文对SQL Server中的索引机制作了一个较深入的讨论,着重分析如何选取索引来有效地提高查询速度、合理分配存储空间等问题,并对几种典型情况下的具体实施方法作了举例说明。

题录[8]:人事工资查询系统
【作  者】孙莹
【题  目】人事工资查询系统
【刊  名】黑龙江科技信息
【关键字】Internet技术; WEB应用 ; 工资查询
【摘  要】该文详细论述了网上工资查询系统的设计和实现的全过程,并对如何选择适当的开发平台及开发环境做了介绍。

题录[9]:Sams Teach Yourself JAVAServer Pages 2.0 with Apache Tomcat in 24 Hours
【作  者】Mark Wutka,Alan Moffet,Kunal Mittal
【题  目】Sams Teach Yourself JAVAServer Pages 2.0 with Apache Tomcat in 24 Hours
【出版社】Sams Publishing
【关键词】JAVAServer Pages;Apache Tomcat
【摘  要】When a client requests the JSP page, the container translates the page into a source code file for a Java servlet and compiles the source into a Java class file—just as you would do if you were writing a servlet from scratch. At runtime, the container can also check the last modified date of the JSP file against the class file. If the JSP file has changed since it was last compiled, the container will retranslate and rebuild the page all over again.

题录[10]:An environment for secure SQL/Server computing
【作  者】Kong Michael
【题  目】An environment for secure SQL/Server computing
【出版社】Oxford University Press Inc.
【关键字】SQL/Server
【摘  要】A database (sometimes spelled data base) is also called an electronic database  , referring to any collection of data, or information, that is specially organized for rapid search and retrieval by a computer. Databases are structured to facilitate the storage, retrieval , modification, and deletion of data in conjunction with various data-processing operations .Databases can be stored on magnetic disk or tape, optical disk, or some other secondary storage device.A database consists of a file or a set of files. The information in these files may be broken down into records, each of which consists of one or more fields. Fields are the basic units of data storage  , and each field typically contains information pertaining to one aspect or attribute of the entity described by the database . Using keywords and various sorting commands, users can rapidly search , rearrange, group, and select the fields  in many records to retrieve or create reports on particular aggregate of data.
 
附录C:部分源代码
DepartmentServic.groovy:
package com.pms.branch
import branch.Department;
class DepartmentService {
    static transactional = true
        def search(def name,int offset,int max){
                def c=Department.createCriteria()
                def results=c.list{
                or{
                    ilike("branchId","%"+name+"%")
                    ilike("branchName","%"+name+"%")
                    }    
                firstResult(offset)
                maxResults(max)
                }
                return results
        }
    def count(def name){
                def s=Department.createCriteria()
                def c=s.count{
                    or{
                        ilike("branchId","%"+name+"%")
                        ilike("branchName","%"+name+"%")
                    }    
                }
                return c
        }
}
EducationService.groovy:
package com.pms.education
import education.Education
class EducationService {
   static transactional = true
   def search(def id,def offset,def max){
        def c=Education.createCriteria()
        def results=c.list{
            ilike("educationEmployeeId","%"+id+"%")    
            firstResult(offset)
            maxResults(max)
        }
        return results
    }
    def count(def id)
    {
        def c=Education.createCriteria()
        def results=c.count{
            ilike("educationEmployeeId","%"+id+"%")    
        }
        return results    
    }
}
EmployeeService.groovy:
package com.pms.employee
import employee.Employee
import premium.Premium
class EmployeeService {
    static transactional = true
    /**
     * *
     * @param branchName
     * @param employeeName
     * @param offset
     * @param max
     * @return
     */
    def search(def branchName,def employeeName,int offset,int max){
        
        def c    =Employee.createCriteria()
        def results=c.list{
            if(branchName&&employeeName)
            {
                ilike("employeeBranchName",branchName)
                or{
                    
                    ilike("employeeName","%"+employeeName+"%")
                    ilike("employeeId","%"+employeeName+"%")
                }
            }
    
            else if(!branchName){
                or{
                    
                    ilike("employeeName","%"+employeeName+"%")
                    ilike("employeeId","%"+employeeName+"%")
                }
                
                }
            else if(!employeeName){
                ilike("employeeBranchName",branchName)
                
            }
           firstResult(offset)
           maxResults(max)
            
        }
        return results
    }
    /**
     * 
     * @param branchName
     * @param employeeName
     * @return
     */
    def count(def branchName,def employeeName){
         def s=Employee.createCriteria()
        def c=s.list{
            if(branchName){
                ilike("employeeBranchName",branchName)
            }
            if(employeeName){
            or{
                ilike("employeeName","%"+employeeName+"%")
                ilike("employeeId","%"+employeeName+"%")
                }
            }
        }
        return c
    }
    def saveChange(def id,def name,def employeeIds){
        def employeeIdLists=employeeIds?.split (" ")
        if(employeeIdLists){
            for(employeeIdList in employeeIdLists)
            {
                StringBuffer r=new StringBuffer()
                def old=Employee.executeQuery("select preId from Employee e where e.employeeId="+"'"+employeeIdList+"'")
                if(old){
                    r.append(old[0]).append(" ").append(id).toString()
                }
                else{
                    r.append(id).toString()
                }
                Employee.executeUpdate("update Employee b set b.preId="+"'"+r+"' "+" where b.employeeId="+"'"+employeeIdList+"'")
            }
        }    
    }    
}
LeService.groovy:
package com.pms.leave
import leave.Le
import pms.DateUtil
class LeService {
    static transactional = true
    def dateUtil=new DateUtil()
    /**
     * 
     * @param name
     * @param date
     * @param offset
     * @param max
     * @return
     */
    def search(def name,def date,def dateEnd,int offset,int max){
        def results
        def date1=dateUtil.parseToDate(date)
        def dateEnd1=dateUtil.parseToDate(dateEnd)
        def c=Le.createCriteria()
        results=c.list{
             if(name&&date&&dateEnd){
                 between("time",date1,dateEnd1)
                 or{
                     ilike("leaveType",name) 
                 }
                 firstResult(offset)
                 maxResults(max)
            }    
             else if(!name){
                 between("time",date1,dateEnd1)
                 firstResult(offset)
                 maxResults(max)
            }
             else if(!date&&!dateEnd){
                 or{
                     ilike("leaveType",name)
                 }
                 firstResult(offset)
                 maxResults(max)
             }
        }
        return results
    }
    def count(def name,def date,def dateEnd){
        def results
        def date1=dateUtil.parseToDate(date)
        def dateEnd1=dateUtil.parseToDate(dateEnd)
        def c=Le.createCriteria()
        results=c.count{
             if(name&&date&&dateEnd){
                 between("time",date1,dateEnd1)
                 or{
                     ilike("leaveType",name)
                     
                 }
            
            }    
             else if(!name){
                 between("time",date1,dateEnd1)
            }
             else if(!date&&!dateEnd){
                 or{
                     ilike("leaveType",name)     
                 }
             }
        }    
        return results    
    }
}
PayService.groovy:
package com.pms.pay
import com.sun.xml.internal.ws.api.streaming.XMLStreamReaderFactory.Default;
import pay.Pay
import pms.DateUtil
import premium.Premium
class PayService {
    static transactional = true
    def dateUtil=new DateUtil()
    def getPre(def id)
    {
       def results
       results=Premium.findAllByEmployeeIdLike("%"+id+"%")
       return results
    
    }
    /**
     * 
     * @param name
     * @param date
     * @param offset
     * @param max
     * @return
     */
    def search(def name,def date,def dateEnd,int offset,int max){
        def results
        if(name&&date&&dateEnd)
        {   
            def date1=dateUtil.parseToDate(date)
            def dateEnd1=dateUtil.parseToDate(dateEnd)
            def c=Pay.createCriteria()
             results=c.list{
                between("payTime",date1,dateEnd1)    
                or{
                    ilike("payEmployeeName","%"+name+"%")
                    ilike("payEmployeeId","%"+name+"%")
                }
                firstResult(offset)
                maxResults(max)
            }    
        }
        else if(!name)
        {   
             def date1=dateUtil.parseToDate(date)
            def dateEnd1=dateUtil.parseToDate(dateEnd)
            def c=Pay.createCriteria()
            results=c.list{
                between("payTime",date1,dateEnd1)
                firstResult(offset)
                maxResults(max)
            }
        }
        else if(!date&&!dateEnd)
        {
            def c=Pay.createCriteria()
            results=c.list{
                or{
                    ilike("payEmployeeName","%"+name+"%")
                    ilike("payEmployeeId","%"+name+"%")
                }
                firstResult(offset)
                maxResults(max)
            }
        }
        return results
    }
    def count(def name,def date,def dateEnd){
        def results
        if(name&&date&&dateEnd)
        {  
            def date1=dateUtil.parseToDate(date)
            def dateEnd1=dateUtil.parseToDate(dateEnd)
            def c=Pay.createCriteria()
            results=c.count{
                between("payTime",date1,dateEnd1)
                or{
                    ilike("payEmployeeName","%"+name+"%")
                    ilike("payEmployeeId","%"+name+"%")
                }
                }
        }
        else if(!name)
        {   
            def date1=dateUtil.parseToDate(date)
            def dateEnd1=dateUtil.parseToDate(dateEnd)
            def c=Pay.createCriteria()
            results=c.count{
                between("payTime",date1,dateEnd1)
            }
        }
        else if(!date&&!dateEnd)
        {
            def c=Pay.createCriteria()
            results=c.count{
                or{
                    ilike("payEmployeeName","%"+name+"%")
                    ilike("payEmployeeId","%"+name+"%")
                }
                
            }
        }
        return results
    } 
}
DateUtil.groovy:
package pms
import java.util.Date;
import java.text.ParseException;
import java.text.SimpleDateFormat
class DateUtil extends org.apache.commons.lang.time.DateUtils {
    /**
    * 
    * @param date
    * @return
    */
    public static Date parseToDate(String str) {
        String[] patters = new String[1];
        patters[0] = "yyyy-MM-dd HH:mm:ss";
        Date date = null;
        try {
            date = parseDate(str, patters);
        } catch (ParseException e) {
            // ignore
        }
        return date;
    }
    /*
     * 
     */
    public static String now() {
        SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss",
                Locale.CHINESE);
        Date date = new Date();
        return df.format(date);
    }
}
EmployedServic.groovy:
package pms
import employed.Employed
class EmployedService {

    static transactional = true
    /***
     * 
     * @param sex
     * @param age
     * @param name
     * @param offset
     * @param max
     * @return
     */
 
    def search(def sex,def age,def name ,int offset,int max ){
        def c=Employed.createCriteria()
        def results=c.list{
            if(age){
               if(age=="1"){
                    le("employedAge",20)   
                }
               else if(age=="2"){
                    between("employedAge",21,40)
                }
               else if(age=='3'){
                   between("employedAge",41,60)
                }
                       
            }    
            and{
                ilike("employedSex","%"+sex+"%")
                ilike("employedBranchId","%"+name+"%")
            }
            firstResult(offset)
            maxResults(max)
        }   
            return results
        
    }
    /**
     * 
     * @return
     */
    def count(def sex,def age,def name ){
        def s=Employed.createCriteria()
        def c=s.count{
            if(age){
                if(age=="1"){
                     le("employedAge",20)
                 }
                else if(age=="2"){
                     between("employedAge",21,40)
                 }
                else if(age=='3'){
                    between("employedAge",41,60)
                 }
                        
             }
             and{
                 ilike("employedSex",sex)
                 ilike("employedBranchId",name)
             }
        
        }
        return c
    
    }
    
}
LoginFilters :
package pss
import java.util.HashMap.Entry
class LoginFilters {
    def filters = {
        def needLogin=[
                    "department":"*",
                    "course":"*",
                    "education":"*",
                    "employed":"*",
                    "employee":"*",
                    "leave":"*",
                    "pay":"*",
                    "login":["top", "logout"]]
        def userRole=[
                    "manerge":"*",
                    "department":"*",
                    "employed":"*",
                    "employee":["create", "delete"],
                    "education":[
                        "create",
                        "edit",
                        "save",
                        "update",
                        "delete"]
                    ,
                    "premium":[
                        "create",
                        "edit",
                        "save",
                        "update",
                        "delete"
                    ],
                    "pay":[
                        "create",
                        "edit",
                        "save",
                        "update",
                        "delete"]
                ]
        all(controller:'*', action:'*') {
            before = {
                for(Entry<String, String> entry : needLogin.iterator()){
                    if(controllerName.equals(entry.getKey()) && (entry.getValue().equals("*") || entry.getValue().equals(actionName) || entry.getValue().contains(actionName))) {
                        if(!session.user){
                            redirect(controller:"login",action:"login")
                            return false
                        }
                    }
                }
                for(Entry<String, String> entry :userRole.iterator()){
                    if(controllerName.equals(entry.getKey()) && (entry.getValue().equals("*") || entry.getValue().equals(actionName) || entry.getValue().contains(actionName))) {
                        if(session.user.purview.equals('2')) {
                            redirect(controller:"login",action:"top")
                            return false
                        }
                        else{        
                           return true
                            }
                    }
                }
            }
            after = {
            }
            afterView = {
            }
        }
    }
}

猜你喜欢

转载自blog.csdn.net/weixin_55459367/article/details/114410735