package com.tzld.piaoquan.recommend.server.service;

import com.google.common.collect.Lists;
import com.google.common.reflect.TypeToken;
import com.tzld.piaoquan.recommend.server.util.CommonCollectionUtils;
import com.tzld.piaoquan.recommend.server.util.HttpClientFactory;
import com.tzld.piaoquan.recommend.server.util.JSONUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.http.HttpEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import java.util.*;

/**
 * @author dyp
 */
@Service
@Slf4j
public class ViewedService {
    private final Map<Integer, List<Integer>> viewedTypesMap = new HashMap<>();
    private final List<Integer> defaultViewedTypes = Lists.newArrayList(1, 6, 7, 5, 9);

    @Value("${video.filter.url:}")
    private String videoFilterUrl;
    @Value("${securityAbExpCode:}")
    private String securityAbExpCode;

    private final CloseableHttpClient client = HttpClientFactory.create(1000, 1000, 200, 200, 0, 1000);


    @PostConstruct
    public void init() {
//        1-已观看 2-视频状态 3-是否进入老年人社区 4-话题状态 5-推荐状态 6-白名单过滤 7-涉政视频过滤
        viewedTypesMap.put(0, Lists.newArrayList(1, 6, 5, 9));
        viewedTypesMap.put(4, Lists.newArrayList(1, 6, 5, 9));
        viewedTypesMap.put(13, Lists.newArrayList(1, 5, 9));
    }


    // TODO 如果过滤失败，那么认为所有视频都被过滤掉
    public List<Long> filterViewedVideo(int appType, String mid, String uid, List<Long> videoIds, String cityCode,
                                        Set<String> abExpCodes, Long hotSceneType, String clientIp) {

        List<Integer> viewedTypes = new ArrayList<>(viewedTypesMap.getOrDefault(appType, defaultViewedTypes));
        if (CommonCollectionUtils.contains(abExpCodes, securityAbExpCode)) {
            viewedTypes.add(8);
        }
        CloseableHttpResponse chr = null;
        try {
            HttpPost post = new HttpPost(videoFilterUrl);
            post.addHeader("Connection", "close");
            post.addHeader("content-type", "application/json");
            Map<String, Object> param = new HashMap<>();
            param.put("appType", appType);
            param.put("mid", mid);
            param.put("uid", uid);
            param.put("types", viewedTypes);
            param.put("videoIds", videoIds);
            param.put("cityCode", cityCode);
            param.put("hotSenceType", hotSceneType);
            param.put("clientIp", clientIp);
            param.put("abExpCodes", abExpCodes);
            List<Integer> recommendStatus = new ArrayList<>();
            recommendStatus.add(-6);
            param.put("recommendStatus", recommendStatus);
            post.setEntity(new StringEntity(JSONUtils.toJson(param)));

            chr = client.execute(post);
            if (chr == null
                    || chr.getStatusLine() == null
                    || chr.getStatusLine().getStatusCode() != 200) {
                log.error("filterViewedVideo failed http status exception!");
                return Collections.emptyList();
            }
            HttpEntity entity = chr.getEntity();
            if (entity == null) {
                return Collections.emptyList();
            }
            String content = EntityUtils.toString(entity);
            Map<String, String> data = JSONUtils.fromJson(content,
                    new TypeToken<Map<String, String>>() {
                    },
                    Collections.emptyMap());
            if (data.get("code") == null
                    || !data.get("code").equals("0")) {
                log.error("filterViewedVideo failed videoFilterUrl return code exception! data={}",
                        JSONUtils.toJson(data));
                return Collections.emptyList();
            }
            return JSONUtils.fromJson(data.get("data"),
                    new TypeToken<List<Long>>() {
                    }, Collections.emptyList());

        } catch (Exception e) {
            log.error("invoke http filterViewedVideo error", e);
        } finally {
            try {
                if (chr != null) {
                    chr.close();
                }
            } catch (Exception ex) {
                log.error("close CloseableHttpResponse error", ex);
            }
        }
        return Collections.emptyList();
    }

}
