浏览代码

易客云天气API

lvy 3 月之前
父节点
当前提交
3a37332252

+ 126 - 0
blade-common/src/main/java/org/springblade/common/utils/YiKeYunApiUtils.java

@@ -0,0 +1,126 @@
+package org.springblade.common.utils;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import lombok.extern.slf4j.Slf4j;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStreamReader;
+import java.net.URL;
+import java.nio.charset.StandardCharsets;
+import java.util.HashMap;
+import java.util.Map;
+
+@Slf4j
+public class YiKeYunApiUtils {
+    private static final String API_YIKEYUN_APPID = "97543277";
+    private static final String API_YIKEYUN_APPSECRET = "PXd7GE2j";
+
+
+
+    /**
+     * 根据城市adcode获取天气信息, 易客云 api
+     * api doc <a href="http://tianqiapi.com/index/doc?version=day"></a>
+     * @param adcode
+     * @return
+     */
+    public static Map<String, String> getTodayWeatherByAdcode(String adcode) {
+        String getUrl = String.format("http://v1.yiketianqi.com/free/day?appid=%s&appsecret=%s&unescape=1&adcode=%s", API_YIKEYUN_APPID, API_YIKEYUN_APPSECRET, adcode);
+        Map<String, String> map = new HashMap<>();
+        try {
+            URL url = new URL(getUrl);
+            BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream(), StandardCharsets.UTF_8));
+            String res;
+            StringBuilder sb = new StringBuilder();
+            while ((res = in.readLine()) != null) {
+                sb.append(res.trim());
+            }
+            log.info("获取当天天气 ======= sb.toString():" + sb);
+            JSONObject jsonData = JSONObject.parseObject(sb.toString());
+            map.put("temp", jsonData.get("tem").toString());
+            map.put("weather", jsonData.get("wea").toString());
+            map.put("high", jsonData.get("tem_day").toString());
+            map.put("low", jsonData.get("tem_night").toString());
+            map.put("windLevel", jsonData.get("win_speed").toString());
+        } catch (IOException e) {
+            e.printStackTrace();
+            return null;
+        }
+        return map;
+    }
+
+    /**
+     * 根据城市id获取天气信息, 易客云 api
+     * @param cityId
+     * @return
+     */
+    public static Map<String, String> getTodayWeatherByCityId(String cityId) {
+        String getUrl = String.format("http://v1.yiketianqi.com/free/day?appid=%s&appsecret=%s&unescape=1&cityid=%s", API_YIKEYUN_APPID, API_YIKEYUN_APPSECRET, cityId);
+        Map<String, String> map = new HashMap<>();
+        try {
+            URL url = new URL(getUrl);
+            BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream(), StandardCharsets.UTF_8));
+            String res;
+            StringBuilder sb = new StringBuilder();
+            while ((res = in.readLine()) != null) {
+                sb.append(res.trim());
+            }
+            log.info("获取当天天气 ======= sb.toString():" + sb);
+            JSONObject jsonData = JSONObject.parseObject(sb.toString());
+            map.put("temp", jsonData.get("tem").toString());
+            map.put("weather", jsonData.get("wea").toString());
+            map.put("high", jsonData.get("tem_day").toString());
+            map.put("low", jsonData.get("tem_night").toString());
+            map.put("windLevel", jsonData.get("win_speed").toString());
+        } catch (IOException e) {
+            e.printStackTrace();
+            return null;
+        }
+        return map;
+    }
+
+    /**
+     * 根据城市id获取天气信息, 易客云 api
+     * @param cityId
+     * @return
+     */
+    public static Map<String, Map<String, String>> getHistoryWeather(String cityId, Integer year, Integer month) {
+        String getUrl = String.format("http://gfeljm.tianqiapi.com/free/history?appid=%s&appsecret=%s&cityid=%s&year=%d&month=%d", API_YIKEYUN_APPID, API_YIKEYUN_APPSECRET, cityId, year, month);
+        Map<String, Map<String, String>> map = new HashMap<>();
+        try {
+            URL url = new URL(getUrl);
+            BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream(), StandardCharsets.UTF_8));
+            String res;
+            StringBuilder sb = new StringBuilder();
+            while ((res = in.readLine()) != null) {
+                sb.append(res.trim());
+            }
+            log.info("获取当天天气 ======= sb.toString():" + sb);
+            JSONObject jsonData = JSONObject.parseObject(sb.toString());
+            JSONArray list = jsonData.getJSONArray("list");
+
+            list.forEach(item -> {
+                Map<String, String> data = new HashMap<>();
+                JSONObject itemObj = (JSONObject) item;
+                data.put("weather", itemObj.getString("wea_day"));
+                data.put("low", itemObj.getString("tem_night"));
+                data.put("high", itemObj.getString("tem_day"));
+                data.put("windLevel", itemObj.getString("win_speed"));
+                String date = itemObj.getString("date");
+                // 将 yyyy-MM-dd 转化为 yyyy年MM月dd日
+                String dateFormat = date.replace("-", "年");
+                dateFormat = dateFormat.replace("-", "月") + "日";
+                map.put(dateFormat, data);
+            });
+
+
+        } catch (IOException e) {
+            e.printStackTrace();
+            return null;
+        }
+        return map;
+    }
+
+
+}

