【SSM】医疗健康平台-管理端-运营数据报表导出

知识目标

  • 熟悉JasperReports的用法,能够使用JasperReports实现PDF文件导出

  • 掌握Excel方式导出运营数据报表的方法,能够使用Apache POI以Excel方式导出运营数据报表

  • 掌握PDF方式导出运营数据报表的方法,能够使用JasperReports以PDF方式导出运营数据报表

在有网络的环境下,传智健康的管理员可以随时随地浏览线上的运营数据报表,但有时候,管理员也希望能将线上的数据导出,独立保存在本地计算机中进行归档,以及做一些其他的数据加工等工作。对此,传智健康提供了两种运营数据报表导出功能,分别是 Excel 方式导出运营数据报表和 PDF 方式导出运营数据报表。接下来,本模块将对管理端的运营数据报表导出进行详细讲解。

10-1 Excel方式导出运营数据报表

运营数据报表的内容是以表格的形式展示的,为了使报表导出之后的数据格式与运营数据报表本身的数据格式保持一致,可以将页面中的报表数据写入 Excel 文件,再通过浏览器进行下载。

在浏览器中访问report_business.html 页面。

在report_business.html页面中,单击“导出Excel”按钮,导出完成后,页面底部显示下载了一个 Excel 格式的文件。

(1)提供Excel模板文件

在backend的template目录下,创建一个名称为report_template的XLSX文件作为模板文件,在该模板文件中创建一个名称为运营数据统计的sheet工作表,工作表中包含会员数据、预约与到诊数据和热门套餐。

(2)提交导出Excel文件的请求

在report_business.html页面中,为“导出 Excel”按钮绑定单击事件,并设置单击时要调用的方法,在该方法中提交导出 Excel 文件的请求。

<div class="excelTitle" >
    <el-button @click="exportExcel()">导出Excel</el-button>
    ......
</div>

在页面中定义exportExcel()方法用于导出 Excel 文件。

<script>
    var vue = new Vue({
        ......
        methods:{
            //导出Excel报表
            exportExcel(){
                window.location.href = '/report/exportBusinessReport.do';
            }
        }
    })
</script>

(3)实现Excel报表下载控制器

在 ReportController 类中定义 exportBusinessReport( )方法,用于接收并处理导出 Excel 文件的请求。 通过调用ReportService接口的getBusinessReportData()方法获取运营数据,并读取数据写入与模板对应的变量或对象中;向模板中写入数据;进行文件下载。

