day56_电力项目_POI导出JXL导入

项目第九天(分页+报表)

1:分页

原理分析:
userIndex.jsp
这里写图片描述

userList.jsp
这里写图片描述

原理:
pub.js(dom对象的ajax封装)
1:在userIndex.jsp中存在2个Form表单(Form1和Form2)
2:传递表单Form1中的元素作为参数传递给服务器的参数,在服务器端进行处理,将处理后的结果(即分页后的结果)显示在userList.jsp中
3:将userList.jsp的内容,放置到userIndex.jsp的Form2中

整合项目步骤:

第一步:导入2个java文件,放置到util包下
这里写图片描述

表示:
这里写图片描述

PageBean中的内容:

    private int pageNo;//存放当前页
    private boolean firstPage;//当前页是否是第一页:是:true
    private boolean lastPage; //当前页是否是最后一页:是:true
    private int sumPage;//总页数
    private int pageSize ;//当前页最多显示几条记录
    private int totalResult ;//总记录数

第二步:导入一个js文件,page.js放置到script包下
这里写图片描述

第三步:修改userIndex.jsp的内容:
(1)添加:


<script language="javascript" src="${pageContext.request.contextPath }/script/page.js"></script>
<script language="javascript" src="${pageContext.request.contextPath }/script/validate.js"></script>
<script language="javascript"
src="${pageContext.request.contextPath }/script/pub.js"></script>

(2)修改【查询】按钮的连接

<input style="font-size:12px; color:black; height=20;width=80" id="BT_Add" type="button" value="查询" name="BT_find" 
onclick="gotoquery('elecUserAction_home.do')">&nbsp;&nbsp;

(3)在Form1的表单中添加2个隐藏域

<s:hidden name="initPage" value="1"></s:hidden>
<!-- 处理分页必须要传递的属性(当前页) -->
<s:hidden name="pageNO"></s:hidden>

(4)在Form2的表单中,加载pageUI.jsp,这个jsp页面显示分页的相关信息,添加:

<%@include file="/WEB-INF/page/pageUI.jsp" %>

第四步:将userIndex.jsp的Form2表单的内容,单独提取出来,命名为userList.jsp

第五步:在struts.xml中添加:

<result name="list">/WEB-INF/page/system/userList.jsp</result>

第六步:在Action类中添加:

//判断:什么情况调整到userList.jsp,什么情况调整到userIndex.jsp
String initPage = request.getParameter("initPage");
if(initPage!=null && initPage.equals("1")){
    //调整到userList.jsp(执行ajax的分页)
    return "list";
}

第七步:在Service类中添加:

PageInfo pageInfo = new PageInfo(ServletActionContext.getRequest());
* currentPageNo:表示当前页(从PageNO中获取)
* pageSize:表示默认该页最多显示多少条记录
 * req:存放request对象
List<ElecUser> list = elecUserDao.findCollectionByConditionWithPage(condition, params, orderby,pageInfo);
ServletActionContext.getRequest().setAttribute("page",pageInfo.getPageBean());
第八步:在Dao类中添加:
pageInfo.setTotalResult(query.list().size());
* totalResult:存放总记录数
* totalPage:存放总页数
query.setFirstResult(pageInfo.getBeginResult());//当前页从第几条开始检索,默认是0,0表示第1条
* currentPageNo:存放当前页;
* beginResult:表示当前页从第几条开始检索,默认是0;
* pageSize:表示当前页做多显示的记录数;
query.setMaxResults(pageInfo.getPageSize());//表示当前页最多显示多少条记录

2:POI报表(excel文件的导出)

(1)POI报表整合项目

第一步:导入jar包:
这里写图片描述

第二步:导入java文件(使用poi生成excel报表,放置到输出流中),类放置到util包下
这里写图片描述

第三步:在userIndex.jsp中定义:
(1)添加按钮

