package com.example.demo.service.impl;

import java.time.LocalDateTime;
import java.time.ZoneId;
import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.UUID;
import java.util.stream.Collectors;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.example.demo.common.APIResponse;
import com.example.demo.dto.DealCreateDTO;
import com.example.demo.dto.DealDeleteDTO;
import com.example.demo.dto.DealResponseDTO;
import com.example.demo.dto.DealUpdateDTO;
import com.example.demo.entity.Configurations;
import com.example.demo.entity.Deal;
import com.example.demo.redisentity.DealRedis;
import com.example.demo.repository.ConfigurationRepo;
import com.example.demo.repository.DealRepository;
import com.example.demo.service.DealService;

import redis.clients.jedis.Jedis;

@Service
public class DealServiceImpl implements DealService {

	@Autowired
	private DealRepository repo;

	@Autowired
	private ConfigurationRepo configRepo;

	@Autowired
	private Jedis jedis;

	@Override
	public APIResponse createdeal(DealCreateDTO create) {
		APIResponse api = new APIResponse();
		Deal deal = new Deal();
		deal.setBidfloor(create.getBidfloor());
		deal.setName(create.getName());
		deal.setIncluding_seats(create.getIncluding_seats());
		deal.setKeywords(create.getKeywords());
		deal.setCreated_at(LocalDateTime.now());
		deal.setUpdated_at(LocalDateTime.now());
		deal.setCreated_by(create.getCreated_by());
		repo.save(deal);

		DealRedis dealredis = new DealRedis();

		dealredis.setDeal_id(deal.getDeal_id());
		UUID id = dealredis.getDeal_id();
		String id_str = id.toString();

		dealredis.setName(deal.getName());
		String name_str = dealredis.getName();

		String bid_floor_str = null;
		if (deal.getBidfloor() != null) {
			dealredis.setBid_floor(deal.getBidfloor());
			bid_floor_str = dealredis.getBid_floor();
		}
		String including_seats_str = null;
		if (deal.getIncluding_seats() != null) {
			dealredis.setIncluding_seats(deal.getIncluding_seats());
			including_seats_str = dealredis.getIncluding_seats();
		}

		String keywords_str = null;
		if (deal.getKeywords() != null) {
			dealredis.setKeyword(deal.getKeywords());
			keywords_str = dealredis.getKeyword();
		}

		dealredis.setCreated_at(deal.getCreated_at());
		LocalDateTime now = deal.getCreated_at();

		String[] arr = new String[2];

		arr[0] = now.toString();

		arr[1] = now.format(DateTimeFormatter.ofPattern("hh:mm:ss a", Locale.ENGLISH));
		String created_at_str = Arrays.toString(arr);

		dealredis.setCreated_by(deal.getCreated_by());
		UUID created_by = dealredis.getCreated_by();
		String created_by_str = created_by.toString();

		dealredis.setUpdated_at(deal.getUpdated_at());
		LocalDateTime now1 = deal.getUpdated_at();

		String[] arr1 = new String[2];

		arr1[0] = now1.toString();

		arr1[1] = now1.format(DateTimeFormatter.ofPattern("hh:mm:ss a", Locale.ENGLISH));
		String updated_at_str = Arrays.toString(arr1);

		String Key = "Deal_" + deal.getDeal_id();
		Map<String, String> map = new HashMap<>();
		map.put("deal_id", id_str);
		map.put("name", name_str);
		if (bid_floor_str != null) {
			map.put("bid_floor", bid_floor_str);
		}
		if (including_seats_str != null) {
			map.put("including_seats", including_seats_str);
		}
		if (keywords_str != null) {
			map.put("keywords", keywords_str);
		}
		map.put("created_at", created_at_str);
		map.put("created_by", created_by_str);
		map.put("updated_at", updated_at_str);
		jedis.hmset(Key, map);

		api.setData(deal);
		api.setMessage("Deal Created Successfully");
		api.setMsgCode("DEAL CREATED SUCCESSFULLY");
		return api;
	}

	@Override
	public APIResponse updatedeal(DealUpdateDTO update, UUID deal_id) {
		APIResponse api = new APIResponse();
		Deal deal = repo.findById(deal_id).orElse(null);
		if (deal == null) {
			api.setMessage("Deal Id Not Found");
			api.setMsgCode("DEAL ID NOT FOUND");
			return api;
		} else {
			deal.setBidfloor(update.getBidfloor());
			deal.setName(update.getName());
			deal.setIncluding_seats(update.getIncluding_seats());
			deal.setKeywords(update.getKeywords());
			deal.setUpdated_at(LocalDateTime.now());
			deal.setUpdated_by(update.getUpdated_by());
			repo.save(deal);

			DealRedis dealredis = new DealRedis();

			dealredis.setDeal_id(deal.getDeal_id());
			UUID id = dealredis.getDeal_id();
			String id_str = id.toString();

			dealredis.setName(deal.getName());
			String name_str = dealredis.getName();

			String bid_floor_str = null;
			if (deal.getBidfloor() != null) {
				dealredis.setBid_floor(deal.getBidfloor());
				bid_floor_str = dealredis.getBid_floor();
			}
			String including_seats_str = null;
			if (deal.getIncluding_seats() != null) {
				dealredis.setIncluding_seats(deal.getIncluding_seats());
				including_seats_str = dealredis.getIncluding_seats();
			}

			String keywords_str = null;
			if (deal.getKeywords() != null) {
				dealredis.setKeyword(deal.getKeywords());
				keywords_str = dealredis.getKeyword();
			}

			dealredis.setCreated_at(deal.getCreated_at());
			LocalDateTime now = deal.getCreated_at();

			String[] arr = new String[2];

			arr[0] = now.toString();

			arr[1] = now.format(DateTimeFormatter.ofPattern("hh:mm:ss a", Locale.ENGLISH));
			String created_at_str = Arrays.toString(arr);

			dealredis.setCreated_by(deal.getCreated_by());
			UUID created_by = dealredis.getCreated_by();
			String created_by_str = created_by.toString();

			dealredis.setUpdated_at(deal.getUpdated_at());
			LocalDateTime now1 = deal.getUpdated_at();

			String[] arr1 = new String[2];

			arr1[0] = now1.toString();

			arr1[1] = now1.format(DateTimeFormatter.ofPattern("hh:mm:ss a", Locale.ENGLISH));
			String updated_at_str = Arrays.toString(arr1);

			dealredis.setUpdated_by(deal.getUpdated_by());
			UUID updated_by = dealredis.getUpdated_by();
			String updated_by_str = updated_by.toString();

			String Key = "Deal_" + deal.getDeal_id();
			Map<String, String> map = new HashMap<>();
			map.put("deal_id", id_str);
			map.put("name", name_str);
			if (bid_floor_str != null) {
				map.put("bid_floor", bid_floor_str);
			}
			if (including_seats_str != null) {
				map.put("including_seats", including_seats_str);
			}
			if (keywords_str != null) {
				map.put("keywords", keywords_str);
			}
			map.put("created_at", created_at_str);
			map.put("created_by", created_by_str);
			map.put("updated_at", updated_at_str);
			map.put("updated_by", updated_by_str);
			jedis.hmset(Key, map);

			api.setData(deal);
			api.setMessage("Deal Update Successfully");
			api.setMsgCode("DEAL UPDATE SUCCESSFULLY");
			return api;
		}

	}