//导出运营数据到Excel并提供客户端下载
    @RequestMapping("/exportBusinessReport")
    public Result exportBusinessReport(HttpServletRequest request, HttpServletResponse response){
        try{
            //1.获取运营数据,并读取数据写入与模板对应的变量或对象中
            Map<String,Object> result = reportService.getBusinessReportData();
            //取出返回结果数据,准备将报表数据写入到Excel文件中
            String reportDate = (String) result.get("reportDate");
            Integer todayNewMember = (Integer) result.get("todayNewMember");
            Integer totalMember = (Integer) result.get("totalMember");
            Integer thisWeekNewMember = (Integer) result
                    .get("thisWeekNewMember");
            Integer thisMonthNewMember = (Integer) result
                    .get("thisMonthNewMember");
            Integer todayOrderNumber = (Integer) result.get("todayOrderNumber");
            Integer thisWeekOrderNumber = (Integer) result
                    .get("thisWeekOrderNumber");
            Integer thisMonthOrderNumber = (Integer) result
                    .get("thisMonthOrderNumber");
            Integer todayVisitsNumber = (Integer) result
                    .get("todayVisitsNumber");
            Integer thisWeekVisitsNumber = (Integer) result
                    .get("thisWeekVisitsNumber");
            Integer thisMonthVisitsNumber = (Integer) result
                    .get("thisMonthVisitsNumber");
            List<Map> hotSetmeal = (List<Map>) result.get("hotSetmeal");

            //2.向模板中写入数据
            //动态获取Excel模板文件绝对磁盘路径
            String filePath = request.getSession().getServletContext()
                    .getRealPath("template").split("out")[0]+"/web/backend/template"+ File.separator+"report_template.xlsx";
            //基于POI在内存中创建一个Excel文件
            XSSFWorkbook excel = new XSSFWorkbook(
                    new FileInputStream(new File(filePath)));
            XSSFSheet sheet = excel.getSheetAt(0);
            XSSFRow row = sheet.getRow(2);
            row.getCell(5).setCellValue(reportDate);//日期
            row = sheet.getRow(4);
            row.getCell(5).setCellValue(todayNewMember);//新增会员数(本日)
            row.getCell(7).setCellValue(totalMember);//总会员数
            row = sheet.getRow(5);
            row.getCell(5).setCellValue(thisWeekNewMember);//本周新增会员数
            row.getCell(7).setCellValue(thisMonthNewMember);//本月新增会员数
            row = sheet.getRow(7);
            row.getCell(5).setCellValue(todayOrderNumber);//今日预约数
            row.getCell(7).setCellValue(todayVisitsNumber);//今日到诊数
            row = sheet.getRow(8);
            row.getCell(5).setCellValue(thisWeekOrderNumber);//本周预约数
            row.getCell(7).setCellValue(thisWeekVisitsNumber);//本周到诊数
            row = sheet.getRow(9);
            row.getCell(5).setCellValue(thisMonthOrderNumber);//本月预约数
            row.getCell(7).setCellValue(thisMonthVisitsNumber);//本月到诊数
            int rowNum = 12;
            for(Map map : hotSetmeal){//热门套餐
                String name = (String) map.get("name");
                Long setmeal_count = (Long) map.get("setmeal_count");
                BigDecimal proportion = (BigDecimal) map.get("proportion");
                row = sheet.getRow(rowNum ++);
                row.getCell(4).setCellValue(name);//套餐名称
                row.getCell(5).setCellValue(setmeal_count);//预约数量
                row.getCell(6).setCellValue(proportion.doubleValue());//占比
            }
            //3.文件下载
            ServletOutputStream out = response.getOutputStream();//创建输出流
            response.setContentType("application/vnd.ms-excel");//指定响应类型
            //指定以附件形式下载
            response.setHeader("content-Disposition","attachment;filename=report.xlsx");
            excel.write(out);//写入流文件
            out.flush();//关闭缓冲区的数据流
            out.close();//关闭流对象
            excel.close();
            return null;
        }catch (Exception e){
            e.printStackTrace();
            return new Result(false, MessageConstant.GET_BUSINESS_REPORT_FAIL);
        }
    }

(4)查询运营数据

在ReportController类的exportBusinessReport()方法中,调用了ReportService接口的getBusinessReportData()方法,该方法之前已经实现,这里不再重复,直接调用即可。

(5)测试 Excel 方式导出运营数据报表

启动服务,在浏览器中访http://localhost:8080/backend/pages/report_business.html。单击“导出Excel”按钮。

10-2 PDF方式导出运营数据报表

PDF 文件在企业办公中很常用,它不仅适合阅读,而且可以防止他人修改文件内容。传智健康管理端提供 PDF 方式导出运营数据报表的功能。

在浏览器中访问 report_business.html 页面。

在 report_business.html 页面单击“导出PDF”按钮,导出完成后,页面底部显示下载了一个PDF 文件。

使用 PDF 方式导出运营数据报表时,需要按照运营数据统计页面的内容分布创建PDF文件,然后将数据填充到 PDF 文件中。在实际企业项目开发中,有两种常见的PDF文件生成方式,具体如下。 iText生成PDF。 JasperReports生成PDF。 由于 iText 的原生 API 编程比较烦琐,为了简化编程过程,在实际项目开发时,大多数情况下使用JasperReports 生成 PDF 文件。对此本任务采用JasperReports结合模板设计器Jaspersoft Studio生成PDF文件。

JasperReports简介

JasperReports是一个强大、灵活的报表生成工具,能够展示丰富的页面内容,并将之转换成PDF、HTML或者XML格式。JasperReports完全由Java语言编写而成,可以用在 J2EE、Web等 Java应用程序中生成动态内容。使用 JasperReports 时,需要导入 JasperReports 的依赖具体如下所示。