<input style="font-size:12px; color:black; height=20;width=80" id="BT_Export" type="button" value="导出设置" name="BT_Export"       onclick="openWindow('${pageContext.request.contextPath }/system/elecExportFieldsAction_setExportExcel.do?belongTo=5-1','700','400')">&nbsp;&nbsp;

<input style="font-size:12px; color:black; height=20;width=80" id="BT_Add" type="button" value="导出" name="BT_Add" onclick="exportExcel()">&nbsp;&nbsp;

(2)js代码:

//导出excel
function exportExcel(){
    var userName = document.getElementById("userName").value;
    userName = encodeURI(userName,"UTF-8");
    userName = encodeURI(userName,"UTF-8");
    var jctID = document.getElementById("jctID").value;
    var onDutyDateBegin = document.getElementById("onDutyDateBegin").value;
    var onDutyDateEnd = document.getElementById("onDutyDateEnd").value;
    openWindow('${pageContext.request.contextPath }/system/elecUserAction_exportExcel.do?userName='+userName+'&jctID='+jctID+'&onDutyDateBegin='+onDutyDateBegin+'&onDutyDateEnd='+onDutyDateEnd,'700','400')
}

第四步:在Action类中定义:

/**  
    * @Name: exportExcel
    * @Description: 用户列表的信息动态导出excel
    * @Author: 刘洋(作者)
    * @Version: V1.00 (版本号)
    * @Create Date:
    * @Parameters: 无
    * @Return: String:null(不使用struts2的方式,完成流的操作)
    */
    public String exportExcel() throws Exception{
        //构造2个数据集合
        //构造excel的标题
        ArrayList<String> fieldName = elecUserService.findExcelFiledName();
        //构造excel的数据
        ArrayList<ArrayList<String>> fieldData = elecUserService.findExcelFieldData(elecUser);

        //使用ExcelFileGenerator完成导出
        ExcelFileGenerator excelFileGenerator = new ExcelFileGenerator(fieldName,fieldData);
        OutputStream os = response.getOutputStream();
        //导出excel建议加上重置输出流,可以不加该代码,但是如果不加必须要保证输出流中不应该在存在其他数据,否则导出会有问题
        response.reset();
        //配置:
        //文件名
        String fileName = "用户报表("+new SimpleDateFormat("yyyyMMddHHmmss").format(new Date())+").xls";
        fileName = new String(fileName.getBytes("gbk"),"iso-8859-1");
        response.setContentType("application/vnd.ms-excel");
        response.setHeader("Content-disposition", "attachment;filename="+fileName);
        response.setBufferSize(1024);

        //导出excel的操作
        excelFileGenerator.expordExcel(os);
        return null;
    }

    /**  
    * @Name: exportExcel
    * @Description: 用户列表的信息动态导出excel
    * @Author: 刘洋(作者)
    * @Version: V1.00 (版本号)
    * @Create Date: 
    * @Parameters: 无
    * @Return: String:success(使用struts2的方式,完成流的操作)
    */
    public String exportExcel() throws Exception{
        //构造2个数据集合
        //构造excel的标题
        ArrayList<String> fieldName = elecUserService.findExcelFiledName();
        //构造excel的数据
        ArrayList<ArrayList<String>> fieldData = elecUserService.findExcelFieldData(elecUser);

        //使用ExcelFileGenerator完成导出
        ExcelFileGenerator excelFileGenerator = new ExcelFileGenerator(fieldName,fieldData);
        ByteArrayOutputStream os = new ByteArrayOutputStream();
        //导出excel建议加上重置输出流,可以不加该代码,但是如果不加必须要保证输出流中不应该在存在其他数据,否则导出会有问题
        response.reset();
        //配置:
        //文件名
        String fileName = "用户报表("+new SimpleDateFormat("yyyyMMddHHmmss").format(new Date())+").xls";
        fileName = new String(fileName.getBytes("gbk"),"iso-8859-1");
        request.setAttribute("filename", fileName);

        //导出excel的操作
        excelFileGenerator.expordExcel(os);

        //将输入流的文件,放置到栈顶的Inputstream中
        byte [] buf = os.toByteArray();
        ByteArrayInputStream in = new ByteArrayInputStream(buf);
        elecUser.setInputStream(in);
        return "success";
    }

