package com.bonus.core.customer.utils;

import cn.hutool.core.io.IORuntimeException;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.bonus.common.core.exception.ServiceException;
import com.bonus.core.common.utils.SpringContextHolder;
import com.bonus.core.customer.dto.BitmainOtherInfoDTO;
import com.bonus.core.customer.metadata.model.FaceMetadataModel;
import com.bonus.core.customer.metadata.service.FaceMetadataService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.web.util.UriComponents;
import org.springframework.web.util.UriComponentsBuilder;

import javax.annotation.Resource;
import javax.validation.constraints.NotNull;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@Service
public class BitmainUtil {
   private static final Logger log = LoggerFactory.getLogger(BitmainUtil.class);
   private static final String FACE_API = "/SophonFace/api/faces";
   private static final String IDENTITIES_API = "/SophonFace/api/identities";
   private static final String GROUPS_API = "/SophonFace/api/groups";
   private static final String GROUPS_IDENTITIES_API = "/SophonFace/api/groups/<group_id>/identities";
   private static final String GET_IDENTITY_INFO_FACE_API = "/SophonFace/api/identities/<identity_id>";
   private static final HashMap<String, Integer> sortMap = new HashMap(3);
   @Resource
   private FaceMetadataService faceMetadataService;

   public static JSONObject registerFaceQuick(String imgBase64, BitmainOtherInfoDTO bitmainOtherInfoDTO, UriComponents uri) {
      RedisTemplate<Object, Object> redisTemplate = (RedisTemplate) SpringContextHolder.getBean("redisTemplate");
      String var10000 = uri.getHost();
      String groupIdKey = "yst:bitmain:" + var10000 + ":" + uri.getPort() + ":groupId";
      log.info("groupIdKey:{}", groupIdKey);
      String targetGroupId = (String)Optional.ofNullable(redisTemplate.opsForValue().get(groupIdKey)).orElseGet(() -> {
         String listGroupsRes = listGroups(uri);
         JSONArray groups = JSON.parseObject(listGroupsRes).getJSONArray("data");
         ArrayList<Object> groupsSorted = (ArrayList)groups.stream().sorted((o1, o2) -> {
            String o1Name = JSONObject.parseObject(JSON.toJSONString(o1)).getJSONObject("info").getString("groupname");
            Integer o1Id = (Integer)Optional.ofNullable((Integer)sortMap.get(o1Name)).orElse(sortMap.size() + 1);
            String o2Name = JSONObject.parseObject(JSON.toJSONString(o2)).getJSONObject("info").getString("groupname");
            Integer o2Id = (Integer)Optional.ofNullable((Integer)sortMap.get(o2Name)).orElse(sortMap.size() + 1);
            return Integer.compare(o1Id, o2Id);
         }).collect(Collectors.toCollection(ArrayList::new));
         Iterator var6 = groupsSorted.iterator();

         JSONObject jsonObject;
         String name;
         do {
            if (!var6.hasNext()) {
               return null;
            }

            Object o = var6.next();
            jsonObject = JSONObject.parseObject(JSONObject.toJSONString(o));
            name = jsonObject.getJSONObject("info").getString("groupname");
         } while(!"全部".equals(name) && !"default_group".equals(name));

         String groupId = jsonObject.getString("_id");
         redisTemplate.opsForValue().set(groupIdKey, groupId, 300L, TimeUnit.SECONDS);

         try {
            TimeUnit.MILLISECONDS.sleep(200L);
         } catch (Exception var12) {
            log.info(var12.toString());
            Thread.currentThread().interrupt();
         }

         return groupId;
      });
      if (targetGroupId != null) {
         JSONObject userInfo = new JSONObject();
         userInfo.put("psnid", bitmainOtherInfoDTO.getCustId());
         userInfo.put("xm", bitmainOtherInfoDTO.getCustName());
         userInfo.put("user_id", bitmainOtherInfoDTO.getCustId());
         userInfo.put("bh", bitmainOtherInfoDTO.getCustNum());

         try {
            TimeUnit.MILLISECONDS.sleep(200L);
         } catch (Exception var10) {
            log.info(var10.toString());
            Thread.currentThread().interrupt();
         }

         String res = createFaceQuick(imgBase64, bitmainOtherInfoDTO.getCustId().toString(), userInfo, targetGroupId, uri);

         try {
            TimeUnit.MILLISECONDS.sleep(100L);
         } catch (Exception var9) {
            log.info(var9.toString());
            Thread.currentThread().interrupt();
         }

         return JSONObject.parseObject(res);
      } else {
         throw new ServiceException("注册失败！未找到默认组ID！");
      }
   }

   private static String createIdentity(JSONObject infoFiled, UriComponents uri) {
      return createIdentityOrGroup(infoFiled, uri.expand(new Object[]{"/SophonFace/api/identities"}).toUriString());
   }