JasperReports的工作流程

第1步,创建 JRXML 文件,该文件包含报表布局定义的 XML 文档,可以通过手动编码完成,也可以使用报表设计工具 Jaspersoft Studio 完成。 第2步,使用JasperReports 提供的JasperCompileManager工具将报表模板编译为.jasper 文件; 第3步,使用 JasperReports 提供的 JasperFillManager工具填充编译后的.jasper文件,填充后生成一个.jrprint文件; 第4步,使用文件导出器 JasperExportManager 将.jrprint 文件导出成各种格式的报表文件。

JasperReports入门案例

(1)设计PDF报表模板文件

先使用模板设计器 Jaspersoft Studio 设计入门案例的报表模板文件 demo.jrxml。 将设计好的 demo.jrxml 文件复制到backend 中的template 目录下。

(2)引入JasperReports的依赖

(3)编写单元测试方法

在controller包下创建测试类TestExport,在类中定义testJasperReports( )方法,用于测试导出 PDF 文件。

/**
 * 测试类
 */
public class TestExport {
    //单元测试方法,测试PDF报表导出
    @Test
    public void testJasperReports() throws Exception{
        //获取pdf模板文件绝对磁盘路径
        String jrxmlPath ="D:\\health\\10\\health_parent\\" +
                "health_backend\\src\\main\\webapp\\template\\demo.jrxml";
        String jasperPath="D:\\health\\10\\health_parent\\" +
                "health_backend\\src\\main\\webapp\\template\\demo.jasper";
        //编译模板
        JasperCompileManager.compileReportToFile(jrxmlPath,jasperPath);
        //构造数据
        Map paramters = new HashMap();
        paramters.put("reportDate","2022-03-01");
        paramters.put("company","itcast");
        List<Map> list = new ArrayList();
        Map map1 = new HashMap();
        map1.put("name","小明");
        map1.put("address","beijing");
        map1.put("email","xiaoming@itcast.cn");
        Map map2 = new HashMap();
        map2.put("name","xiaoli");
        map2.put("address","nanjing");
        map2.put("email","xiaoli@itcast.cn");
        list.add(map1);
        list.add(map2);
        //填充数据
        JasperPrint jasperPrint = JasperFillManager.fillReport(jasperPath, paramters, new JRBeanCollectionDataSource(list));
        //输出文件
        String pdfPath = "D:\\test.pdf";
        JasperExportManager.exportReportToPdfFile(jasperPrint,pdfPath);
    }
}

(4)测试导出PDF文件

name为中文“小明”的数据没有显示出来,由于JasperReports的jar包中不包含中文的字体库,导致默认情况下中文无法正常显示,对此,可以在程序中导入中文字体库以解决中文无法显示的问题。

(5)导入中文字体库

导入的字体库文件包括fonts.xml和stsong.ttf,其中,fonts.xml用于配置字体信息,stsong.ttf表示华文宋体的字体文件。

 在resources 目录下创建 jasperreports_extension.properties 配置文件,并在配置文件中添加如下配置信息。

net.sf.jasperreports.extension.registry.factory.simple.font.families=net.sf.jasperreports.engine.fonts.SimpleFontExtensionsRegistryFactory
net.sf.jasperreports.extension.simple.font.families.lobstertwo=stsong/fonts.xml

(6)修改demo.jrxml

打开demo.jrxml模板文件查看内容,找到模板中需要显示中文的元素,统一将字体设置为华文宋体。

......
<textField>
   <reportElement x="60" y="4" width="100" height="30" 
                         uuid="9fd8ea6a-722d-4c35-a4dc-74f3ed490709"/>
   <textElement>
         <font fontName="华文宋体" size="14"/>
   </textElement>
   <textFieldExpression><![CDATA[$F{name}]]></textFieldExpression>
</textField>
......

(7)运行testJasperReports()方法

功能实现

(1)提供PDF模板文件

使用模板设计器 Jaspersoft Studio 设计运营数据报表的模板文件 health_business3.jrxml。 将设计好的模板文件复制到 backend 的 template 目录下。

