07-03
17

人事部门管理系统(1)

       很长一段时间来,确切的说是两个多月,从年前开始就没有再过多的写程序。主要精力都投入在这个网站上面了,对于Java编程很少去碰。只是偶尔翻翻《核心技术》,不过是蜻蜓点水。前天本想编写一个米店(Domain)的管理系统为自己用,发现编的很吃力。本觉得瞒简单的东西,突然看来如此复杂。编了两天,决定不再写了。去温习一下从前写过的代码。我觉得,这样的话对我的帮助会很大。
       下面介绍我去年11月编写的一套人事部门管理系统,项目用时一周(需求分析2天,美工设计2天,其余时间为代码实现)。如图:



       需求文档的地址:http://www.yexu8.com/attachments/month_0703/person_xuqiu.htm

       从需求文档可以看出,这个项目的布局是由Tiles框架完成的。我们要作的是首先设计出一个完成的框架布局结构页layout.jsp.然后在其中定义其他页面分布位置。此项目共有四部分组成:siderbar.jsp用来作左侧列表选择,header.jsp用来放置logo,footer.jsp用于作者声明,另外一个至关重要的部分是可变的——随着siderbar.jsp的超链接选择而变。有了这种思想以后就可以写tiles-config了:

<definition name="layout-definition" path="/layout.jsp">
<put name="sidebar" value="sidebar.jsp"></put>
<put name="header" value="header.jsp"></put>
<put name="content"></put>
<put name="footer" value="footer.jsp"></put>
</definition>

       从上面可以看出内容是可变的,这段代码是接下来所有代码的父级代码,用于作继承之用。
       接下来作一个内容页:

<definition extends="layout-definition" name="index-definition">
<put name="content" value="indexContent.jsp"></put>
</definition>

       从name大致可以看出这个是为了index首页来使用的。而在index.jsp页面写入代码
<%@ page contentType="text/html; charset=UTF-8" language="java" %>
<%@ taglib uri="/WEB-INF/struts-tiles.tld" prefix="tiles" %>
<tiles:insert definition="index-definition">
</tiles:insert>

       这样即可,其实我们最关心的是列表(siderbar)及其内容(contents)部分。它们之间的互动性是我们使用tiles框架的原因。

       列表的第一个超链接是"添加员工":

<html:link page="/link1.do"><font color="#000000" style="text-decoration: none"><bean:message key="link.add.emp"/></font></html:link>

       link.add.emp分别对应两份bundle文件——这里使用了中英文国际化。国际化是一种反复的简单劳动,这里就不多作阐述了。我们关心的是link1.do的走向,看sturts-config:

<action path="/link1" parameter="link1" type="companypj.AddEmployeeAction" validate="false">
<forward name="link1_success" path="/link1.jsp">
</forward>

进入AddEmployeeAction

图1-1,AddEmployeeAction全部代码:

public class AddEmployeeAction extends Action {
    public ActionForward execute(ActionMapping mapping, ActionForm form,
                                 HttpServletRequest request,
                                 HttpServletResponse response) {
         DynaValidatorForm empDynForm=(DynaValidatorForm)form;
         Log log=LogFactory.getLog("A");
         String type=mapping.getParameter();
         DataSource ds=getDataSource(request);
         if(type.equals("link1"))
         {
             log.info("return_link1..");
             DepartmentBean departmentbean=new DepartmentBean(ds);
             Collection onlydep=departmentbean.getOnlyDepartments();//这里转入部门类,取出部门集合
             request.getSession().setAttribute(Constants.ONLYDEPARTMENTS_KEY,onlydep);//集合保存,并传入下一页面
             return mapping.findForward(Constants_url.RETURN_LINK1_SUCCESS);
         }
         if(type.equals("link_addemp"))
         {
            EmployeeBean empbean=new EmployeeBean(ds);
            //String address=empDynForm.get("address").toString();
            empbean.addEmployee(empDynForm);
            return mapping.findForward(Constants_url.RETURN_ADD_EMP_READY);
         }
         return null;
    }
}


