package com.fs.app.controller;

import cn.hutool.json.JSONUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.fs.app.annotation.Login;
import com.fs.app.utils.JwtUtils;
import com.fs.call.config.CallApiConfig;
import com.fs.call.domain.CallNotifyResponse;
import com.fs.call.domain.CallResult;
import com.fs.call.service.ICallService;
import com.fs.common.annotation.RepeatSubmit;
import com.fs.common.core.controller.BaseController;
import com.fs.common.core.domain.R;
import com.fs.common.utils.ServletUtils;
import com.fs.common.utils.StringUtils;
import com.fs.company.domain.*;
import com.fs.company.service.*;
import com.fs.crm.domain.CrmCustomer;
import com.fs.crm.domain.CrmCustomerContacts;
import com.fs.crm.service.ICrmCustomerContactsService;
import com.fs.crm.service.ICrmCustomerService;
import com.fs.system.oss.CloudStorageService;
import com.fs.system.oss.OSSFactory;
import com.fs.voice.service.IVoiceService;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import io.jsonwebtoken.Claims;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.scheduling.annotation.Async;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import javax.net.ssl.*;
import javax.servlet.http.HttpServletRequest;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.security.SecureRandom;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;

import static com.fs.common.constant.Constants.PAGE_SIZE;

@Api("呼叫接口")
@RestController
@RequestMapping("/app/voiceApi")
public class VoiceApiController extends AppBaseController {
    private Logger logger = LoggerFactory.getLogger(VoiceApiController.class);
    @Autowired
    private IVoiceService voiceService;
    @Autowired
    private ICompanyVoiceMobileService mobileService;
    @Autowired
    private ICompanyUserService companyUserService;

    @Autowired
    private ICompanyVoiceLogsService companyVoiceLogsService;

    @Autowired
    private ICompanyVoiceApiService companyVoiceApiService;
    @Autowired
    private ICompanyVoiceService companyVoiceService;
    @Autowired
    private ICompanyVoiceMobileService companyVoiceMobileService;

    @Autowired
    private ICompanyVoiceCallerService callerService;

    @Autowired
    private ICompanyService companyService;

    @Autowired
    private ICompanyUserService userService;

    @Autowired
    private ICrmCustomerService crmService;

    @Autowired
    private ICrmCustomerContactsService crmContactsService;

    @Autowired
    private ICompanyVoiceBlacklistService blacklistService;

    @Autowired
    ICompanyVoiceLogsService logsService;

    @Autowired
    JwtUtils jwtUtils;
    @Login
    @ApiOperation("呼叫")
    @GetMapping("/callMobile")
    @RepeatSubmit
    public R callMobile(HttpServletRequest request,
                        @ApiParam(required = false, name = "mobile", value = "被叫号") @RequestParam(value = "mobile", required = false) String mobile,
                        @ApiParam(required = false, name = "customerId", value = "客户ID") @RequestParam(value = "customerId", required = false) Long customerId,
                        @ApiParam(required = false, name = "callerId", value = "线路接口id") @RequestParam(value = "callerId", required = false) Long callerId
    ) throws Exception
    {
        String headValue = request.getHeader("APPToken");
        Claims claims = jwtUtils.getClaimByToken(headValue);
        Long userId =Long.parseLong( claims.getSubject().toString());
        CompanyUser user=companyUserService.selectCompanyUserById(userId);
        return voiceService.voiceAppCall(user.getCompanyId(),customerId,user.getUserId(), mobile,callerId);
    }

    @ApiOperation("外呼挂断")
    @GetMapping("callOffMobile")
    public R callOffMobile(@RequestParam("voiceId") Long voiceId) throws Exception
    {
        return voiceService.voiceAppCallOff(voiceId);
    }


    @Login
    @ApiOperation("获取我的呼叫记录")
    @GetMapping("/getMyCallList")
    public R getMyCallList(
            HttpServletRequest request,
            @ApiParam(required = true, name = "page", value = "页号") @RequestParam(value = "page", required = true) Integer page,
            @ApiParam(required = false, name = "customerId", value = "客户ID") @RequestParam(value = "customerId", required = false) Long customerId
    ){
        PageHelper.startPage(page, PAGE_SIZE);
        String headValue = request.getHeader("APPToken");
        Claims claims=jwtUtils.getClaimByToken(headValue);
        String userId = claims.getSubject().toString();
        CompanyVoiceLogs logs=new CompanyVoiceLogs();
        logs.setCompanyUserId(Long.parseLong(userId));
        logs.setCustomerId(customerId);
        List<CompanyVoiceLogs> list=companyVoiceLogsService.selectCompanyVoiceLogsList(logs);
        PageInfo<CompanyVoiceLogs> listPageInfo=new PageInfo<>(list);
        return R.ok().put("data",listPageInfo);
    }

    //抖音 https://api.yjf.runtzh.com/app/common/douyinNotify