(2)提交导出PDF文件的请求

在report_business.html 页面,为“导出 PDF”按钮绑定单击事件,并设置单击时要调用的方法,在方法中提交导出 PDF 文件的请求。

<div class="excelTitle" >
    <el-button @click="exportPDF()">导出PDF</el-button>
    ......
</div>

在report_business.html 页面中定义exportPDF()方法用于导出 PDF 文件。

<script>
    var vue = new Vue({
        ......
        methods:{
            //导出PDF报表
            exportPDF(){
                window.location.href = '/report/exportBusinessReport4PDF.do';
            }
        }
    })
</script>

(3)实现PDF报表下载控制器

在ReportController 类中定义exportBusinessReport4PDF( )方法,用于接收并处理导出 PDF 文件的请求。 通过调用ReportService接口的getBusinessReportData( )方法查询运营数据,并将数据存储到集合中返回。 获取PDF模板文件绝对路径,编译模板并向模板中写入数据。 设置响应头信息中的响应类型和文件下载类型,并输出对应的文件。

//导出运营数据到PDF文件并提供下载
    @RequestMapping("/exportBusinessReport4PDF")
    public Result exportBusinessReport4PDF(HttpServletRequest request, HttpServletResponse response){
        try{
            Map<String,Object> result = reportService.getBusinessReportData();
            //取出返回结果数据,准备将报表数据写入到Excel文件中
            List<Map> hotSetmeal = (List<Map>) result.get("hotSetmeal");
            //动态获取pdf模板文件绝对磁盘路径
             String jrxmlPath = request.getSession().getServletContext()
                    .getRealPath("template") .split("out")[0]+"/web/backend/template"+ File.separator +
                    "health_business3.jrxml";
           String jasperPath = request.getSession().getServletContext()
                    .getRealPath("template") .split("out")[0]+"/web/backend/template"+ File.separator + "health_business3.jasper";
            //编译模板
            JasperCompileManager.compileReportToFile(jrxmlPath, jasperPath);
            //填充数据---使用JavaBean数据源方式填充
            JasperPrint jasperPrint =
                    JasperFillManager.fillReport(jasperPath,result,
                            new JRBeanCollectionDataSource(hotSetmeal));
            //创建输出流,用于从服务器写数据到浏览器
            ServletOutputStream out = response.getOutputStream();
            response.setContentType("application/pdf");
            response.setHeader("content-Disposition","attachment;filename=report.pdf");
            //输出文件
            JasperExportManager.exportReportToPdfStream(jasperPrint,out);
            out.flush();
            out.close();
            return null;
        }catch (Exception e){
            e.printStackTrace();
            return new Result(false, MessageConstant.GET_BUSINESS_REPORT_FAIL);
        }
    }

(4)查询运营数据

在 ReportController 类的 exportBusinessReport4PDF( )方法中,调用了 ReportService 接口的 getBusinessReportData( )方法查询运营数据,由于在统计分析模块的运营数据统计功能中已经实现了运营数据的查询,这里可以直接调用查询运营数据的相关方法。

(5)测试 PDF 方式导出运营数据报表

启动服务。在浏览器中访问 http://localhost:8080/backend/pages/report_business.html,单击“导出PDF”按钮,以PDF方式导出运营数据。

在report_business.html页面中,单击“导出 PDF”按钮后,浏览器下载了一个名称为 report 的 PDF 文件。

 

模块小结

本模块主要对管理端的运营数据报表导出进行了讲解。首先讲解了 Excel 方式导出运营数据报表;其次讲解了 JasperReports 的使用并实现了 PDF 方式导出运营数据报表。希望通过本模块的学习,可以熟悉JasperReports 的使用,掌握 Excel 方式和 PDF 方式导出运营数据报表的功能。

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/748240.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

如何快速解决验证码图像问题 | 最佳图像(OCR)验证码解决工具

你是否曾经遇到过陷入一个看似无尽的 CAPTCHA 挑战中&#xff0c;努力识别扭曲的字符或数字&#xff1f;这些令人抓狂的 CAPTCHA 是为了确保你是人类而不是机器人&#xff0c;但它们也给真正的用户带来了头痛。那么&#xff0c;有没有快速解决这些 CAPTCHA 图像的方法&#xff…