+ 70 - 23
blade-service/blade-business/src/main/java/org/springblade/business/service/impl/WeatherInfoServiceImpl.java

@@ -1,7 +1,6 @@
 package org.springblade.business.service.impl;
 
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
-import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.hankcs.hanlp.dictionary.py.Pinyin;
 import com.hankcs.hanlp.dictionary.py.PinyinDictionary;
@@ -13,27 +12,33 @@ import org.jsoup.Jsoup;
 import org.jsoup.nodes.Document;
 import org.jsoup.nodes.Element;
 import org.jsoup.select.Elements;
-import org.springblade.common.utils.BaiduApiUtil;
-import org.springblade.core.tool.utils.DateUtil;
 import org.springblade.business.entity.WeatherInfo;
 import org.springblade.business.mapper.WeatherInfoMapper;
 import org.springblade.business.service.WeatherInfoService;
-//import org.springframework.scheduling.annotation.Scheduled;
+import org.springblade.common.utils.BaiduApiUtil;
+import org.springblade.common.utils.YiKeYunApiUtils;
+import org.springblade.core.mp.support.Condition;
+import org.springblade.core.tool.utils.DateUtil;
 import org.springblade.core.tool.utils.Func;
-import org.springblade.manager.entity.ContractInfo;
 import org.springblade.manager.entity.ProjectContractArea;
 import org.springblade.manager.entity.ProjectInfo;
 import org.springblade.manager.feign.ProjectClient;
 import org.springblade.manager.feign.ProjectContractAreaClient;
 import org.springblade.manager.vo.ContractInfoVO;
-import org.springframework.scheduling.annotation.Async;
+import org.springframework.dao.DataAccessException;
+import org.springframework.jdbc.core.JdbcTemplate;
+import org.springframework.jdbc.core.ResultSetExtractor;
 import org.springframework.scheduling.annotation.Scheduled;
 import org.springframework.stereotype.Service;
-import org.springblade.core.mp.support.Condition;
 
 import java.io.IOException;
 import java.math.BigDecimal;
-import java.time.*;
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.time.Duration;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.ZoneId;
 import java.time.format.DateTimeFormatter;
 import java.util.*;
 import java.util.stream.Collectors;
@@ -47,6 +52,8 @@ public class WeatherInfoServiceImpl extends ServiceImpl<WeatherInfoMapper, Weath
 
     private final ProjectClient projectClient;
 
+    private final JdbcTemplate jdbcTemplate;
+
     /**
      * 根据所选年份获取当年所有天气台账
      */