   private static String createFaceQuick(String imageBase64, String identityId, JSONObject identityInfo, String groupId, UriComponents uri) {
      JSONObject params = new JSONObject();
      params.put("image_base64_str", imageBase64);
      if (identityId != null) {
         params.put("identity_id", identityId);
      }

      if (!identityInfo.isEmpty()) {
         params.put("identity_info", identityInfo);
      }

      if (groupId != null) {
         params.put("group_id", groupId);
      }

      String url = uri.expand(new Object[]{"/SophonFace/api/faces"}).toUriString();
      log.info("比特请求地址：{}", url);
      if (imageBase64.length() > 100) {
         log.info("比特请求参数[image_base64_str]：{}", imageBase64.substring(0, 50));
      } else {
         log.info("比特请求参数[image_base64_str]：{}", imageBase64);
      }

      log.info("比特请求参数[identity_id]：{}", params.getString("identity_id"));
      log.info("比特请求参数[identity_info]：{}", params.getString("identity_info"));
      log.info("比特请求参数[group_id]：{}", params.getString("group_id"));
      return HttpUtil.post(url, params.toString(), 10000);
   }

   private static String createFace(UriComponents uri, @NotNull String imageBase64, String identityId, Double qualityScore) {
      JSONObject params = new JSONObject();
      params.put("image_base64_str", imageBase64);
      if (identityId != null) {
         params.put("identity_id", identityId);
      }

      if (qualityScore != null) {
         params.put("quality_score", qualityScore);
      }

      String url = uri.expand(new Object[]{"/SophonFace/api/faces"}).toUriString();
      return HttpUtil.post(url, params.toString(), 10000);
   }

   private static String createGroup(JSONObject infoFiled, UriComponents uri) {
      return createIdentityOrGroup(infoFiled, uri.expand(new Object[]{"/SophonFace/api/groups"}).toUriString());
   }

   private static String listGroups(UriComponents uri) {
      String url = uri.expand(new Object[]{"/SophonFace/api/groups"}).toUriString();
      return HttpUtil.get(url, 10000);
   }

   private static void delFace(UriComponents uri, String identityId) {
      try {
         log.info("开始删除旧face!" + identityId);
         String path = "/SophonFace/api/identities/<identity_id>".replace("<identity_id>", identityId);
         String url = uri.expand(new Object[]{path}).toUriString();
         JSONObject json = new JSONObject();
         json.put("iteratively_delete", true);
         String body = HttpRequest.delete(url).body(json.toJSONString()).execute().body();
         log.info("删除结果:{}", body);
      } catch (Exception var6) {
         log.error(var6.toString());
         if (var6 instanceof IORuntimeException) {
            throw new IORuntimeException("请求超时！");
         }
      }

   }

   private static String addIdentityToGroup(String groupId, String identityId, UriComponents uri) {
      JSONObject params = new JSONObject();
      params.put("identity_id", identityId);
      String path = "/SophonFace/api/groups/<group_id>/identities".replace("<group_id>", groupId);
      String url = uri.expand(new Object[]{path}).toUriString();
      return HttpUtil.post(url, params.toString(), 10000);
   }

   private static String createIdentityOrGroup(JSONObject infoFiled, String url) {
      JSONObject params = new JSONObject();
      params.put("info", infoFiled);
      return HttpUtil.post(url, params.toString(), 10000);
   }

   List<UriComponents> getUriComponents(List<String> addresses) {
      List<UriComponents> urlPrefix = new ArrayList(addresses.size());
      Iterator var3 = addresses.iterator();

      while(var3.hasNext()) {
         String address = (String)var3.next();
         String[] elements = address.split(":");
         UriComponents prefix = UriComponentsBuilder.newInstance().scheme("http").host(elements[0]).port(elements[1]).path("{template}").build();
         urlPrefix.add(prefix);
      }

      return urlPrefix;
   }

   public void deleteIdentityFace(String identityId) {
      FaceMetadataModel faceMetadataModel = this.faceMetadataService.queryMetadata();
      if (!ObjectUtil.isEmpty(faceMetadataModel) && !"2".equals(faceMetadataModel.getIfUseBitFaceBoxUrl())) {
         List<String> serverUrls = (List)Optional.ofNullable(faceMetadataModel.getBitFaceBoxUrl()).map((settingValue) -> {
            return JSON.parseArray(settingValue, String.class);
         }).orElse(new ArrayList());
         Iterator var4 = serverUrls.iterator();

         while(var4.hasNext()) {
            String serverUrl = (String)var4.next();
            String[] elements = serverUrl.split(":");
            if (!ArrayUtil.isEmpty(elements) && elements.length != 1) {
               UriComponents uriComponent = UriComponentsBuilder.newInstance().scheme("http").host(elements[0]).port(elements[1]).path("{template}").build();
               delFace(uriComponent, identityId);
            }
         }

      }
   }

   static {
      sortMap.put("请求", 1);
      sortMap.put("全部", 2);
   }
}