SiLM59xx系列SiLM5991SHCG-DG 带有主动保护和高 CMTI 的单通道隔离门极驱动芯片

SiLM59xx系列SiLM5991SHCG-DG是一款单通道隔离驱动器&#xff0c;提供12A源电流和12A灌电流。主动保护功能包括退饱和过流检测、UVLO、隔离故障报警和 4A 米勒钳位。输入侧电源的工作电压为3V至5.5V&#xff0c;输出侧电源的工作电压范围为13V至30V。所有电源电压引脚都有欠压锁…

多车自动驾驶编队与协同控制引领智能物流革命

多车自动驾驶编队与协同控制引领智能物流革命 随着科技的不断进步&#xff0c;智能物流正以前所未有的速度和效率改变着我们的生活和工作方式。在这个领域的最前沿&#xff0c;北京渡众机器人科技有限公司的多车自动驾驶编队与协同控制技术正在为物流行业带来革命性的变革。 北…

武汉星起航:引领潮流!中国跨境出口电商展现强劲增长势头

在全球贸易结构深刻变革的当下&#xff0c;中国跨境出口电商行业正以前所未有的活力和创新能力&#xff0c;引领着中国制造业的转型升级。面对国际贸易规则的日益严格和市场需求的持续升级&#xff0c;中国制造业正通过新型营销渠道和技术条件&#xff0c;以更加开放和主动的姿…

音频概念_STFT_窗口函数

短时傅里叶变换 (Short-Time Fourier Transform, STFT) 是一种时频谱转换算法&#xff0c;它通过在时间上移动窗口函数并计算窗口内信号的频谱来获得信号在时间和频率上的信息。填充信号可以确保每个窗口都有足够的数据进行频谱计算&#xff0c;特别是在窗口函数的边缘。 窗口…

【微服务网关——Go令牌桶限流】

1. time/rate限速器使用 令牌桶限流算法rate.NewLimiter(limit,burst)产生一个新的限速器 limit表示每秒产生token数、burst表示最多存token数 Allow判断当前是否可以取到tokenWait阻塞等待直到取到tokenReverse返回等待时间&#xff08;预估的等待时间&#xff09;&#xff0…

240626_昇思学习打卡-Day8-稀疏矩阵

240626_昇思学习打卡-Day8-稀疏矩阵 稀疏矩阵 在一些应用场景中&#xff0c;比如训练二值化图像分割时&#xff0c;图像的特征是稀疏的&#xff0c;使用一堆0和极个别的1表示这些特征即费事又难看&#xff0c;此时就可以使用稀疏矩阵。通过参考大佬博文&#xff0c;结合个人理…

读AI新生:破解人机共存密码笔记13有益机器

1. 标准模型 1.1. 我们能控制一个从外太空来的超级智能实体的概率几乎为零 1.2. 随着根据标准模型设计的机器变得更加智能&#xff0c;以及它们的行动范围遍及全球&#xff0c;关闭机器这种方法越来越不可行 1.2.1. 机器将会追求它们自己的目标&#xff0c;无论目标错得多么…

禁止浏览器对input的自动填充和填充提示(适用于谷歌、火狐、Edge(原IE浏览器)等常见浏览器)

目录 1.要解决的问题2.一技能&#xff1a;原生属性&#xff0c;小试牛刀3.二技能&#xff1a;傀儡input&#xff0c;瞒天过海4.三技能&#xff1a;JavaScript出击&#xff0c;直接开大 写在前面&#xff1a; 如有转载&#xff0c;务必注明出处&#xff0c;否则后果自负。 1.要解…

Java | Leetcode Java题解之第200题岛屿数量

题目&#xff1a; 题解&#xff1a; class Solution {void dfs(char[][] grid, int r, int c) {int nr grid.length;int nc grid[0].length;if (r < 0 || c < 0 || r > nr || c > nc || grid[r][c] 0) {return;}grid[r][c] 0;dfs(grid, r - 1, c);dfs(grid, r…

Pytorch实战(一):LeNet神经网络

