浏览代码

Merge #49 into master from pingkang

feat(drama): 新增快手短剧剧集报表功能

* pingkang: (2 commits)
  feat(kuaishou): 新增快手短剧剧集及剧集详情批量插入功能
  feat(drama): 新增快手短剧剧集报表功能

Signed-off-by: 黄平康 <accounts_6361eaad7b63b44dd7833e63@mail.teambition.com>
Merged-by: 黄平康 <accounts_6361eaad7b63b44dd7833e63@mail.teambition.com>

CR-link: https://codeup.aliyun.com/60c06368dbbed34fe0f0c263/job/hr_job-kuaishou/change/49
huangpingkang 8 月之前
父节点
当前提交
7d1ef13e4c

+ 1 - 0
.gitignore

@@ -32,3 +32,4 @@ gen
 hs_err_pid*
 **/target/
 #application.yml
+.ace-tool/

+ 15 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/controller/KuaiShouDramaController.java

@@ -94,4 +94,19 @@ public class KuaiShouDramaController {
         return MessageModel.ok();
     }
 
+    @GetMapping("/episodeReport")
+    public MessageModel episodeReport(@RequestParam(required = false) Long adminAdvertiserId,
+                                      @RequestParam(required = false) String startDate,
+                                      @RequestParam(required = false) String endDate) {
+        startDate = startDate == null ? DateUtils.getAnotherDay("yyyy-MM-dd", -2) : startDate;
+        endDate = endDate == null ? DateUtils.getAnotherDay("yyyy-MM-dd", -2) : endDate;
+        List<JSONObject> allAdvertiserIdsInfo = kuaiShouDramaService.queryAdminAdvertiserToken(adminAdvertiserId);
+        for (JSONObject info : allAdvertiserIdsInfo) {
+            Long advertiserId = info.getLong("admin_advertiser_id");
+            String accessToken = info.getString("access_token");
+            kuaiShouDramaService.queryEpisodeReport(accessToken, advertiserId, startDate, endDate, 1, null, null);
+        }
+        return MessageModel.ok();
+    }
+
 }

+ 1 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/constant/KuaishouLinkConstants.java