    @ApiOperation("外呼回调")
    @PostMapping(value="/callNotify",consumes = MediaType.APPLICATION_JSON_VALUE, produces = {"application/json; charset=UTF-8"})
    @Transactional
    public CallResult callNotify(@RequestBody String json) throws Exception {
        logger.info(json);
        CallNotifyResponse notifyResponse= JSONUtil.toBean(json, CallNotifyResponse.class);
        CompanyVoiceLogs logs = companyVoiceLogsService.selectCompanyVoiceLogsBySessionId(notifyResponse.getNotify().getUserData());
        if (logs != null) {
            if(StringUtils.isNotEmpty(notifyResponse.getNotify().getRecordFile())) {
                CompanyVoiceApi api = companyVoiceApiService.selectCompanyVoiceApiById(logs.getApiId());
                CallApiConfig apiConfig = JSONUtil.toBean(api.getApiJson(), CallApiConfig.class);
                if (StringUtils.isNotEmpty(notifyResponse.getNotify().getRecordFile())) {
                    String url=apiConfig.getUrl().replace("/openapi/V2.0.6","");
                    logs.setVoiceUrl(url + notifyResponse.getNotify().getRecordFile());
                }
                Long remain = notifyResponse.getNotify().getTimeLength() % 60;
                Long times = notifyResponse.getNotify().getTimeLength() / 60;
                if (remain > 0) {
                    times++;
                }
                logs.setStatus(1);
                logs.setTimes(notifyResponse.getNotify().getTimeLength());
                logs.setBillingTime(times);
                SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");//设置日期格式
                logs.setStartTime(df.parse(notifyResponse.getNotify().getAnswerTime()));
                logs.setFinishTime(df.parse(notifyResponse.getNotify().getByeTime()));
                companyVoiceLogsService.updateCompanyVoiceLogs(logs);
                companyVoiceService.updateCompanyVoiceRemainTimes(logs.getCompanyId(), -times);
            }
            else{
                logs.setStatus(-1);
                companyVoiceLogsService.updateCompanyVoiceLogs(logs);
            }
        }else{
            JSONObject callObj=JSON.parseObject(json);
            JSONObject notifyObj=callObj.getJSONObject("notify");
            String type=notifyObj.getString("type");
            String session=notifyObj.getString("session");
            String callee=notifyObj.getString("agent");//被叫/坐席号
            String caller=notifyObj.getString("number");//主叫
            if(type.contentEquals("callin")){   //回拨接听
                CompanyVoiceCaller callerEE=callerService.selectCompanyVoiceCallerByCallerNo(callee);
                CrmCustomer customer=crmService.selectFscrmByMobile(caller);
                Long customerId=0L;
                if(customer!=null){
                    customerId=customer.getCustomerId();
                }
                else{
                    CrmCustomerContacts contactsMap=new CrmCustomerContacts();
                    contactsMap.setMobile(caller);
                    List<CrmCustomerContacts>  contactsList=crmContactsService.selectCrmCustomerContactsList(contactsMap);
                    if(contactsList.size()>0){
                        CrmCustomerContacts contacts=contactsList.get(0);
                        customerId=contacts.getCustomerId();
                    }
                }
                callInAction(callerEE.getCompanyId(),customerId,callerEE.getCompanyUserId(),session,caller,callerEE);
            }
        }
        CallResult result=new CallResult();
        result.setMsg("");
        result.setError("");
        return result;
    }

    private  R callInAction(Long companyId, Long customerId, Long userId,String session,String caller,CompanyVoiceCaller callerEE){
        //查询主叫号是不是坐席 查询主叫号是否已过期
        Company company=companyService.selectCompanyById(companyId);
        if(company.getStatus()==0){
            return R.error("公司已停用");
        }
        if(company.getVoiceApiId()==null){
            return R.error("未配置外呼接口");
        }
        CompanyVoiceApi api=companyVoiceApiService.selectCompanyVoiceApiById(company.getVoiceApiId());
        if(api==null){
            return R.error("外呼接口不存在");
        }
        if(api.getStatus().equals(0)){
            return R.error("外呼接口已禁用");
        }
        CompanyUser user=userService.selectCompanyUserById(userId);
        //CompanyVoiceCaller voiceCaller=callerService.selectCompanyVoiceCallerByUserId(companyId,userId);
        CompanyVoice companyVoice=companyVoiceService.selectCompanyVoiceByCompanyId(user.getCompanyId());
        if(callerEE==null){
            return R.error("未绑定坐席");
        }
        if(companyVoice.getTimes()<=0){
            return R.error("剩余时长不足,请购买套餐");
        }

//      CompanyVoiceMobile voiceMobile=mobileService.selectEmptyCompanyVoiceMobile(companyId,api.getApiId());
//      if(voiceMobile==null){
//           return R.error("没有空闲号码");
//      }

        //黑名单处理
        if(blacklistService.selectCompanyVoiceBlacklistByMobile(caller)>0){
            return R.error("主叫号码已被设置为黑名单");
        }
        //写入SESSION
        CompanyVoiceLogs logs=new CompanyVoiceLogs();
        logs.setCompanyId(companyId);
        logs.setVoiceTitle(caller+"回拨："+user.getNickName());
        logs.setStartTime(new Date());
        logs.setVoiceType(1);
        logs.setCalleePhone(callerEE.getMobile());
        logs.setCallerPhone(caller);
        logs.setDisplayCalleeNumber(callerEE.getMobile());
        logs.setDisplayCallerNumber(caller);
        logs.setRemark(caller +"回拨呼叫"+user.getNickName());
        logs.setCompanyUserId(userId);
        logs.setCustomerId(customerId);
        logs.setApiId(api.getApiId());
        logs.setSessionId(session);
        logs.setCallerNo(caller);
        logsService.insertCompanyVoiceLogs(logs);
//        voiceMobile.setStatus(0);
//        mobileService.updateCompanyVoiceMobile(voiceMobile);
        return R.ok();

    }

    @Login
    @ApiOperation("获取SIP")
    @GetMapping(value="/getSipAccount")
    public R getSipAccount(@RequestParam(value = "callerId",required = false) Long callerId) throws Exception
    {

        String userId=getUserId();
        return voiceService.getSipAccount(Long.parseLong(userId),callerId);
    }







}
