package com.viettel.campaign.web.rest;

import com.viettel.campaign.model.ccms_full.TimeRangeDialMode;
import com.viettel.campaign.model.ccms_full.TimeZoneDialMode;
import com.viettel.campaign.service.CampaignExecuteService;
import com.viettel.campaign.service.CampaignService;
import com.viettel.campaign.web.dto.CampaignDTO;
import com.viettel.campaign.web.dto.ResultDTO;
import com.viettel.campaign.web.dto.request_dto.CampaignRequestDTO;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.sleuth.instrument.reactor.ReactorSleuth;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.util.List;
import java.util.Map;

@RestController
@RequestMapping("/ipcc/campaign")
@CrossOrigin
public class CampaignController {

    private static final Logger logger = LoggerFactory.getLogger(CampaignController.class);

    @Autowired
    CampaignService campaignService;

    @Autowired
    CampaignExecuteService campaignExecuteService;

    @PostMapping("/searchCampaignExecute")
    @ResponseBody
    public ResponseEntity<ResultDTO> searchCampaignExecute(@RequestBody CampaignRequestDTO requestDto) {
        ResultDTO result = campaignExecuteService.searchCampaignExecute(requestDto);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @PostMapping("/getExecuteCampaign")
    @ResponseBody
    public ResponseEntity<ResultDTO> getExecuteCampaign(@RequestBody CampaignRequestDTO requestDto) {
        ResultDTO result = campaignExecuteService.getExecuteCampaign(requestDto);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @PostMapping("/getCall")
    @ResponseBody
    public ResponseEntity<ResultDTO> getCall(@RequestBody CampaignRequestDTO requestDto) {
        ResultDTO result = campaignExecuteService.getCall(requestDto);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @RequestMapping(value = "/search", method = RequestMethod.POST)
    public ResponseEntity<ResultDTO> search(@RequestBody CampaignRequestDTO requestDto) {
        ResultDTO result = campaignService.search(requestDto);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @RequestMapping(value = "/find-by-campaign-code", method = RequestMethod.POST)
    public ResultDTO findByCampaignCode(@RequestBody CampaignRequestDTO dto) {
        return campaignService.findByCampaignCode(dto);
    }

    @RequestMapping(method = RequestMethod.POST)
    public ResultDTO addNewCampaign(@RequestBody CampaignDTO dto) {
        return campaignService.addNewCampaign(dto);
    }

    @GetMapping("/countRecallCustomer")
    @ResponseBody
    public ResponseEntity countRecallCustomer(@RequestParam("companySiteId") Long companySiteId, @RequestParam("agentId") Long agentId) {
        Map result = campaignService.countRecallCustomer(companySiteId, agentId);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @GetMapping("/findByCampaignId")
    @ResponseBody
    public ResponseEntity findByCampaignId(@RequestParam("campaignId") Long campaignId) {
        ResultDTO result = campaignService.findByCampaignId(campaignId);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @GetMapping("/findCampaignTimeRangeMode")
    @ResponseBody
    public ResponseEntity<?> findCampaignTimeRangeMode(@RequestParam("campaignId") Long campaignId, @RequestParam("companySiteId") Long companySiteId) {
        List<TimeRangeDialMode> list = campaignService.getCampaignTimeRangeMode(campaignId, companySiteId);
        return new ResponseEntity<>(list, HttpStatus.OK);
    }

    @GetMapping("/findCampaignTimeZoneMode")
    @ResponseBody
    public ResponseEntity<?> findCampaignTimeZoneMode(@RequestParam("campaignId") Long campaignId, @RequestParam("companySiteId") Long companySiteId) {
        List<TimeZoneDialMode> list = campaignService.getCampaignTimeZoneMode(campaignId, companySiteId);
        return new ResponseEntity<>(list, HttpStatus.OK);
    }

    @PostMapping("/searchInteractiveResult")
    @ResponseBody
    public ResponseEntity<ResultDTO> searchInteractiveResult(@RequestBody CampaignRequestDTO dto) throws Exception {
        ResultDTO result = campaignExecuteService.searchInteractiveResult(dto);
        return new ResponseEntity<>(result, HttpStatus.OK);
    }

    @PostMapping("/exportInteractiveResult")
    @ResponseBody
    public ResponseEntity<?> exportInteractiveResult(HttpServletResponse response, @RequestBody CampaignRequestDTO dto) {
        XSSFWorkbook workbook = null;
        byte[] contentReturn = null;
        try {
            String fileName = "report_campaign_exec_interactive_result.xlsx";
            response.setHeader("Content-Disposition", "attachment; filename=" + fileName);
            OutputStream outputStream;
            workbook = campaignExecuteService.exportInteractiveResult(dto);
            outputStream = response.getOutputStream();
            workbook.write(outputStream);
            ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
            workbook.write(byteArrayOutputStream);
            contentReturn = byteArrayOutputStream.toByteArray();
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            return new ResponseEntity<byte[]>(null, null, HttpStatus.BAD_REQUEST);
        } finally {
            if (workbook != null) {
                try {
                    workbook.close();
                } catch (IOException e) {
                    logger.error(e.getMessage(), e);
                }
            }
        }
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.parseMediaType("application/vnd.ms-excel"));
        return new ResponseEntity<byte[]>(contentReturn, headers, HttpStatus.OK);
    }

    @RequestMapping(value = "/changeCampaignStatus", method = RequestMethod.PUT)
    public ResultDTO changeCampaignStatus(@RequestBody CampaignDTO dto, HttpServletRequest request) {
        dto.setSessionId(request.getSession().getId());
        return campaignService.changeCampaignStatus(dto);
    }

    @RequestMapping(value = "/check-allow-status-to-prepare", method = RequestMethod.GET)
    public ResultDTO checkAllowStatusToPrepare(@RequestParam("campaignId") Long campaignId) {
        return campaignService.checkAllowStatusToPrepare(campaignId);
    }

    @RequestMapping(value = "/exportCampaigns", method = RequestMethod.POST)
    @ResponseBody
    public ResponseEntity<?> exportCampaigns(HttpServletResponse response, @RequestBody CampaignRequestDTO dto) {
        XSSFWorkbook workbook = null;
        byte[] contentReturn = null;
        try {
            String fileName = "report_campaigns.xlsx";
            response.setHeader("Content-Disposition", "attachment; filename=" + fileName);
            OutputStream outputStream;
            workbook = campaignService.exportCampaigns(dto);
            outputStream = response.getOutputStream();
            workbook.write(outputStream);
            ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
            workbook.write(byteArrayOutputStream);
            contentReturn = byteArrayOutputStream.toByteArray();
        } catch (Exception ex) {
            logger.error(ex.getMessage(), ex);
            return new ResponseEntity<byte[]>(null, null, HttpStatus.BAD_REQUEST);
        } finally {
            if (workbook != null) {
                try {
                    workbook.close();
                } catch (IOException e) {
                    logger.error(e.getMessage(), e);
                }
            }
        }
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.parseMediaType("application/vnd.ms-excel"));
        return new ResponseEntity<byte[]>(contentReturn, headers, HttpStatus.OK);
    }

    @PostMapping("/updateCampaign")
    @ResponseBody
    public ResponseEntity<?> updateCampaign(@RequestBody CampaignDTO dto) {
        ResultDTO resultDTO = campaignService.updateCampaign(dto);
        return new ResponseEntity<>(resultDTO, HttpStatus.OK);
    }
}