再来看下面的getOnlyDepartments()方法,用于取出部门的方法

    public Collection getOnlyDepartments()     //只找出所有部门的集合,这个方法多此一举,都是动态数据即时更新的,所有没必要用它,当写着玩了~
    {
        Collection list=new ArrayList();
        Collection departments = this.getDepartments();//跳转
        Iterator i = departments.iterator();
        while(i.hasNext()) {
          DepartmentVO Onlydepartments=(DepartmentVO) i.next();
          log.info("Onlydep:"+Onlydepartments.getName());
          Onlydepartments.setName(Onlydepartments.getName()); //筛选后重新放入
          list.add(Onlydepartments);
        }
        return list;
    }

       。。。不看不知道,当初我还写了不少没用的解释,哈哈!注意这里有个跳转,跳转到另一个方法,接着看:

public Collection getDepartments()
    {
        log.info("提交所有部门数据集合");
        return this.getDepartmentsHelper(Constants_sql.DEPARTMENT_ALL_SQL);
    }

       这个方法也只是为了层次清晰和重用性,接着把一条SQL丢给下面赶事实的方法getDepartmentsHelper():

private Collection getDepartmentsHelper(String sql) //遍历集合 帮助方法
    {
        Collection list=new ArrayList();
        try {
            Connection conn=ds.getConnection();
            Statement stmt=conn.createStatement();
            ResultSet rs=stmt.executeQuery(sql);
            while(rs.next())
            {
                DepartmentVO departmentvo=new DepartmentVO();
                log.info("取部门数据开始");
                departmentvo.setId(rs.getInt("id"));
                departmentvo.setName(rs.getString("name"));
                departmentvo.setDescription(rs.getString("description"));
                log.info(rs.getString("description"));
                departmentvo.setLeader(rs.getString("leader"));
                departmentvo.setPhone(rs.getString("phone"));
                departmentvo.setAddress(rs.getString("address"));
                departmentvo.setStarttime(rs.getString("starttime"));
                departmentvo.setInfo(rs.getString("info"));
                list.add(departmentvo);
                log.info("取部门数据结束");
            }
            conn.close();
            stmt.close();
            rs.close();
        } catch (SQLException ex) {
            ex.getMessage();
        }
        return list;
    }

       OK,拿到了所有部门的所有信息;回到上面那句:
Onlydepartments.setName(Onlydepartments.getName()); //筛选后重新放入

       看来当时我是想作一个优化,减轻页面的负担,而在后台多了下些功夫,现在想来大可不必,不如直接另写一个找差name的SQL语句。。我当时大脑在想些什么哩。。
       回到图1-1中的
request.getSession().setAttribute(Constants.ONLYDEPARTMENTS_KEY,onlydep);//集合保存,并传入下一页面

存入session中,返回到添加员工表单;
<forward name="link1_success" path="/link1.jsp">



箭头所指,就是我们刚才作遍历出来的部门集合位置。

       回到了link1.jsp,而在tiles中实际表单位置是CreateEmployee.jsp:

<definition extends="layout-definition" name="link1-definition">
<put name="content" value="return/CreateEmployee.jsp"></put>
</definition>

       下面找CreateEmployee.jsp代码,代码太多,我把主要的写上,至于其他部分感兴趣可以去下载我整个项目来看,我提供了下载。
       这里是拿到部门集合在表单上的遍历:

<html:select property="department">
              <logic:iterate id="onlydep" name="ONLYDEPARTMENTS" type="companypj.DepartmentVO" scope="session">
                <option value="<bean:write name="onlydep" property="name"/>">
                  <bean:write name="onlydep" property="name"/>
                </option>
              </logic:iterate>
            </html:select>

       name拿到了集合,type转型成VO以作分类遍历,scope指定去session中拿。
       再来看看表单的提交
<html:form action="/link_addemp.do" method="POST">

       在struts-config中找到:

<action input="/link1.jsp" name="EmpForm" path="/link_addemp" parameter="link_addemp"
scope="request" type="companypj.AddEmployeeAction" validate="true" >

       看到还是转入AddEmployeeAction,图1-1。但是validate="true",表明先要进行表单验证,那么我们就去看一下配置文件validation:

<formset>
<form name="EmpForm">
<field property="name" depends="required">
<arg0 key="label.emp.name"/>
</field>
<field property="age" depends="required">
<arg0 key="label.emp.age"/>
</field>
<field property="salary" depends="required">
<arg0 key="label.emp.salary"/>
</field>
</form>
</formset>

       简单的让人觉得可怜哈,都不为空就行!
       PS:这里是作得动态表单,而下一个超链接的部门添加是用了静态表单。别的就没有太多差别,思想都一样!
       如果验证通过,转入Action中处理,看代码:

if(type.equals("link_addemp"))
         {
            EmployeeBean empbean=new EmployeeBean(ds);
            //String address=empDynForm.get("address").toString();
            empbean.addEmployee(empDynForm);
            return mapping.findForward(Constants_url.RETURN_ADD_EMP_READY);
         }

        addEmployee方法把form接收过去:

public void addEmployee(DynaValidatorForm empDynForm) {
        EmployeeVO employeeVO = this.NynaIntoEmp(empDynForm);
        String strSQL="{call demo_empadd(?,?,?,?,?,?,?,?,?)}";//存储过程
        this.executeEmpHelper(employeeVO, strSQL);
    }

        这里我作的是一个存储过程:

Create PROCEDURE demo_empadd
@inparam1 varchar(10),@inparam2 varchar(20),@inparam3 int,
@inparam4 varchar(10),@inparam5 varchar(20),@inparam6 varchar(10),
@inparam7 varchar(20),
@inparam8 varchar(10),@inparam9 varchar(40)
AS insert into employee(name,sex,age,salary,department,marriage,address,phone,resume)values
(@inparam1,@inparam2,@inparam3,@inparam4,@inparam5,@inparam6,@inparam7,@inparam8,@inparam9)
GO

       接着再转到executeEmpHelper()方法来作实际工作,这时传入了一个VO,和一个存储过程的指令:

private void executeEmpHelper(EmployeeVO employeeVO, String sql) { //帮助方法
        try {
            Connection conn = ds.getConnection();
            java.sql.CallableStatement pstm=conn.prepareCall(sql);
            //PreparedStatement pstm = conn.prepareStatement(sql);
            log.info("雇员信息开始加入");
            pstm.setString(1, employeeVO.getName());
            pstm.setString(2, employeeVO.getSex());
            pstm.setInt(3, employeeVO.getAge());
            pstm.setString(4, employeeVO.getSalary());
            pstm.setString(5, employeeVO.getDepartment());
            pstm.setString(6, employeeVO.getMarriage());
            pstm.setString(7, employeeVO.getAddress());
            pstm.setString(8, employeeVO.getPhone());
           // log.info("1");
            pstm.setString(9, employeeVO.getResume());
           // log.info("2");
            pstm.executeUpdate();
            log.info("雇员信息加入结束");
        } catch (SQLException ex) {
        }
    }

       OK,从图1-1中的Action传回一个信号,config接收到
<forward name="link_addemp_ready" path="/link1_add_success.jsp">

       添加完成!

文章来自: 本站原创
引用通告: 查看所有引用 | 我要引用此文章
Tags: Sturts SQL存储过程
相关日志:
评论: 2 | 引用: 0 | 查看次数: -
回复回复blurxx[2007-07-29 11:33 PM | del]
引用来自 冰风 引用来自 冰风
你这个系统是商用吗?如果不是能不能把完整的源码发给我一份。我的邮箱是yuyanshan1@163.com谢谢了

这程序并非商用,只是自己练习时所写,至于你说的完整源码。以后我会传到空间上面提供下载,如果真这必要的话—_—||!
回复回复冰风[2007-07-28 10:57 AM | del]
你这个系统是商用吗?如果不是能不能把完整的源码发给我一份。我的邮箱是yuyanshan1@163.com谢谢了
发表评论
昵 称:
密 码: 游客发言不需要密码.
内 容:
验证码: 验证码
选 项:
虽然发表评论不用注册,但是为了保护您的发言权,建议您注册帐号.