传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(二)

简介: 传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)

2.6 发送短信

2.6.1 导入maven坐标

<dependency>
  <groupId>com.aliyun</groupId>
  <artifactId>aliyun-java-sdk-core</artifactId>
  <version>3.3.1</version>
</dependency>
<dependency>
  <groupId>com.aliyun</groupId>
  <artifactId>aliyun-java-sdk-dysmsapi</artifactId>
  <version>1.0.0</version>
</dependency>

2.6.2 封装工具类

package com.itheima.utils;
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.IAcsClient;
import com.aliyuncs.dysmsapi.model.v20170525.SendSmsRequest;
import com.aliyuncs.dysmsapi.model.v20170525.SendSmsResponse;
import com.aliyuncs.exceptions.ClientException;
import com.aliyuncs.http.MethodType;
import com.aliyuncs.profile.DefaultProfile;
import com.aliyuncs.profile.IClientProfile;
/**
 * 短信发送工具类
 */
public class SMSUtils {
  public static final String VALIDATE_CODE = "SMS_159620392";//发送短信验证码
  public static final String ORDER_NOTICE = "SMS_159771588";//体检预约成功通知
  /**
   * 发送短信
   * @param phoneNumbers
   * @param param
   * @throws ClientException
   */
  public static void sendShortMessage(String templateCode,String phoneNumbers,String param) throws ClientException{
    // 设置超时时间-可自行调整
    System.setProperty("sun.net.client.defaultConnectTimeout", "10000");
    System.setProperty("sun.net.client.defaultReadTimeout", "10000");
    // 初始化ascClient需要的几个参数
    final String product = "Dysmsapi";// 短信API产品名称(短信产品名固定,无需修改)
    final String domain = "dysmsapi.aliyuncs.com";// 短信API产品域名(接口地址固定,无需修改)
    // 替换成你的AK
    final String accessKeyId = "accessKeyId";// 你的accessKeyId,参考本文档步骤2
    final String accessKeySecret = "accessKeySecret";// 你的accessKeySecret,参考本文档步骤2
    // 初始化ascClient,暂时不支持多region(请勿修改)
    IClientProfile profile = DefaultProfile.getProfile("cn-hangzhou", accessKeyId, accessKeySecret);
    DefaultProfile.addEndpoint("cn-hangzhou", "cn-hangzhou", product, domain);
    IAcsClient acsClient = new DefaultAcsClient(profile);
    // 组装请求对象
    SendSmsRequest request = new SendSmsRequest();
    // 使用post提交
    request.setMethod(MethodType.POST);
    // 必填:待发送手机号。支持以逗号分隔的形式进行批量调用,批量上限为1000个手机号码,批量调用相对于单条调用及时性稍有延迟,验证码类型的短信推荐使用单条调用的方式
    request.setPhoneNumbers(phoneNumbers);
    // 必填:短信签名-可在短信控制台中找到
    request.setSignName("传智健康");
    // 必填:短信模板-可在短信控制台中找到
    request.setTemplateCode(templateCode);
    // 可选:模板中的变量替换JSON串,如模板内容为"亲爱的${name},您的验证码为${code}"时,此处的值为
    // 友情提示:如果JSON中需要带换行符,请参照标准的JSON协议对换行符的要求,比如短信内容中包含\r\n的情况在JSON中需要表示成\\r\\n,否则会导致JSON在服务端解析失败
    request.setTemplateParam("{\"code\":\""+param+"\"}");
    // 可选-上行短信扩展码(扩展码字段控制在7位或以下,无特殊需求用户请忽略此字段)
    // request.setSmsUpExtendCode("90997");
    // 可选:outId为提供给业务方扩展字段,最终在短信回执消息中将此值带回给调用者
    // request.setOutId("yourOutId");
    // 请求失败这里会抛ClientException异常
    SendSmsResponse sendSmsResponse = acsClient.getAcsResponse(request);
    if (sendSmsResponse.getCode() != null && sendSmsResponse.getCode().equals("OK")) {
      // 请求成功
      System.out.println("请求成功");
    }
  }
}

2.6.3 测试短信发送

public static void main(String[] args)throws Exception {
    SMSUtils.sendShortMessage("SMS_159620392","13812345678","1234");
}


