# Java企业框架 实验三 全球新型冠状病毒实时数据统计应用程序的设计与实现 **Repository Path**: yanliye/spring-boot-exp03-427yeziyin ## Basic Information - **Project Name**: Java企业框架 实验三 全球新型冠状病毒实时数据统计应用程序的设计与实现 - **Description**: No description available - **Primary Language**: Java - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2020-11-23 - **Last Updated**: 2020-12-19 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # 东莞理工学院网络空间安全学院 课程名称 :企业级开发框架专题 学期:2020秋季 实验名称:全球新型冠状病毒实时数据统计应用程序的设计与实现   实验序号:三 | 姓名:叶梓茵 | 学号:201841413427 | 班级:18网工4班 | |---|---|---| | 实验地址:学校 |实验日期:2020-11-09 | 指导老师:黎志雄 | | 教师评语:XXX | 实验成绩:XXX | 百分制:XXX | 同组同学:无 ### 一、 实验目的 1、 掌握使用Spring框架自带的RestTemplate工具类爬取网络数据;
2、 掌握使用Spring框架自带的计划任务功能;
3、 掌握使用Apache Commons CSV组件解释CSV文件;
4、 掌握Java 8的Stream API处理集合类型数据;
5、 了解使用模板引擎或前端框架展示数据。 ### 二、 实验环境
1、 JDK 1.8或更高版本
2、 Maven 3.6+
3、 IntelliJ IDEA
4、 commons-csv 1.8+
### 三、 实验任务 1、 通过IntelliJ IDEA的Spring Initializr向导创建Spring Boot项目。
2、 添加功能模块:spring MVC、lombok、commons-csv等。 推荐使用commons-csv组件处理csv文件:
![输入图片说明](https://images.gitee.com/uploads/images/2020/1122/235427_b06b2ed5_8149149.png "屏幕截图.png")
3、 爬取全球冠状病毒实时统计数据。(Java,Spring) Gitee仓库的csv文件 4、 使用Spring框架自带的RestTemplate工具类爬取数据。 ```java public class Covid19DateService implements InitializingBean { //将url设置为静态且不可更改的常量 private static final String Covid19_Date_URL = "https://gitee.com/dgut-sai/COVID-19/raw/master/csse_covid_19_data/csse_covid_19_time_series/time_series_covid19_confirmed_global.csv"; private final ArrayList regionStatsList = new ArrayList<>(); private Logger Log= LoggerFactory.getLogger(Covid19DateService.class); //日志记录 //设置每日凌晨1.更新任务,更新 @Scheduled(cron = "${yzy.Schedules.updateVirusDataCron}") public void fetchCovid19Data() throws IOException{ regionStatsList.removeAll(regionStatsList); //初始化列表 if(regionStatsList.isEmpty()){ Log.info("初始化数据列表完成"); } RequestEntity requestEntity = RequestEntity.get(URI.create(Covid19_Date_URL)) .headers(httpHeaders -> httpHeaders.add("User-Agent","yeziyin")) .build(); ResponseEntity exchange = new RestTemplate().exchange(requestEntity,Resource.class); Resource body = exchange.getBody(); ``` 5、 分析csv文件的数据结构,定义model类。 ```java package com.dgutnw.yeziyin.sbexp.exp03_covid19_realtimedate.models; import lombok.Data; @Data public class RegionStats { private String state; //州/省市 private String country; //国家 private int latestTotalSaes; //统计至当天共有病例 private int diffFromPrevDay; //与前一天对比差异 } ``` 6、 使用Apache Commons CSV组件解释CSV文件。 ```java (接第4题 Covid19DateService() 后) Reader readin; if(body != null){ Log.info("数据拉取成功"); readin = new InputStreamReader(body.getInputStream()); Iterable records = CSVFormat.RFC4180.withFirstRecordAsHeader().parse(readin); for (CSVRecord record : records) { RegionStats model = new RegionStats(); model.setState(record.get("Province/State")); model.setCountry(record.get("Country/Region")); int latesttotal = Integer.parseInt(record.get(record.size() - 1)); int thedaybefore = Integer.parseInt(record.get(record.size() - 2)); model.setLatestTotalSaes(latesttotal); model.setDiffFromPrevDay(latesttotal - thedaybefore); regionStatsList.add(model); } } } ```
7、 使用Spring框架自带的计划任务功能定时更新统计数据。
![输入图片说明](https://images.gitee.com/uploads/images/2020/1123/001057_84c3bd53_8149149.png "屏幕截图.png")
![输入图片说明](https://images.gitee.com/uploads/images/2020/1123/001136_8d0883f3_8149149.png "屏幕截图.png")
8、 要确保应用程序启动时,获取一次统计数据。 ```java // 程序启动时,自动拉取一次数据 @Override public void afterPropertiesSet() throws Exception{ fetchCovid19Data(); } ``` 9、 单元测试。 ```java //设置断言测试是否成功抓取csv文件 @Test void TestCsvCatch(){ Resource csv = covid19DateService.getBody(); Assertions.assertNotNull(csv); } ``` 测试结果无报错: ![输入图片说明](https://images.gitee.com/uploads/images/2020/1123/002059_f59500b4_8149149.png "屏幕截图.png") ```java //测试是否解析数据成功 @Autowired Covid19DateService covid19DateService; @Test void ServiceTest() { try{ this.covid19DateService.fetchCovid19Data(); List TestList = covid19DateService.getRegionStatsList(); System.out.println("共爬取解析数据数:"+TestList.size()); System.out.println("前五条数据:"+TestList.subList(0,4)+"\n"); //打印出前五条数据 System.out.println("后五条数据:"+TestList.subList(TestList.size()-6,TestList.size()-1)+"\n"); //打印出后五条数据 } catch (IOException e) { e.printStackTrace(); } } ``` 测试结果成功: ![输入图片说明](https://images.gitee.com/uploads/images/2020/1123/001659_8d3a0164_8149149.png "屏幕截图.png") 10、 定义Cotroller控制器。 ```java @Controller public class HomeController { @Autowired Covid19DateService covid19DateService; @RequestMapping("/{countryn}") public String SearchCountry(Model model, @PathVariable("countryn") String country) { List RS ; if(country==null || country.equals("all")){ RS= covid19DateService.getRegionStatsList(); } else{//将查询结果收集为不可变的List集合 RS = covid19DateService.getRegionStatsList() .parallelStream().filter(locationStats -> locationStats.getCountry().equals(country)) .collect(Collectors.toUnmodifiableList()); } Date TimeAtNow = new Date(); int latestTotalCases; int diffFromPrevDayTotal; //求和 latestTotalCases= RS.stream().mapToInt(RegionStats::getLatestTotalSaes).sum(); diffFromPrevDayTotal= RS.stream().mapToInt(RegionStats::getDiffFromPrevDay).sum(); model.addAttribute("country",country); model.addAttribute("ragionStats",RS); model.addAttribute("datenow",TimeAtNow); model.addAttribute("totalReportCases",latestTotalCases); model.addAttribute("totalNewCases",diffFromPrevDayTotal); return "index"; } } ``` 11、 定义前端数据展示页面。 ![输入图片说明](https://images.gitee.com/uploads/images/2020/1123/132238_cc1c8f27_8149149.png "屏幕截图.png") ![输入图片说明](https://images.gitee.com/uploads/images/2020/1123/132304_9c43391c_8149149.png "屏幕截图.png") ### 四、 实验总结 这次实验主要是不熟悉爬取数据的部分,本来想尝试webclient,学习文档上的还是有些不熟悉,先用RestTemplate,感觉没有想象中的难上手。感觉老师的实验比较新,贴近生活实用也有趣。前端页面统计图的实现还不太熟悉,需要进一步学习,先编写了简单的列表样式,添加了搜索框。