第五步:在Service类中定义(构造数据集合):

/**  
    * @Name: findExcelFiledName
    * @Description: 构造excel的标题内容
    * @Author: 刘洋(作者)
    * @Version: V1.00 (版本号)
    * @Parameters: 无
    * @Return: ArrayList<String>:excel的标题:
    *           ArrayList<String> fieldName
                  fieldName.add("登录名");
                  fieldName.add("用户姓名");
                  ...
    */
    public ArrayList<String> findExcelFiledName() {
        //查询导出设置表,主键是用户管理5-1的设置
        ElecExportFields elecExportFields = elecExportFieldsDao.findObjectByID("5-1");
        //获取导出中文的名称
        String zName = elecExportFields.getExpNameList();
        //将String类型的字符,按照#号分割成集合
        List<String> list = StringToListUtils.stringToList(zName, "#");
        ArrayList<String> filedName = new ArrayList<String>(list);
        return filedName;
    }

    /**  
    * @Name: findExcelFieldData
    * @Description: 构造excel的数据内容
    * @Author: 刘洋(作者)
    * @Version: V1.00 (版本号)
    * @Create Date: 
    * @Parameters: ElecUser:VO对象
    * @Return: ArrayList<ArrayList<String>> fieldData:存放的时候所有的数据
                  ArrayList<String> data1:存放的是每一条的数据
                    data1.add("liubei");
                    data1.add("刘备");
                    ...
                  ArrayList<String> data2:存放的是每一条的数据
                    data2.add("zhugeliang");
                    data2.add("诸葛亮");
                    …
                  fieldData.add(data1);
                  fieldData.add(data2);
    */
    public ArrayList<ArrayList<String>> findExcelFieldData(ElecUser elecUser) {
        //返回最后的结果集
        ArrayList<ArrayList<String>> fieldData = new ArrayList<ArrayList<String>>();

        //查询导出设置表,主键是用户管理5-1的设置
        ElecExportFields elecExportFields = elecExportFieldsDao.findObjectByID("5-1");
        //获取导出中文的名称
        String zName = elecExportFields.getExpNameList();
        //将String类型的字符,按照#号分割成集合
        List<String> zlist = StringToListUtils.stringToList(zName, "#");
        //获取导出英文的名称
        String eName = elecExportFields.getExpFieldName();
        //将英文字段的#号替换成逗号
        String selectCondition = eName.replace("#", ",");

        //封装查询条件
        String condition = "";
        List<Object> paramsList = new ArrayList<Object>();
        //姓名
        String userName = elecUser.getUserName();
        //处理乱码
        try {
            userName = URLDecoder.decode(userName, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
        if(StringUtils.isNotBlank(userName)){
            condition += " and o.userName like ?";
            paramsList.add("%"+userName+"%");
        }
        //所属单位
        if(StringUtils.isNotBlank(elecUser.getJctID())){
            condition += " and o.jctID = ?";
            paramsList.add(elecUser.getJctID());
        }
        //入职开始时间
        if(elecUser.getOnDutyDateBegin()!=null){
            condition += " and o.onDutyDate >= ?";
            paramsList.add(elecUser.getOnDutyDateBegin());
        }
        //入职结束时间
        if(elecUser.getOnDutyDateEnd()!=null){
            condition += " and o.onDutyDate <= ?";
            paramsList.add(elecUser.getOnDutyDateEnd());
        }
        Object [] params = paramsList.toArray();
        //排序:按照入职时间升序
        Map<String, String> orderby = new LinkedHashMap<String, String>();
        orderby.put("o.onDutyDate", "asc");
        //处理查询,list总存放的时候所有的记录
        List list = elecUserDao.findCollectionByConditionNoPageWithSelectCondition(condition, params, orderby,selectCondition);
        //遍历list
        if(list!=null && list.size()>0){
            for(int i=0;i<list.size();i++){
                //统一使用数组的方式存放每一条的数据
                Object [] arrays = null;
                //如果投影查询是多个字段,返回的是Object数组对象
                if(selectCondition.contains(",")){
                    arrays = (Object[]) list.get(i);
                }
                //如果投影查询是一个字段,返回的是Object对象
                else{
                    arrays = new Object[1];
                    arrays[0] = list.get(i);
                }
                //封装成每一条的数据
                ArrayList<String> data = new ArrayList<String>();
                if(arrays!=null && arrays.length>0){
                    for(int j=0;j<arrays.length;j++){
                        //获取每个字段的值
                        Object o = arrays[j];
                        //数据字典的转换(由于使用的中文和英文要一一对应)
                        if(zlist!=null && zlist.get(j).equals("性别") || zlist.get(j).equals("所属单位") || zlist.get(j).equals("职位") || zlist.get(j).equals("是否在职")){
                            data.add(o!=null?elecSystemDDLDao.findDdlNameByKeywordAndDdlCode(zlist.get(j), o.toString()):"");
                        }
                        else{
                            data.add(o!=null?o.toString():"");
                        }
                    }
                }
                fieldData.add(data);
            }
        }
        return fieldData;
    }

第六步:使用struts2方式的导出
(1)配置struts.xml

<result name="success" type="stream">
    <param name="contentType">application/vnd.ms-excel</param>
    <param name="inputName">inputStream</param>
    <param name="contentDisposition">attachment;filename="${#request.filename}.xls"</param>
    <param name="bufferSize">1024</param>
</result>

(2)在模型驱动的对象中添加:

//导出excel文件的流
    private InputStream inputStream;

    public InputStream getInputStream() {
        return inputStream;
    }
    public void setInputStream(InputStream inputStream) {
        this.inputStream = inputStream;
    }

(2)POI报表的几个核心对象
这里写图片描述

(3)POI报表(应对面试)

面试的时候,如果问到使用poi报表如何处理数据导出的?
这里写图片描述

导出功能:
(1)作用一:导出excel报表
(2)作用二:分公司每个月将每个月录入的数据,【导出】excel报表,传递给总部,总部可以执行【导入】,将数据添加到总部的系统

3:Get请求出现乱码的解决方案

Get请求出现乱码,模拟一般出现的场景。
(2)超链接
(3)window.opon(“url?name=张三&age=18”)

解决方案:
方案一:
在jsp中的js代码定义:

userName = encodeURI(userName,"UTF-8");

在Action类中定义:

//获取流程定义的key
String userName = elecUser.getUserName(); 
try {
    userName = new String(userName.getBytes("iso-8859-1"),"UTF-8");
} catch (UnsupportedEncodingException e) {
    e.printStackTrace();
}

方案二:
在jsp中定义:

userName = encodeURI(userName,"UTF-8");
userName = encodeURI(userName,"UTF-8");//将中文转换成二进制的格式

在Action类中定义:

//获取流程定义的key
String userName = elecUser.getUserName(); 
try {
userName = URLDecoder.decode(userName, "UTF-8");
} catch (UnsupportedEncodingException e) {
    e.printStackTrace();
}

方案三:
修改服务器(tomcat)的配置文件
这里写图片描述
Server.xml中的配置:
这里写图片描述

4:JXL报表(excel文件的导入)

(1)JXL报表整合项目

第一步:导入jar包:
这里写图片描述

第二步:导入java文件(完成封装),从文件中获取Excel的数据,读取excel的数据,写到集合中,将类放置到util包下。
这里写图片描述

第三步:导入jsp文件,实现文件上传,使用<s:file>标签
这里写图片描述

指定导入模板,用户在导入模板上填写数据,从导入模板获取数据并读取数据,导入到数据库中。

第四步:在userIndex.jsp中定义:

<input style="font-size:12px; color:black; height=20;width=80" id="BT_Add" type="button" value="导入" name="BT_Add"       onclick="openWindow('${pageContext.request.contextPath }/system/elecUserAction_importPage.do','700','400')">&nbsp;&nbsp;

第五步:在struts.xml中定义:跳转到导入excel的页面(文件上传)

<result name="importPage">/WEB-INF/page/system/userImport.jsp</result>

第六步:在Action类中定义:

/**  
    * @Name: importPage
    * @Description: 跳转到导入excel报表的页面
    * @Author: 刘洋(作者)
    * @Version: V1.00 (版本号)
    * @Create Date: 
    * @Parameters: 无
    * @Return: String:跳转到system/userImport.jsp
    */
    public String importPage(){
        return "importPage";
    }

    /**  
    * @Name: importData
    * @Description: 从excel中读取数据,将数据保存到数据库表中
    * @Author: 刘洋(作者)
    * @Version: V1.00 (版本号)
    * @Create Date: 
    * @Parameters: 无
    * @Return: String:跳转到system/userImport.jsp
    */
    public String importData() throws Exception{
        //获取上传的文件File
        File formFile = elecUser.getFile();
        GenerateSqlFromExcel fromExcel = new GenerateSqlFromExcel();
        ArrayList<String[]> data = fromExcel.generateUserSql(formFile);
        //定义一个错误的集合,String用来存放错误的信息
        List<String> errorList = new ArrayList<String>();
        //组织PO对象,完成保存
        List<ElecUser> list = this.convertFromExcelToUser(data,errorList);
        //说明存在了错误信息
        if(errorList!=null && errorList.size()>0){
            //将错误的信息在页面中显示
            request.setAttribute("errorList", errorList);
        }
        //说明不存在错误信息
        else{
            //执行批量的保存
            elecUserService.saveUserList(list);
        }
        return "importPage";
    }

    /**组织PO对象的集合,校验的方法*/
    private List<ElecUser> convertFromExcelToUser(ArrayList<String[]> data,List<String> errorList) {
        //定义返回的用户PO的集合
        List<ElecUser> list = new ArrayList<ElecUser>();
        if(data!=null && data.size()>0){
            for(int i=0;i<data.size();i++){
                //每一行的数据,格式:gj  123 郭靖  男   北京  北京中关村   是   1982-1-10   部门经理
                String arrays [] = data.get(i);
                //组织成对象,满足数据库保存字段的格式要正确
                ElecUser elecUser = new ElecUser();
                //登录名
                if(StringUtils.isNotBlank(arrays[0])){
                    String message = elecUserService.checkUserByLogonName(arrays[0]);
                    if(message!=null && message.equals("3")){
                        elecUser.setLogonName(arrays[0]);
                    }
                    else{
                        errorList.add("第"+(i+2)+"行,第"+(0+1)+"列,登录名在数据库中出现重复!");
                    }
                }
                else{
                    errorList.add("第"+(i+2)+"行,第"+(0+1)+"列,登录名为空!");
                }
                //密码
                //添加默认密码
                if(StringUtils.isBlank(arrays[1])){
                    arrays[1] = "123";
                }
                if(StringUtils.isNotBlank(arrays[1])){
                    MD5keyBean md5keyBean = new MD5keyBean();
                    String md5LogonPwd = md5keyBean.getkeyBeanofStr(arrays[1]);
                    elecUser.setLogonPwd(md5LogonPwd);
                }

                //用户姓名
                if(StringUtils.isNotBlank(arrays[2])){
                    elecUser.setUserName(arrays[2]);
                }

                //性别
                if(StringUtils.isNotBlank(arrays[3])){
                    //数据字典转换
                    String ddlCode = elecSystemDDLService.findDdlCodeByKeywordAndDdlName("性别", arrays[3]);
                    if(StringUtils.isNotBlank(ddlCode)){
                        elecUser.setSexID(ddlCode);
                    }
                    else{
                        errorList.add("第"+(i+2)+"行,第"+(3+1)+"列,性别转换出现异常!");
                    }

                }
                else{
                    errorList.add("第"+(i+2)+"行,第"+(3+1)+"列,性别不能为空!");
                }
                //所属单位
                if(StringUtils.isNotBlank(arrays[4])){
                    //数据字典转换
                    String ddlCode = elecSystemDDLService.findDdlCodeByKeywordAndDdlName("所属单位", arrays[4]);
                    if(StringUtils.isNotBlank(ddlCode)){
                        elecUser.setJctID(ddlCode);
                    }
                    else{
                        errorList.add("第"+(i+2)+"行,第"+(4+1)+"列,所属单位转换出现异常!");
                    }

                }
                else{
                    errorList.add("第"+(i+2)+"行,第"+(4+1)+"列,所属单位不能为空!");
                }

                //联系地址
                if(StringUtils.isNotBlank(arrays[5])){
                    elecUser.setAddress(arrays[5]);
                }

                //是否在职
                if(StringUtils.isNotBlank(arrays[6])){
                    //数据字典转换
                    String ddlCode = elecSystemDDLService.findDdlCodeByKeywordAndDdlName("是否在职", arrays[6]);
                    if(StringUtils.isNotBlank(ddlCode)){
                        elecUser.setIsDuty(ddlCode);
                    }
                    else{
                        errorList.add("第"+(i+2)+"行,第"+(6+1)+"列,是否在职转换出现异常!");
                    }

                }
                else{
                    errorList.add("第"+(i+2)+"行,第"+(6+1)+"列,是否在职不能为空!");
                }

                //出生时间
                if(StringUtils.isNotBlank(arrays[7])){
                    Date birthday = DateUtils.stringToDate(arrays[7]);
                    elecUser.setBirthday(birthday);
                }

                //职位
                if(StringUtils.isNotBlank(arrays[8])){
                    //数据字典转换
                    String ddlCode = elecSystemDDLService.findDdlCodeByKeywordAndDdlName("职位", arrays[8]);
                    if(StringUtils.isNotBlank(ddlCode)){
                        elecUser.setPostID(ddlCode);
                    }
                    else{
                        errorList.add("第"+(i+2)+"行,第"+(8+1)+"列,职位转换出现异常!");
                    }

                }
                else{
                    errorList.add("第"+(i+2)+"行,第"+(8+1)+"列,职位不能为空!");
                }
                list.add(elecUser);
            }
        }
        return list;
    }

第七步:在Service类中定义:

@Transactional(isolation=Isolation.DEFAULT,propagation=Propagation.REQUIRED,readOnly=false)
    public void saveUserList(List<ElecUser> list) {
        elecUserDao.saveObjectList(list);
    }

第八步:在Dao类中定义:

/**批量保存对象集合*/
    public void saveObjectList(List<T> list) {
        this.getHibernateTemplate().saveOrUpdateAll(list);
    }

(2)JXL报表的几个核心对象
这里写图片描述

(3)JXL报表(应对面试)
面试的时候,如果问到如何实现excel报表数据导入的?即导入流程:

这里写图片描述

这里写图片描述

(4)扩展:excel字段实现动态导入

分析:导入和未导入字段的设置
这里写图片描述

保存数据库的结果:(字段显示的是导入中文字段和导入英文字段)
这里写图片描述

即:按照导入的中文字段生成excel模板

操作步骤如下:
这里写图片描述

注意:JXL报表只支持office2003的操作,不支持office2007的操作,即只支持.xls格式的文件,不支持.xlsx类型的文件,那么此时可以使用POI报表完成导入。

导入的相关操作:大家可以参考【技术资料\poi报表\附加:使用poi报表完成excel文件的导入】中的《帮助.doc》

5:需要掌握的知识点总结

重点:分页+报表
了解:报表的导入和导出的设计思想、分页思想

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值