3.定时任务组件Quartz

3.1 Quartz介绍


Quartz是Job scheduling**(作业调度)领域的一个开源项目,Quartz既可以单独使用也可以跟spring框架整合使用**,在实际开发中一般会使用后者。使用Quartz可以开发一个或者多个定时任务,每个定时任务可以单独指定执行的时间,例如每隔1小时执行一次、每个月第一天上午10点执行一次、每个月最后一天下午5点执行一次等。


官网:http://www.quartz-scheduler.org/


maven坐标:


<dependency>
  <groupId>org.quartz-scheduler</groupId>
  <artifactId>quartz</artifactId>
  <version>2.2.1</version>
</dependency>
<dependency>
  <groupId>org.quartz-scheduler</groupId>
  <artifactId>quartz-jobs</artifactId>
  <version>2.2.1</version>
</dependency>

3.2 Quartz入门案例

本案例基于Quartz和spring整合的方式使用。具体步骤:

(1)创建maven工程quartzdemo,导入Quartz和spring相关坐标,pom.xml文件如下

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.itheima</groupId>
    <artifactId>quartdemo</artifactId>
    <version>1.0-SNAPSHOT</version>
    <dependencies>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context-support</artifactId>
            <version>5.0.2.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-tx</artifactId>
            <version>5.0.2.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>org.quartz-scheduler</groupId>
            <artifactId>quartz</artifactId>
            <version>2.2.1</version>
        </dependency>
        <dependency>
            <groupId>org.quartz-scheduler</groupId>
            <artifactId>quartz-jobs</artifactId>
            <version>2.2.1</version>
        </dependency>
    </dependencies>
</project>

(2)自定义一个Job

package com.itheima.jobs;
/**
 * 自定义Job
 */
public class JobDemo {
    public void run(){
        System.out.println("job execute...");
    }
}

(3)提供Spring配置文件spring-jobs.xml,配置自定义Job、任务描述、触发器、调度工厂等

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
            http://www.springframework.org/schema/beans/spring-beans.xsd
            http://www.springframework.org/schema/mvc
            http://www.springframework.org/schema/mvc/spring-mvc.xsd
            http://code.alibabatech.com/schema/dubbo
            http://code.alibabatech.com/schema/dubbo/dubbo.xsd
            http://www.springframework.org/schema/context
            http://www.springframework.org/schema/context/spring-context.xsd">
  <!-- 注册自定义Job -->
    <bean id="jobDemo" class="com.itheima.jobs.JobDemo"></bean>
  <!-- 注册JobDetail,作用是负责通过反射调用指定的Job -->
    <bean id="jobDetail" 
          class="org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean">
        <!-- 注入目标对象 -->
        <property name="targetObject" ref="jobDemo"/>
        <!-- 注入目标方法 -->
        <property name="targetMethod" value="run"/>
    </bean>
    <!-- 注册一个触发器,指定任务触发的时间 -->
    <bean id="myTrigger" class="org.springframework.scheduling.quartz.CronTriggerFactoryBean">
        <!-- 注入JobDetail -->
        <property name="jobDetail" ref="jobDetail"/>
        <!-- 指定触发的时间,基于Cron表达式 -->
        <property name="cronExpression">
            <value>0/10 * * * * ?</value>
        </property>
    </bean>
    <!-- 注册一个统一的调度工厂,通过这个调度工厂调度任务 -->
    <bean id="scheduler" class="org.springframework.scheduling.quartz.SchedulerFactoryBean">
        <!-- 注入多个触发器 -->
        <property name="triggers">
            <list>
                <ref bean="myTrigger"/>
            </list>
        </property>
    </bean>
</beans>

(4)编写main方法进行测试

package com.itheima.jobs.com.itheima.app;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class App {
    public static void main(String[] args) {
        new ClassPathXmlApplicationContext("spring-jobs.xml");
    }
}

执行上面main方法观察控制台,可以发现每隔10秒会输出一次,说明每隔10秒自定义Job被调用一次。

b3251ed3edc6ee5836ffc3a74b8b8bd9.png

3.3 cron表达式

上面的入门案例中我们指定了一个表达式:0/10 * * * * ?