	@Override
	public APIResponse getbyId(UUID deal_id) {
		APIResponse api = new APIResponse();
		Deal deal = repo.findById(deal_id).orElse(null);
		if (deal == null) {
			api.setMessage("Deal Id Not Found");
			api.setMsgCode("DEAL ID NOT FOUND");
			return api;
		} else {
			DealResponseDTO response = MapToDTO(deal);
			api.setData(response);
			api.setMessage("Deal Details Get Successfully");
			api.setMsgCode("DEAL DETAILS GET SUCCESSFULLY");
			return api;
		}
	}

	@Override
	public APIResponse getall() {
		APIResponse api = new APIResponse();
		List<Deal> deal = repo.findAll();
		List<DealResponseDTO> response = deal.stream().map(use -> MapToDTO(use)).collect(Collectors.toList());
		api.setData(response);
		api.setMessage("Deal List Get Successfully");
		api.setMsgCode("DEAL LIST GET SUCCESSFULLY");
		return api;
	}

	@Override
	public APIResponse deletedeal(DealDeleteDTO delete) {
		APIResponse api = new APIResponse();

		Deal deal = repo.findById(delete.getDeal_id()).orElse(null);
		deal.setIs_deleted(1);
		deal.setDeleted_at(LocalDateTime.now());
		deal.setDeleted_by(delete.getDeleted_by());
		repo.save(deal);

		DealRedis dealredis = new DealRedis();

		dealredis.setIs_deleted(deal.getIs_deleted());
		int is_deleted = dealredis.getIs_deleted();
		String is_deleted_str = Integer.toString(is_deleted);

		dealredis.setDeleted_at(deal.getDeleted_at());
		LocalDateTime now = dealredis.getDeleted_at();

		String[] arr = new String[2];

		arr[0] = now.toString();

		arr[1] = now.format(DateTimeFormatter.ofPattern("hh:mm:ss a", Locale.ENGLISH));
		String deleted_at_str = Arrays.toString(arr);

		dealredis.setDeleted_by(deal.getDeleted_by());
		UUID deleted_by = dealredis.getDeleted_by();
		String deleted_by_str = deleted_by.toString();

		String Key = "Deal_" + deal.getDeal_id();
		Map<String, String> map = new HashMap<>();
		map.put("is_deleted", is_deleted_str);
		map.put("deleted_at", deleted_at_str);
		map.put("deleted_by", deleted_by_str);
		jedis.hmset(Key, map);

		api.setData(deal);
		api.setMessage("Deal Delete Successfully");
		api.setMsgCode("DEAL DELETE SUCCESSFULLY");
		return api;
	}

	private DealResponseDTO MapToDTO(Deal deal) {
		DealResponseDTO response = new DealResponseDTO();
		response.setDeal_id(deal.getDeal_id());
		response.setDeal_name(deal.getName());
		response.setIncluding_seats(deal.getIncluding_seats());
		response.setKeywords(deal.getKeywords());
		response.setBidfloor(deal.getBidfloor());
		response.setCreated_by(deal.getCreated_by());
		response.setUpdated_by(deal.getUpdated_by());
		response.setDeleted_by(deal.getDeleted_by());
		response.setIs_deleted(deal.getIs_deleted());

		List<Configurations> allObj = configRepo.findAll();
		Configurations config = allObj.get(0);
		DateTimeFormatter newYorkDateFormatter = DateTimeFormatter.ofPattern(config.getConfigValue());
		String arr = newYorkDateFormatter.format(ZonedDateTime.of(deal.getCreated_at(), ZoneId.of("UTC-4")));
		response.setCreated_at(arr);

		if (deal.getUpdated_at() != null) {
			String arr1 = newYorkDateFormatter.format(ZonedDateTime.of(deal.getUpdated_at(), ZoneId.of("UTC-4")));
			response.setUpdated_at(arr1);
		}

		if (deal.getDeleted_at() != null) {
			String arr2 = newYorkDateFormatter.format(ZonedDateTime.of(deal.getDeleted_at(), ZoneId.of("UTC-4")));
			response.setDeleted_at(arr2);
		}

		return response;
	}

}
