package com.chinacreator.process.job;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.chinacreator.process.exception.BusinessException;
import com.chinacreator.process.dao.DictionaryDao;
import com.chinacreator.process.dao.NewYearVideoDao;
import com.chinacreator.process.util.JsonUtil;
import com.chinacreator.process.util.URLUtil;
import oracle.sql.CLOB;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import sun.misc.BASE64Decoder;

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.net.URL;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.*;

/**
 * @author zhengrong.yan
 * @date 2021/2/1 9:45
 */
public class NewYearVideoJob {
    private Logger log = Logger.getLogger("newyearvideo");

    @Autowired
    private DictionaryDao dictionaryDao;

    @Autowired
    private NewYearVideoDao newYearVideoDao;

    public void doProcess() throws Exception {
        log.info(Thread.currentThread().getName() + "定时任务开始");
        long beginTime = System.currentTimeMillis();
        List<HashMap> list = newYearVideoDao.getpushData();
        if (list != null && list.size() > 0) {
            CountDownLatch threadSignal = new CountDownLatch(list.size());
            ExecutorService executorService = new ThreadPoolExecutor(12, 16, 10L, TimeUnit.MINUTES, new LinkedBlockingQueue<Runnable>(), new ThreadPoolExecutor.CallerRunsPolicy());
            //去除重复数据
            //List<HashMap> dataList = paraseData(list);
            log.info("数据库有效需要处理的数：" + list.size());

            for (HashMap vipmap : list) {
                NewYearVideoService continueService = new NewYearVideoService(list.size(), threadSignal, vipmap, dictionaryDao, newYearVideoDao);
                executorService.execute(continueService);
            }
            executorService.shutdown();
            try {
                executorService.awaitTermination(5L, TimeUnit.MINUTES);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        log.info(Thread.currentThread().getName() + "定时任务完成，耗时：" + (System.currentTimeMillis() - beginTime) / 1000 + " 秒");
    }

    /**
     * 去除重复数据，防止赠送会员接口被并发限制
     *
     * @param dataList
     * @return
     */
    private List<HashMap> paraseData(List<HashMap> dataList) {
        //去重复后的数据集
        List<HashMap> reDataList = new ArrayList<HashMap>();
        HashMap<String, List> tmpMap = new HashMap<String, List>();
        for (HashMap dataMap : dataList) {
            if (tmpMap.containsKey(dataMap.get("USERID").toString())) {
                log.info("重复数据，" + dataMap.get("USERID"));
            } else {
                reDataList.add(dataMap);
                List tmpList = new ArrayList();
                tmpList.add(dataMap.get("ID"));
                tmpMap.put(dataMap.get("USERID").toString(), tmpList);
            }
        }
        return reDataList;
    }

    static class NewYearVideoService implements Runnable {

        private static Logger log = Logger.getLogger("newyearvideo");
        private int totalSize;
        private CountDownLatch threadSignal;
        private HashMap busimap;
        private DictionaryDao dictionaryDao;
        private NewYearVideoDao newYearVideoDao;

        public NewYearVideoService(int totalSize, CountDownLatch threadSignal, HashMap busimap, DictionaryDao dictionaryDao, NewYearVideoDao newYearVideoDao) {
            this.totalSize = totalSize;
            this.threadSignal = threadSignal;
            this.busimap = busimap;
            this.dictionaryDao = dictionaryDao;
            this.newYearVideoDao = newYearVideoDao;
        }

        /**
         * 业务处理
         *
         * @param
         */
        public void run() {
            long startime = System.currentTimeMillis();
            Map logMap = new HashMap();
            //logMap.put("data", busimap);
            String resultCode = "-1";
            String resultInfo = "";
            String id = String.valueOf(busimap.get("ID"));
            try {
                //办理结果编码，0成功，-1待处理，1处理中，其他为异常
                newYearVideoDao.updateProcessing(id);
                //上传图片到服务器
                CLOB clob = (CLOB) busimap.get("BASE64CODE");
                String[] base64 = newYearVideoDao.ClobToString(clob).split(",");
                for (String s : base64) {
                    BASE64Decoder decoder = new BASE64Decoder();
                    //base64解码
                    byte[] bytes = decoder.decodeBuffer(s);
                    FileOutputStream fout = new FileOutputStream("/kc/data/cdn/images/" + id + ".jpg");
                    //将字节写入文件
                    fout.write(bytes);
                    fout.close();
                }
                busimap.put("photosurl","http://res.tv.wo.cn/springfestival/images/"+id+".jpg");
                //提交工单给合作方
                String result = invoke(busimap);
                JSONObject jsonObject = JSON.parseObject(result);
                resultCode = jsonObject.getString("code");
                resultInfo = jsonObject.getString("msg");
            } catch (Exception e) {
                //回滚
                try {
                    newYearVideoDao.updateRowbackPhotos(String.valueOf(busimap.get("ID")));
                } catch (Exception e1) {
                    e1.printStackTrace();
                }
                e.printStackTrace();
                if (e instanceof BusinessException) {
                    resultInfo = ((BusinessException) e).getMessage();
                    resultCode = ((BusinessException) e).getCode();
                } else {
                    resultCode = "8000";
                    resultInfo = "系统错误，" + e.getMessage();
                }
            } finally {
                threadSignal.countDown();
                try {
                    if (resultInfo != null && resultInfo.length() > 250) {
                        resultInfo = resultInfo.substring(0, 250);
                    }
                    newYearVideoDao.upHasSubmit(id, resultCode, resultInfo, "http://res.tv.wo.cn/springfestival/images/" + id + ".jpg");
                } catch (Exception e) {
                    e.printStackTrace();
                    log.error("更新数据出现异常，" + id + ", resultCode:" + resultCode + ", resultInfo:" + resultInfo);
                }
                logMap.put("reusltCode", resultCode);
                logMap.put("resultInfo", resultInfo);
                log.info(JsonUtil.objectToJson(logMap));
            }
        }


        /**
         * 调合作方接口
         *
         * @param
         * @return
         * @throws Exception
         */
        private String invoke(Map params) throws Exception {
            String result = "";
            String url = dictionaryDao.getValue("NewYearVideoUrl");
            //新年视频换脸工单提交
            String jsonParams = "";
            String timestamp = System.currentTimeMillis() + "";
            String http_callback_url = dictionaryDao.getValue("NewYearVideoBackUrl");//从字典表里拿
            String wid =String.valueOf(params.get("ID")) ;
            //外网地址
            String img = String.valueOf(params.get("photosurl"));
            JSONObject json = new JSONObject();
            JSONArray jsonArray = new JSONArray();
            jsonArray.add(img);
            json.put("images", jsonArray);
            json.put("http_callback_url", http_callback_url);
            json.put("timestamp", timestamp);
            json.put("app_id", "b5czqjiujukzssmdw3lyjmdz4twhnfvs");
            json.put("secret_key", "MlOWTRj9ljqAfWPGbSy1x7dIiwKYKROp");
            json.put("wid", wid);
            System.out.println("modules===>"+params.get("VIDEOMODULES"));
            json.put("template_id", String.valueOf(params.get("VIDEOMODULES")));
            JSONArray jsonArray2 = new JSONArray();
            json.put("videos", jsonArray2);
            json.put("texts", jsonArray2);
            jsonParams = json.toJSONString();
            log.info("url: " + url);
            log.info(jsonParams);
            result = URLUtil.postJson(url, jsonParams);
            System.out.println("result=====>"+result);
            log.info("调合作方接口结果=> id: " + wid + " , result: " + result);
            return result;
        }


        /**
         * 解析数据
         *
         * @param body orderId TD_POINTS_ORDER_REC表ID字段，我方生成的订单流水号
         *             orderNo 积分商城订单号
         *             requestId 返回给客户的请求ID
         * @return
         */
        public Map transBean(Map<String, Object> body) {
            String jsonStr = JsonUtil.objectToJson(body);
            return (Map) JsonUtil.jsonToBean(jsonStr, Map.class);
        }


        /**
         * 获取请求属性性
         *
         * @return
         */
        private static Map getProperty() {
            Map reqProperty = new HashMap();
            reqProperty.put("Content-type", "application/json;charset=UTF-8");
            return reqProperty;
        }

    }
}