这种表达式称为cron表达式,通过cron表达式可以灵活的定义出符合要求的程序执行的时间。本小节我们就来学习一下cron表达式的使用方法。如下图:

ea24c6fc5aa993cbda7dd6ba7575ec18.png

cron表达式分为七个域,之间使用空格分隔。其中最后一个域(年)可以为空。每个域都有自己允许的值和一些特殊字符构成。使用这些特殊字符可以使我们定义的表达式更加灵活。


下面是对这些特殊字符的介绍:


逗号(,):指定一个值列表,例如使用在月域上1,4,5,7表示1月、4月、5月和7月


横杠(-):指定一个范围,例如在时域上3-6表示3点到6点(即3点、4点、5点、6点)


星号(*):表示这个域上包含所有合法的值。例如,在月份域上使用星号意味着每个月都会触发


斜线(/):表示递增,例如使用在秒域上0/15表示每15秒


问号(?):只能用在日和周域上,但是不能在这两个域上同时使用。表示不指定


井号(#):只能使用在周域上,用于指定月份中的第几周的哪一天,例如6#3,意思是某月的第三个周五 (6=星期五,3意味着月份中的第三周)


L:某域上允许的最后一个值。只能使用在日和周域上。当用在日域上,表示的是在月域上指定的月份的最后一天。用于周域上时,表示周的最后一天,就是星期六


W:W 字符代表着工作日 (星期一到星期五),只能用在日域上,它用来指定离指定日的最近的一个工作日


3.4 cron表达式在线生成器


前面介绍了cron表达式,但是自己编写表达式还是有一些困难的,我们可以借助一些cron表达式在线生成器来根据我们的需求生成表达式即可。


http://cron.qqe2.com/


6835bcb72b32c80c4d4924911bcfc576.png


4. 图形报表ECharts


4.1 ECharts简介


ECharts缩写来自Enterprise Charts,商业级数据图表,是百度的一个开源的使用JavaScript实现的数据可视化工具,可以流畅的运行在 PC 和移动设备上,兼容当前绝大部分浏览器(IE8/9/10/11,Chrome,Firefox,Safari等),底层依赖轻量级的矢量图形库 ZRender,提供直观、交互丰富、可高度个性化定制的数据可视化图表。


官网:https://echarts.baidu.com/


下载地址:https://echarts.baidu.com/download.html


04902bca21cf39d0d3b3def3a9b8aff9.png


下载完成可以得到如下文件:


eb1f543106fc4b765533e6862348fee0.png


解压上面的zip文件:


2fcf3058f164d8419710a9026378861c.png


我们只需要将dist目录下的echarts.js文件引入到页面上就可以使用了


c9bd0019cc4a6ea8f5802d8b411482d3.png


4.2 5分钟上手ECharts


我们可以参考官方提供的5分钟上手ECharts文档感受一下ECharts的使用方式,地址如下:


https://www.echartsjs.com/tutorial.html#5%20%E5%88%86%E9%92%9F%E4%B8%8A%E6%89%8B%20ECharts


第一步:创建html页面并引入echarts.js文件

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <!-- 引入 ECharts 文件 -->
    <script src="echarts.js"></script>
</head>
</html>

第二步:在页面中准备一个具备宽高的DOM容器。

<body>
    <!-- 为 ECharts 准备一个具备大小(宽高)的 DOM -->
    <div id="main" style="width: 600px;height:400px;"></div>
</body>

第三步:通过echarts.init方法初始化一个 echarts 实例并通过setOption方法生成一个简单的柱状图

<script type="text/javascript">
  // 基于准备好的dom,初始化echarts实例
  var myChart = echarts.init(document.getElementById('main'));
  // 指定图表的配置项和数据
  var option = {
    title: {
      text: 'ECharts 入门示例'
    },
    tooltip: {},
    legend: {
      data:['销量']
    },
    xAxis: {
      data: ["衬衫","羊毛衫","雪纺衫","裤子","高跟鞋","袜子"]
    },
    yAxis: {},
    series: [{
      name: '销量',
      type: 'bar',
      data: [5, 20, 36, 10, 10, 20]
    }]
};
// 使用刚指定的配置项和数据显示图表。
myChart.setOption(option);
</script>

效果如下:


932c0c3a3f1d9a75c0779faba4c1eb47.png


4.3 查看ECharts官方实例


ECharts提供了很多官方实例,我们可以通过这些官方实例来查看展示效果和使用方法。


官方实例地址:https://www.echartsjs.com/examples/


9f64c8ee7979ac5d55d29201a02aa7e6.png


可以点击具体的一个图形会跳转到编辑页面,编辑页面左侧展示源码(js部分源码),右侧展示图表效果,如下:


0a32c82baa56c61d07d530ccc124ee71.png


要查看完整代码可以点击右下角的Download按钮将完整页面下载到本地。


通过官方案例我们可以发现,使用ECharts展示图表效果,关键点在于确定此图表所需的数据格式,然后按照此数据格式提供数据就可以了,我们无须关注效果是如何渲染出来的。


在实际应用中,我们要展示的数据往往存储在数据库中,所以我们可以发送ajax请求获取数据库中的数据并转为图表所需的数据即可。


5. Apache POI


5.1 POI介绍


Apache POI是用Java编写的免费开源的跨平台的Java API,Apache POI提供API给Java程序对Microsoft Office格式档案读和写的功能,其中使用最多的就是使用POI操作Excel文件。


jxl:专门操作Excel


maven坐标:

<dependency>
  <groupId>org.apache.poi</groupId>
  <artifactId>poi</artifactId>
  <version>3.14</version>
</dependency>
<dependency>
  <groupId>org.apache.poi</groupId>
  <artifactId>poi-ooxml</artifactId>
  <version>3.14</version>
</dependency>

POI结构:

HSSF - 提供读写Microsoft Excel XLS格式档案的功能
XSSF - 提供读写Microsoft Excel OOXML XLSX格式档案的功能
HWPF - 提供读写Microsoft Word DOC格式档案的功能
HSLF - 提供读写Microsoft PowerPoint格式档案的功能
HDGF - 提供读Microsoft Visio格式档案的功能
HPBF - 提供读Microsoft Publisher格式档案的功能
HSMF - 提供读Microsoft Outlook格式档案的功能

5.2 入门案例

5.2.1 从Excel文件读取数据

使用POI可以从一个已经存在的Excel文件中读取数据

//创建工作簿
XSSFWorkbook workbook = new XSSFWorkbook("D:\\hello.xlsx");
//获取工作表,既可以根据工作表的顺序获取,也可以根据工作表的名称获取
XSSFSheet sheet = workbook.getSheetAt(0);
//遍历工作表获得行对象
for (Row row : sheet) {
  //遍历行对象获取单元格对象
  for (Cell cell : row) {
    //获得单元格中的值
    String value = cell.getStringCellValue();
    System.out.println(value);
  }
}
workbook.close();

通过上面的入门案例可以看到,POI操作Excel表格封装了几个核心对象:

XSSFWorkbook:工作簿
XSSFSheet:工作表
Row:行
Cell:单元格

上面案例是通过遍历工作表获得行,遍历行获得单元格,最终获取单元格中的值。

还有一种方式就是获取工作表最后一个行号,从而根据行号获得行对象,通过行获取最后一个单元格索引,从而根据单元格索引获取每行的一个单元格对象,代码如下:

//创建工作簿
XSSFWorkbook workbook = new XSSFWorkbook("D:\\hello.xlsx");
//获取工作表,既可以根据工作表的顺序获取,也可以根据工作表的名称获取
XSSFSheet sheet = workbook.getSheetAt(0);
//获取当前工作表最后一行的行号,行号从0开始
int lastRowNum = sheet.getLastRowNum();
for(int i=0;i<=lastRowNum;i++){
  //根据行号获取行对象
  XSSFRow row = sheet.getRow(i);
  short lastCellNum = row.getLastCellNum();
  for(short j=0;j<lastCellNum;j++){
    String value = row.getCell(j).getStringCellValue();
    System.out.println(value);
  }
}
workbook.close();

5.2.2 向Excel文件写入数据

使用POI可以在内存中创建一个Excel文件并将数据写入到这个文件,最后通过输出流将内存中的Excel文件下载到磁盘

//在内存中创建一个Excel文件
XSSFWorkbook workbook = new XSSFWorkbook();
//创建工作表,指定工作表名称
XSSFSheet sheet = workbook.createSheet("传智播客");
//创建行,0表示第一行
XSSFRow row = sheet.createRow(0);
//创建单元格,0表示第一个单元格
row.createCell(0).setCellValue("编号");
row.createCell(1).setCellValue("名称");
row.createCell(2).setCellValue("年龄");
XSSFRow row1 = sheet.createRow(1);
row1.createCell(0).setCellValue("1");
row1.createCell(1).setCellValue("小明");
row1.createCell(2).setCellValue("10");
XSSFRow row2 = sheet.createRow(2);
row2.createCell(0).setCellValue("2");
row2.createCell(1).setCellValue("小王");
row2.createCell(2).setCellValue("20");
//通过输出流将workbook对象下载到磁盘
FileOutputStream out = new FileOutputStream("D:\\itcast.xlsx");
workbook.write(out);
out.flush();
out.close();
workbook.close();

6.PDF报表生成技术—JasperReports

6. 1常见的PDF报表生成方式

6.1.1 iText

iText是著名的开放源码的站点sourceforge一个项目,是用于生成PDF文档的一个java类库。通过iText不仅可以生成PDF或rtf的文档,而且可以将XML、Html文件转化为PDF文件。 iText的安装非常方便,下载iText.jar文件后,只需要在系统的CLASSPATH中加入iText.jar的路径,在程序中就可以使用iText类库了。


maven坐标:


<dependency>
  <groupId>com.lowagie</groupId>
  <artifactId>itext</artifactId>
  <version>2.1.7</version>
</dependency>

示例代码:

package com.itheima.app;
import com.lowagie.text.Document;
import com.lowagie.text.DocumentException;
import com.lowagie.text.Paragraph;
import com.lowagie.text.pdf.PdfWriter;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
public class ItextDemo {
    public static void main(String[] args) {
        try {
            Document document = new Document();
            PdfWriter.getInstance(document, new FileOutputStream("D:\\test.pdf"));
            document.open();
            document.add(new Paragraph("hello itext"));
            document.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (DocumentException e) {
            e.printStackTrace();
        }
    }
}
package com.ithe
相关文章
|
6月前
|
人工智能 自然语言处理 BI
草料二维码表单功能:轻松收集和管理数据
表单作为草料二维码的高级功能之一,可用于收集格式统一的数据。你可以通过组合姓名、图片、检查项等组件搭建出电子表单,关联到二维码中,扫码填写表单即可更快速、规范的收集数据。 这些数据保存在账号下形成动态档案,可以导出Excel或PDF进行存档;也可以根据企业要求自定义PDF导出格式。
204 2
|
6月前
|
JavaScript 小程序 Java
基于Java+SpringBoot+Vue的大学生考勤系统的设计与实现(亮点:多角色、打卡签到、请假审批、上传成绩单文件、统计图展示)
基于Java+SpringBoot+Vue的大学生考勤系统的设计与实现(亮点:多角色、打卡签到、请假审批、上传成绩单文件、统计图展示)
301 0
基于Java+SpringBoot+Vue的大学生考勤系统的设计与实现(亮点:多角色、打卡签到、请假审批、上传成绩单文件、统计图展示)
|
6月前
|
监控 安全 BI
宜搭报表中,如何实现将报表定时下载并推送到群里
宜搭报表中,如何实现将报表定时下载并推送到群里
|
BI 数据库
汇总报表怎么做,如何设计实现汇总报表?
汇总报表怎么做,如何设计实现汇总报表?
|
SQL 存储 Java
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(四)
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(四)
|
存储 Java BI
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(一)
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(一)
|
XML 存储 开发框架
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(三)
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)
传智健康项目中相关知识点介绍(如图片存储,发送短信,定时调度,统计报表...)(三)
|
JSON 分布式计算 大数据
行政区统计_功能实现|学习笔记
快速学习行政区统计_功能实现
114 0
行政区统计_功能实现|学习笔记
|
JSON 关系型数据库 大数据
电商项目之用户行为日志字段分析|学习笔记
快速学习电商项目之用户行为日志字段分析
|
小程序 API
实战:业务逻辑设计(疫苗预约)进度记录
实战:业务逻辑设计(疫苗预约)进度记录
202 0
实战:业务逻辑设计(疫苗预约)进度记录