文章目录 一、模型实现1.1数据集的下载1.2加载数据集1.3模型训练1.4模型预测 LeNet神经网络是第一个卷积神经网络&#xff08;CNN&#xff09;&#xff0c;首次采用了卷积层、池化层这两个全新的神经网络组件&#xff0c;接收灰度图像&#xff0c;并输出其中包含的手写数字&…

STM32之IIC(软件)

介绍 IIC &#xff08; 又称为 I2C 或 IC &#xff09;是一种串行通信协议&#xff0c; IIC使用两根线路来进行通信&#xff1a; 串行数据线&#xff08;SDA&#xff09; 和 串行时钟线&#xff08;SCL&#xff09; 。 SDA 线上的数据在 SCL 线的时钟信号下进行 同步传输。 主…

安宝特方案 | AR术者培养:AR眼镜如何帮助医生从“看”到“做”?

每一种新药品的上市都需要通过大量的临床试验&#xff0c;而每一种新的手术工具在普及使用之前也需要经过反复的实践和验证。医疗器械公司都面临着这样的挑战&#xff1a;如何促使保守谨慎的医生从仅仅观察新工具在手术中的应用&#xff0c;转变为在实际手术中实操这项工具。安…

centos7迁移部分成功

早闻CentOS不再维护的消息&#xff0c;确实有些遗憾&#xff0c;毕竟这个系统好用又简单&#xff0c;已经成为了我们工作中的一种习惯。然而&#xff0c;2024年6月30日这一天如约而至&#xff0c;CentOS 7停止维护后&#xff0c;随之而来的安全漏洞又该如何防范&#xff1f;系统…

Stirling-PDF 安装和使用教程

PDF (便携式文档格式) 目前已经成为了文档交换和存储的标准。然而&#xff0c;找到一个功能全面、安全可靠、且完全本地化的 PDF 处理工具并不容易。很多在线 PDF 工具存在隐私和安全风险&#xff0c;而桌面软件往往价格昂贵或功能有限。那么&#xff0c;有没有一种解决方案能够…

Linux安装JDk教程

&#x1f4d6;Linux安装JDk教程 ✅下载✅安装 ✅下载 官方Oracle地址&#xff1a;https://www.oracle.com/java/technologies/downloads/archive/ 123云盘&#xff1a;https://www.123pan.com/s/4brbVv-JdmWA.html ✅安装 1.上传安装包jdk-17_linux-x64_bin.tar.gz到指定位…

java易错题型(复习必看)

java易错题型&#xff1a; 下列符号中&#xff0c;哪个用于分隔throws关键字抛出的多个异常 逗号&#xff0c; Java中用来声明一个方法可能抛出某种异常的关键字是throw 对于catch子句的排列&#xff0c;下列哪种是正确的&#xff1a;子类异常在先&#xff0c;父类异常在后&a…

解决“Duplicate keys detected: ‘ ‘.This may cause an update error.”问题

问题原因 出现“Duplicate keys detected”的错误&#xff0c;通常表示在v-for指令中使的:key绑定值有重复。 如果前端是静态数据&#xff0c;一般能自我避免:key绑定值有重复。如果前端是绑定的动态数据&#xff0c;那么需要另外提供一个唯一的键。 在这个例子中&#xff0c…

CV每日论文--2024.6.26

1、StableNormal: Reducing Diffusion Variance for Stable and Sharp Normal 中文标题&#xff1a;StableNormal&#xff1a;减少扩散方差以实现稳定且锐利的法线 简介&#xff1a;本文介绍了一种创新解决方案&#xff0c;旨在优化单目彩色输入&#xff08;包括静态图片与动态…

糖与蛋白质的“隐秘对话”:DeepGlycanSite如何揭示生命之谜

在生命的复杂舞台上&#xff0c;糖类与蛋白质之间的相互作用犹如一场精心编排的舞蹈&#xff0c;其背后的每一个细微动作都可能对生物体的生理与病理过程产生深远影响。然而&#xff0c;糖类分子的多样性和复杂性&#xff0c;使得科学家们对糖-蛋白质结合位点的识别和研究充满了…