@@ -19,6 +19,7 @@ public class KuaishouLinkConstants {
     public static final String DRAMA_SALER_COPY_RIGHT_DATA = "/rest/openapi/gw/dsp/series/report/querySalerCopyRightData";
     public static final String DRAMA_SALER_DATA = "/rest/openapi/gw/dsp/series/report/querySalerData";
     public static final String DRAMA_SERIES_INFO = "/rest/openapi/gw/dsp/series/report/querySeriesInfo";
+    public static final String DRAMA_EPISODE_REPORT = "/rest/openapi/gw/dsp/series/report/queryEpisodeDetail";
     public static final String AD_SOCIAL_TASK_LIST = "/rest/openapi/gw/ad_social/v1/quick_task/task/list";
     public static final String AD_SOCIAL_ORDER_LIST = "/rest/openapi/gw/ad_social/v1/quick_task/order/list";
     public static final String AD_SOCIAL_ORDER_DAILY_DATA = "/rest/openapi/gw/ad_social/v1/quick_task/video/order/daily_data";

+ 20 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/entity/KuaiShouDramaEpisodeInfo.java

@@ -0,0 +1,20 @@
+package cn.com.ctop.job.kuaishou.data.entity;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.io.Serializable;
+
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+public class KuaiShouDramaEpisodeInfo implements Serializable {
+    private Long adminAdvertiserId;
+    private Long seriesId;
+    private String seriesName;
+    private Long episodeId;
+    private String episodeName;
+    private Integer orderNo;
+    private Boolean freeEpisode;
+}

+ 23 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/entity/KuaiShouDramaEpisodeReport.java

@@ -0,0 +1,23 @@
+package cn.com.ctop.job.kuaishou.data.entity;
+
+import lombok.Data;
+
+import java.io.Serializable;
+
+@Data
+public class KuaiShouDramaEpisodeReport implements Serializable {
+    private Long adminAdvertiserId;
+    private Integer statDate;
+    private Long seriesId;
+    private Long episodeId;
+    private String accountId;
+    private String resourceType;
+    private Integer isPayEpisode;
+    private String seriesPayTemplateId;
+    private Integer showCnt;
+    private Integer playCnt;
+    private Integer completePlayCnt;
+    private Integer payPanelShowCnt;
+    private Integer payPanelClickCnt;
+    private Double payAmt;
+}

+ 8 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/mapper/KuaiShouDramaMapper.java

@@ -1,6 +1,8 @@
 package cn.com.ctop.job.kuaishou.data.mapper;
 
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaAdReportDetail;
+import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaEpisodeInfo;
+import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaEpisodeReport;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaOrder;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaSalerCopyRightData;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaSeriesInfo;
@@ -33,5 +35,11 @@ public interface KuaiShouDramaMapper {
 
 
     List<JSONObject> queryAdminAdvertiserToken(@Param("adminAdvertiserId") Long adminAdvertiserId);
+
+    void insertEpisodeInfo(List<KuaiShouDramaEpisodeInfo> episodeInfoList);
+
+    void insertEpisodeReport(List<KuaiShouDramaEpisodeReport> episodeReportList);
+
+    List<Long> querySeriesIdsByDate(@Param("adminAdvertiserId") Long adminAdvertiserId, @Param("statDate") Integer statDate);
 }
 

+ 52 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/mapper/xml/KuaiShouDramaMapper.xml

@@ -284,4 +284,56 @@
         </if>
     </select>
 
+    <insert id="insertEpisodeInfo" parameterType="java.util.List">
+        replace INTO media_api.kuaishou_drama_episode_info (
+        admin_advertiser_id, series_id, series_name, episode_id, episode_name, order_no, free_episode
+        ) VALUES
+        <foreach collection="list" item="item" index="index" separator=",">
+            (
+            #{item.adminAdvertiserId},
+            #{item.seriesId},
+            #{item.seriesName},
+            #{item.episodeId},
+            #{item.episodeName},
+            #{item.orderNo},
+            #{item.freeEpisode}
+            )
+        </foreach>
+    </insert>
+
+    <insert id="insertEpisodeReport" parameterType="java.util.List">
+        replace INTO media_api.kuaishou_drama_episode_report (
+        admin_advertiser_id, stat_date, series_id, episode_id, account_id, resource_type, is_pay_episode,
+        series_pay_template_id, show_cnt, play_cnt, complete_play_cnt, pay_panel_show_cnt, pay_panel_click_cnt, pay_amt
+        ) VALUES
+        <foreach collection="list" item="item" index="index" separator=",">
+            (
+            #{item.adminAdvertiserId},
+            #{item.statDate},
+            #{item.seriesId},
+            #{item.episodeId},
+            #{item.accountId},
+            #{item.resourceType},
+            #{item.isPayEpisode},
+            #{item.seriesPayTemplateId},
+            #{item.showCnt},
+            #{item.playCnt},
+            #{item.completePlayCnt},
+            #{item.payPanelShowCnt},
+            #{item.payPanelClickCnt},
+            #{item.payAmt}
+            )
+        </foreach>
+    </insert>
+
+    <select id="querySeriesIdsByDate" resultType="java.lang.Long">
+        SELECT DISTINCT series_id FROM (
+            SELECT series_id FROM media_api.kuaishou_drama_order
+            WHERE admin_advertiser_id = #{adminAdvertiserId} AND stat_date = #{statDate}
+            UNION
+            SELECT series_id FROM media_api.kuaishou_drama_ad_detail
+            WHERE admin_advertiser_id = #{adminAdvertiserId} AND stat_date = #{statDate}
+        ) t
+    </select>
+
 </mapper>

+ 2 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/service/IKuaiShouDramaService.java

@@ -20,4 +20,6 @@ public interface IKuaiShouDramaService {
     List<JSONObject> queryAdminAdvertiserToken(Long adminAdvertiserId);
 
     void querySeriesEpisodeNum(String accessToken, Long advertiserId, String startDate, String endDate);
+
+    void queryEpisodeReport(String accessToken, Long advertiserId, String startDate, String endDate, Integer isLog, Long errId, Integer isSend);
 }

+ 127 - 20
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/service/impl/KuaiShouDramaServiceImpl.java

@@ -2,6 +2,8 @@ package cn.com.ctop.job.kuaishou.data.service.impl;
 
 import cn.com.ctop.job.kuaishou.data.constant.KuaishouLinkConstants;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaAdReportDetail;
+import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaEpisodeInfo;
+import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaEpisodeReport;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaOrder;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaSalerCopyRightData;
 import cn.com.ctop.job.kuaishou.data.entity.KuaiShouDramaSeriesInfo;
@@ -267,7 +269,7 @@ public class KuaiShouDramaServiceImpl implements IKuaiShouDramaService {
             if (isLog != null && isLog == 1 && (null == code || code != 3)) {
                 errorLogService.addError(advertiserId, startDate, endDate, "drama_saler_cr_data", "daily", new JSONObject().fluentPut("msg", message).fluentPut("seriesType", seriesType).toJSONString(), 2);
             }
-            if (code != null && code == 3 && errId != null){
+            if (code != null && code == 3 && errId != null) {
                 errorLogService.deleteInfoByErrorId(errId);
             }
             return;
@@ -437,7 +439,7 @@ public class KuaiShouDramaServiceImpl implements IKuaiShouDramaService {
         if (!Check.isNull(seriesIds)) {
             updateSeriesEpisodeNum(advertiserId, accessToken, seriesIds);
         }
-        log.error("批量获取快手短剧剧集信息完成 accountId:{}", advertiserId);
+        log.info("批量获取快手短剧剧集信息完成 accountId:{}", advertiserId);
     }
 
 
@@ -456,31 +458,49 @@ public class KuaiShouDramaServiceImpl implements IKuaiShouDramaService {
             Integer code = resultJson.getInteger("code");
             String message = resultJson.getString("message");
             if (null == code || code != 0) {
-                log.error("批量获取快手短剧剧集信息查询接口异常:{},accountId:{}", message, advertiserId);
-            }
-            JSONArray data = resultJson.getJSONArray("data");
-            List<KuaiShouDramaSeriesInfo> seriesInfos = new ArrayList<>();
-            for (Object datum : data) {
-                JSONObject seriesInfo = JSONObject.parseObject(datum.toString());
-                JSONArray episodeList = seriesInfo.getJSONArray("episode_list");
-                String seriesName = seriesInfo.getString("mini_series_name");
-                Long seriesId = seriesInfo.getLong("mini_series_id");
-                Integer episodeNum = null;
-                if (!Check.isNull(episodeList)) {
-                    episodeNum = episodeList.size();
+                log.error("批量获取快手短剧剧集信息查询接口异常:{},accountId:{},seriesIds:{}", message, advertiserId, param.get("mini_series_ids"));
+            } else {
+                JSONArray data = resultJson.getJSONArray("data");
+                List<KuaiShouDramaSeriesInfo> seriesInfos = new ArrayList<>();
+                List<KuaiShouDramaEpisodeInfo> episodeInfos = new ArrayList<>();
+                for (Object datum : data) {
+                    JSONObject seriesInfo = JSONObject.parseObject(datum.toString());
+                    JSONArray episodeList = seriesInfo.getJSONArray("episode_list");
+                    String seriesName = seriesInfo.getString("mini_series_name");
+                    Long seriesId = seriesInfo.getLong("mini_series_id");
+                    Integer episodeNum = null;
+                    if (!Check.isNull(episodeList)) {
+                        episodeNum = episodeList.size();
+                        for (int i = 0; i < episodeList.size(); i++) {
+                            JSONObject episodeJson = episodeList.getJSONObject(i);
+                            KuaiShouDramaEpisodeInfo episodeInfo = new KuaiShouDramaEpisodeInfo();
+                            episodeInfo.setAdminAdvertiserId(advertiserId);
+                            episodeInfo.setSeriesId(seriesId);
+                            episodeInfo.setSeriesName(seriesName);
+                            episodeInfo.setEpisodeId(episodeJson.getLong("episode_id"));
+                            episodeInfo.setEpisodeName(episodeJson.getString("episode_name"));
+                            episodeInfo.setOrderNo(episodeJson.getInteger("order_no"));
+                            episodeInfo.setFreeEpisode(episodeJson.getBoolean("free_episode"));
+                            episodeInfos.add(episodeInfo);
+                        }
+                    }
+                    KuaiShouDramaSeriesInfo kuaiShouDramaSeriesInfo = new KuaiShouDramaSeriesInfo(advertiserId, seriesId, seriesName, null, null, episodeNum);
+                    seriesInfos.add(kuaiShouDramaSeriesInfo);
                 }
-                KuaiShouDramaSeriesInfo kuaiShouDramaSeriesInfo = new KuaiShouDramaSeriesInfo(advertiserId, seriesId, seriesName, null, null, episodeNum);
-                seriesInfos.add(kuaiShouDramaSeriesInfo);
-            }
-            if (!Check.isNull(seriesInfos)) {
-                kuaiShouDramaMapper.insertSeriesInfo(seriesInfos);
+                if (!Check.isNull(seriesInfos)) {
+                    kuaiShouDramaMapper.insertSeriesInfo(seriesInfos);
+                }
+                if (!Check.isNull(episodeInfos)) {
+                    kuaiShouDramaMapper.insertEpisodeInfo(episodeInfos);
+                }
+                log.info("批量获取快手短剧剧集信息查询接口成功:{},accountId:{},seriesIds:{}", message, advertiserId, param.get("mini_series_ids"));
             }
             if (size > 20) {
                 List<Long> longs = new ArrayList<>(seriesIds.subList(20, size));
                 updateSeriesEpisodeNum(advertiserId, accessToken, longs);
             }
         } catch (Exception e) {
-            e.printStackTrace();
+            log.error("updateSeriesEpisodeNum error, advertiserId:{}", advertiserId, e);
         }
 
     }
@@ -525,4 +545,91 @@ public class KuaiShouDramaServiceImpl implements IKuaiShouDramaService {
         }
         return seriesName;
     }
+
+    @Override
+    public void queryEpisodeReport(String accessToken, Long advertiserId, String startDate, String endDate, Integer isLog, Long errId, Integer isSend) {
+        Integer statDate = DateUtils.getIntegerDate(startDate);
+        List<Long> seriesIds = kuaiShouDramaMapper.querySeriesIdsByDate(advertiserId, statDate);
+        if (Check.isNull(seriesIds)) {
+            log.info("【{}】无需查询的短剧剧集报表 {} {}", advertiserId, startDate, endDate);
+            return;
+        }
+        int batchSize = 20;
+        for (int i = 0; i < seriesIds.size(); i += batchSize) {
+            List<Long> batchSeriesIds = seriesIds.subList(i, Math.min(i + batchSize, seriesIds.size()));
+            queryEpisodeReportBySeriesIds(accessToken, advertiserId, startDate, endDate, batchSeriesIds, 1, isLog, errId, isSend);
+        }
+        log.info("【{}】录入快手短剧剧集报表数据完成 {} {}", advertiserId, startDate, endDate);
+        if (errId != null) {
+            errorLogService.deleteInfoByErrorId(errId);
+        }
+        if (isSend != null && isSend == 1) {
+            AlertUtils.sendMessage(advertiserId, startDate, endDate, 2, "daily", 1, "drama_episode_report");
+        }
+    }
+
+    private void queryEpisodeReportBySeriesIds(String accessToken, Long advertiserId, String startDate, String endDate, List<Long> seriesIds, int page, Integer isLog, Long errId, Integer isSend) {
+        String url = KuaishouLinkConstants.KS_PREFIX + KuaishouLinkConstants.DRAMA_EPISODE_REPORT;
+        Map<String, String> headers = new HashMap<>();
+        headers.put("Content-Type", "application/json");
+        headers.put("Access-Token", accessToken);
+        Map<String, Object> param = new HashMap<>();
+        int pageSize = 100;
+        param.put("advertiser_id", advertiserId);
+        param.put("start_date", DateUtils.timeToStamp(startDate + " 00:00:00"));
+        param.put("end_date", DateUtils.timeToStamp(endDate + " 23:59:59"));
+        param.put("series_ids", seriesIds);
+        param.put("page_size", pageSize);
+        param.put("page_no", page);
+        String result = HttpUtils.httpPostRequest(url, param, headers);
+        if (Check.isNull(result)) {
+            log.error("获取快手短剧剧集报表接口异常:{},accountId:{}", "返回结果为空", advertiserId);
+            if (isLog != null && isLog == 1) {
+                errorLogService.addError(advertiserId, startDate, endDate, "drama_episode_report", "daily", "返回结果为空", 2);
+            }
+            return;
+        }
+        JSONObject resultJson = JSONObject.parseObject(result);
+        Integer code = resultJson.getInteger("code");
+        String message = resultJson.getString("message");
+        if (null == code || code != 0) {
+            log.error("获取快手短剧剧集报表接口异常:{},accountId:{}", message, advertiserId);
+            if (isLog != null && isLog == 1) {
+                errorLogService.addError(advertiserId, startDate, endDate, "drama_episode_report", "daily", message, 2);
+            }
+            return;
+        }
+        JSONObject data = resultJson.getJSONObject("data");
+        int totalCount = data.getIntValue("total_count");
+        int totalPage = (int) Math.ceil(totalCount * 1.0 / pageSize);
+        JSONArray details = data.getJSONArray("data_list");
+        List<KuaiShouDramaEpisodeReport> addList = new ArrayList<>();
+        if (!Check.isNull(details)) {
+            for (int i = 0; i < details.size(); i++) {
+                JSONObject detailJson = details.getJSONObject(i);
+                KuaiShouDramaEpisodeReport report = new KuaiShouDramaEpisodeReport();
+                report.setAdminAdvertiserId(advertiserId);
+                report.setStatDate(DateUtils.getIntegerDate(detailJson.getString("report_date")));
+                report.setSeriesId(detailJson.getLong("series_id"));
+                report.setEpisodeId(detailJson.getLong("episode_id"));
+                report.setAccountId(detailJson.getString("account_id"));
+                report.setResourceType(detailJson.getString("resource_type"));
+                report.setIsPayEpisode(detailJson.getInteger("is_pay_episode"));
+                report.setSeriesPayTemplateId(detailJson.getString("series_pay_template_id"));
+                report.setShowCnt(detailJson.getInteger("show_cnt"));
+                report.setPlayCnt(detailJson.getInteger("play_cnt"));
+                report.setCompletePlayCnt(detailJson.getInteger("complete_play_cnt"));
+                report.setPayPanelShowCnt(detailJson.getInteger("pay_panel_show_cnt"));
+                report.setPayPanelClickCnt(detailJson.getInteger("pay_panel_click_cnt"));
+                report.setPayAmt(detailJson.getDouble("pay_amt"));
+                addList.add(report);
+            }
+        }
+        if (!Check.isNull(addList)) {
+            kuaiShouDramaMapper.insertEpisodeReport(addList);
+        }
+        if (page < totalPage) {
+            queryEpisodeReportBySeriesIds(accessToken, advertiserId, startDate, endDate, seriesIds, page + 1, isLog, errId, isSend);
+        }
+    }
 }

+ 8 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/data/utils/DateUtils.java

@@ -58,6 +58,14 @@ public class DateUtils {
         return sdf.format(resultDate);
     }
 
+    public static String getAnotherDay(String format, Integer num) {
+        SimpleDateFormat sdf = new SimpleDateFormat(format);
+        Calendar calendar = Calendar.getInstance();
+        calendar.add(Calendar.DAY_OF_MONTH, num);
+        Date resultDate = calendar.getTime();
+        return sdf.format(resultDate);
+    }
+
     /**
      * 获取两个时间中的每一天
      *

+ 15 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/handler/KuaiShouDramaJob.java

@@ -113,4 +113,19 @@ public class KuaiShouDramaJob {
         String endDate = DateUtils.getAddMinuteDate("yyyy-MM-dd", 0);
         kuaiShouDramaService.querySeriesEpisodeNum(accessToken, adminAdvertiserId, startDate, endDate);
     }
+
+    @XxlJob("dramaEpisodeReport")
+    public void episodeReport() {
+        String param = XxlJobHelper.getJobParam(); // 执行参数
+        if (Check.isNull(param)) {
+            log.error("入参为空");
+            return;
+        }
+        String startDate = DateUtils.getAnotherDay("yyyy-MM-dd", -2);
+        String endDate = DateUtils.getAnotherDay("yyyy-MM-dd", -2);
+        String[] s = param.split("_");
+        Long adminAdvertiserId = Long.valueOf(s[0]);
+        String accessToken = s[1];
+        kuaiShouDramaService.queryEpisodeReport(accessToken, adminAdvertiserId, startDate, endDate, 1, null, null);
+    }
 }

+ 9 - 0
job-kuaishou/src/main/java/cn/com/ctop/job/kuaishou/handler/KuaiShouRetryReportJob.java

@@ -178,6 +178,15 @@ public class KuaiShouRetryReportJob {
                             }
                         }
                     });
+                } else if ("drama_episode_report".equals(dataDimension)) {
+                    dramaExecutorService.submit(new Runnable() {
+                        @Override
+                        public void run() {
+                            if (!Check.isNull(accessToken)) {
+                                dramaService.queryEpisodeReport(accessToken, advertiserId, startDate, endDate, null, id, isSend);
+                            }
+                        }
+                    });
                 }
 
             }