@@ -114,7 +121,7 @@ public class WeatherInfoServiceImpl extends ServiceImpl<WeatherInfoMapper, Weath
     public void syncWeatherInfo() {
         //获取所有合同段的定位信息
         List<ProjectContractArea> areaList = this.projectContractAreaClient.queryAllContractArea();
-
+        Map<String, Map<String, String>> cachedWeatherMap = new HashMap<>();
         for (ProjectContractArea area : areaList) {
             try {
                 //校验当前区域是否已经获取当天日期(手动补填或自动获取)
@@ -128,8 +135,14 @@ public class WeatherInfoServiceImpl extends ServiceImpl<WeatherInfoMapper, Weath
                     log.info("今日的天气已经同步完成!contractAreaId:" + area.getId() + ",syncTime:" + DateUtil.format(new Date(), "yyyy-MM-dd HH:mm:ss"));
                     continue;
                 }
-                //获取天气信息(百度天气)
-                Map<String, String> weatherMap = BaiduApiUtil.getTodayWeather(area.getCity_code());
+                Map<String, String> weatherMap = cachedWeatherMap.get(area.getCity_code());
+                if (weatherMap == null) {
+                    //获取天气信息(百度天气)
+                    weatherMap = YiKeYunApiUtils.getTodayWeatherByAdcode(area.getCity_code());
+                    if (weatherMap == null) {
+                        weatherMap = BaiduApiUtil.getTodayWeather(area.getCity_code());
+                    }
+                }
                 if (weatherMap != null) {
                     //计算平均气温
                     BigDecimal aver = (new BigDecimal(weatherMap.get("high")).add(new BigDecimal(weatherMap.get("low")))).divide(new BigDecimal("2"), 1, BigDecimal.ROUND_HALF_UP);
@@ -231,13 +244,17 @@ public class WeatherInfoServiceImpl extends ServiceImpl<WeatherInfoMapper, Weath
                     while (Duration.between(plainTime, ContractTime).toDays() != 0) {
                         //判断集合中是否存在当前天气,如果不存在则获取
                         if (weatherMap == null || weatherMap.get(plainTime.format(DateTimeFormatter.ofPattern("yyyy年MM月dd日"))) == null) {
-                            weatherMap = this.getWeather(county.toString(), plainTime.format(DateTimeFormatter.ofPattern("yyyyMM")));
-                            if (weatherMap == null || weatherMap.get(plainTime.format(DateTimeFormatter.ofPattern("yyyy年MM月dd日"))) == null) {
-                                weatherMap = this.getWeather(city.toString(), plainTime.format(DateTimeFormatter.ofPattern("yyyyMM")));
-                                county = city;
+                            String month = plainTime.format(DateTimeFormatter.ofPattern("yyyyMM"));
+                            weatherMap = this.getHistoryWeather(projectContractArea, month);
+                            if (weatherMap == null) {
+                                weatherMap = this.getWeather(county.toString(), month);
                                 if (weatherMap == null || weatherMap.get(plainTime.format(DateTimeFormatter.ofPattern("yyyy年MM月dd日"))) == null) {
-                                    log.info("获取历史天气失败!contractAreaId:" + projectContractArea.getId() + ",syncTime:" + plainTime);
-                                    break;
+                                    weatherMap = this.getWeather(city.toString(), month);
+                                    county = city;
+                                    if (weatherMap == null || weatherMap.get(plainTime.format(DateTimeFormatter.ofPattern("yyyy年MM月dd日"))) == null) {
+                                        log.info("获取历史天气失败!contractAreaId:" + projectContractArea.getId() + ",syncTime:" + plainTime);
+                                        break;
+                                    }
                                 }
                             }
                         }
@@ -322,13 +339,16 @@ public class WeatherInfoServiceImpl extends ServiceImpl<WeatherInfoMapper, Weath
             Map<String, List<LocalDate>> map = missDate.stream().collect(Collectors.groupingBy(l -> l.format(DateTimeFormatter.ofPattern("yyyyMM"))));
             for (String s : map.keySet()) {
                 //获取整月天气
-                weatherMap = this.getWeather(county.toString(), s);
-                if (weatherMap == null || weatherMap.size() == 0) {
-                    weatherMap = this.getWeather(city.toString(), s);
-                    county = city;
+                weatherMap = this.getHistoryWeather(area, s);
+                if (weatherMap == null) {
+                    weatherMap = this.getWeather(county.toString(), s);
                     if (weatherMap == null || weatherMap.size() == 0) {
-                        log.info("获取历史天气失败:" + area.getCity()+"-"+area.getCounty() + ",syncTime:" + s);
-                        break;
+                        weatherMap = this.getWeather(city.toString(), s);
+                        county = city;
+                        if (weatherMap == null || weatherMap.size() == 0) {
+                            log.info("获取历史天气失败:" + area.getCity()+"-"+area.getCounty() + ",syncTime:" + s);
+                            break;
+                        }
                     }
                 }
                 //为遗漏日期设置天气
@@ -384,6 +404,33 @@ public class WeatherInfoServiceImpl extends ServiceImpl<WeatherInfoMapper, Weath
         System.out.println("9999");
     }
 
+    public Map<String, Map<String, String>> getHistoryWeather(ProjectContractArea area, String month) {
+        String county = area.getCounty();
+        if (county.length() > 2) {
+            county = county.substring(0, county.length() - 1);
+        }
+        String city = area.getCity();
+        if (city.length() > 2) {
+            city = city.substring(0, city.length() - 1);
+        }
+        Integer count = jdbcTemplate.queryForObject("select count(*) from m_yikeyun_weather_city where cityZh like '" + county + "%'", Integer.class);
+        String cityId = null;
+        if (count == null || count == 0) {
+            return null;
+        } else if (count > 1) {
+            cityId = jdbcTemplate.queryForObject("select id from m_yikeyun_weather_city where cityZh like '" + county + "%' and leaderZh like '" + city + "%' limit 1", String.class);
+        } else {
+            cityId = jdbcTemplate.queryForObject("select id from m_yikeyun_weather_city where cityZh like '" + county + "%'", String.class);
+        }
+        if (cityId != null) {
+            Map<String, Map<String, String>> historyWeather = YiKeYunApiUtils.getHistoryWeather(cityId, Integer.parseInt(month.substring(0, 4)), Integer.parseInt(month.substring(4, 6)));
+            return historyWeather;
+        } else {
+            log.info("获取历史天气失败:" + area.getCity()+"-"+area.getCounty());
+            return null;
+        }
+    }
+
     public Map<String, Map<String, String>> getWeather(String city, String month) {
         String html = "http://www.tianqihoubao.com/lishi/" + city + "/month/" + month + ".html";
         Map<String, Map<String, String>> map = new HashMap<>();