package com.liquidnet.service.platform.service.ticketSystem.impl;

import com.alibaba.fastjson.JSON;
import com.fasterxml.jackson.core.type.TypeReference;
import com.liquidnet.commons.lang.util.CollectionUtil;
import com.liquidnet.commons.lang.util.DateUtil;
import com.liquidnet.commons.lang.util.HttpUtil;
import com.liquidnet.commons.lang.util.JsonUtils;
import com.liquidnet.service.platform.service.ticketSystem.ITicketSystemService;
import com.liquidnet.service.platform.vo.ticketSystem.*;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.MultiValueMap;

import java.time.LocalDateTime;
import java.util.List;

/**
 * <p>
 * 票务对接平台 服务实现类
 * </p>
 *
 * @author liquidnet
 * @since 2021-05-11
 */
@Service
public class ITicketSystemServiceImpl implements ITicketSystemService {
    @Value("${liquidnet.service.other.ticketSystemUrl}")
    private String ticketSystemUrl;
    @Value("${liquidnet.service.other.appId}")
    private String appId;
    @Value("${liquidnet.service.other.secret}")
    private String secret;

    @Override
    public STAccessTokenVo getAccessToken() {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("appId", appId);
        params.add("secret", secret);
        ResponseDataVo<STAccessTokenVo> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/getAccessToken", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<STAccessTokenVo>>() {
                        });
        return response.getData();
    }

    @Override
    public List<STPTListVo> getPerformanceTypeList(String accessToken) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        ResponseListVo<List<STPTListVo>> response =
                JsonUtils.fromJson(HttpUtil.get(ticketSystemUrl + "/standard/performance/type/list?accessToken=" + accessToken, null, headers),
                        new TypeReference<ResponseListVo<List<STPTListVo>>>() {
                        });
        return response.getData().getDataList();
    }

    @Override
    public List<STFieldListVo> getFieldList(String accessToken, String provinceId, String cityId, String districtId, Integer pageNo, Integer pageSize, String venueName) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("provinceId", provinceId);
        params.add("cityId", cityId);
        params.add("districtId", districtId);
        params.add("pageNo", pageNo.toString());
        params.add("pageSize", pageSize.toString());
        params.add("venueName", venueName);
        ResponseDataVo<List<STFieldListVo>> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/standard/venue/list", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<List<STFieldListVo>>>() {
                        });
        return response.getData();
    }

    @Override
    public STFieldChangeVo insertField(String accessToken, String venueCode, Integer provinceId, Integer cityId, Integer districtId, String venueName, String venueAddress,
                                       String managementCompany, Integer hasHall, String hallName, Integer hasSeat, Integer seatNum, Integer seatingCapacity) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("venueCode", venueCode);
        params.add("provinceId", provinceId.toString());
        params.add("cityId", cityId.toString());
        params.add("districtId", districtId.toString());
        params.add("venueName", venueName);
        params.add("venueAddress", venueAddress);
        params.add("managementCompany", managementCompany);
        params.add("hasHall", hasHall.toString());
        params.add("hallName", hallName);
        params.add("hasSeat", hasSeat.toString());
        params.add("seatNum", seatNum.toString());
        params.add("seatingCapacity", seatingCapacity.toString());
        ResponseDataVo<STFieldChangeVo> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/standard/venue/save", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<STFieldChangeVo>>() {
                        });
        return response.getData();
    }

    @Override
    public String insertPerformance(String accessToken, String performanceId, String performanceName, String approval, Integer typeId, String posterUrl,
                                    String performanceDesc, String sponsor, String performer, List<TimesVo> sessionList) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("performanceId", performanceId);
        params.add("performanceName", performanceName);
        params.add("approval", approval);
        params.add("typeId", typeId.toString());
        params.add("posterUrl", posterUrl);
        params.add("performanceDesc", performanceDesc);
        params.add("sponsor", sponsor);
        params.add("performer", performer);
        params.add("sessionList", JSON.toJSONString(sessionList));
        String response = HttpUtil.postRaw(ticketSystemUrl + "/performance/code", JSON.toJSONString(params), headers);
        return response;
    }

    @Override
    public boolean updatePerformance(String accessToken, String performanceId, String performanceName, String performanceDesc, Integer typeId, String posterUrl, String sponsor, String performer, String approval) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("performanceId", performanceId);
        params.add("performanceName", performanceName);
        params.add("approval", approval);
        params.add("typeId", typeId.toString());
        params.add("posterUrl", posterUrl);
        params.add("performanceDesc", performanceDesc);
        params.add("sponsor", sponsor);
        params.add("performer", performer);
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/performance/update", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean updateTimes(String accessToken, String sessionId, String sessionCode, String sessionName, LocalDateTime sessionStartTime,
                               LocalDateTime sessionEndTime, String hallCode, Integer hasSeat, String performanceId, Integer sessionStatus,
                               Integer tag, String seatingChart) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("sessionId", sessionId);
        params.add("sessionCode", sessionCode);
        params.add("sessionName", sessionName);
        params.add("sessionStartTime", DateUtil.Formatter.yyyyMMddHHmmss.format(sessionStartTime));
        params.add("sessionEndTime", DateUtil.Formatter.yyyyMMddHHmmss.format(sessionEndTime));
        params.add("hallCode", hallCode);
        params.add("hasSeat", hasSeat.toString());
        params.add("performanceId", performanceId);
        params.add("sessionStatus", sessionStatus.toString());
        params.add("tag", tag.toString());
        params.add("seatingChart", seatingChart);
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/session/update", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean insertTicketPrice(String accessToken, String sessionCode, List<TicketPriceVo> priceList) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("sessionId", sessionCode);
        params.add("priceList", JSON.toJSONString(priceList));
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/inventory", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean delTicketPrice(String accessToken, String performanceId, String sessionCode, String priceId) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("performanceId", performanceId);
        params.add("sessionCode", sessionCode);
        params.add("priceId", priceId);
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/inventory", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean insertTicket(String accessToken, String performanceId, String sessionId, String sessionCode, String priceId, List<TicketVo> ticketList) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("performanceId", performanceId);
        params.add("sessionId", sessionId);
        params.add("sessionCode", sessionCode);
        params.add("priceId", priceId);
        params.add("ticketList", JSON.toJSONString(ticketList));
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/ticket", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean delTicket(String accessToken, String performanceId, String sessionCode, String priceId, String ticketId) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("performanceId", performanceId);
        params.add("sessionCode", sessionCode);
        params.add("priceId", priceId);
        params.add("ticketId", ticketId);
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/deleteTicket", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean insertOrder(String accessToken, String orderId, LocalDateTime orderTime, Integer channelType, String channelName, Integer ticketNum,
                               long totalAmount, Integer ticketType, Integer ticketMode, Integer authMode, List<OrderVo> ticketOrderList) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("orderId", orderId);
        params.add("orderTime", DateUtil.Formatter.yyyyMMddHHmmss.format(orderTime));
        params.add("channelType", channelType.toString());
        params.add("channelName", channelName);
        params.add("ticketNum", ticketNum.toString());
        params.add("totalAmount", totalAmount + "");
        params.add("ticketType", ticketType.toString());
        params.add("ticketMode", ticketMode.toString());
        params.add("authMode", authMode.toString());
        params.add("ticketOrderList", JSON.toJSONString(ticketOrderList));
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/order", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean refundOrder(String accessToken, String refundOrderId, String orderId, String reason, LocalDateTime refundOrderTime, List<RefundOrderVo> ticketOrderList) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("refundOrderId", refundOrderId);
        params.add("orderId", orderId);
        params.add("reason", reason);
        params.add("refundOrderTime", DateUtil.Formatter.yyyyMMddHHmmss.format(refundOrderTime));
        params.add("ticketOrderList", JSON.toJSONString(ticketOrderList));
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/refundOrder", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }

    @Override
    public boolean insertCheck(String accessToken, List<CheckVo> ticketList) {
        MultiValueMap<String, String> headers = CollectionUtil.linkedMultiValueMapStringString();
        headers.add("Accept", "application/json;charset=UTF-8");
        MultiValueMap<String, String> params = CollectionUtil.linkedMultiValueMapStringString();
        params.add("accessToken", accessToken);
        params.add("ticketList", JSON.toJSONString(ticketList));
        ResponseDataVo<Boolean> response =
                JsonUtils.fromJson(HttpUtil.postRaw(ticketSystemUrl + "/report/checking", JSON.toJSONString(params), headers),
                        new TypeReference<ResponseDataVo<Boolean>>() {
                        });
        return response.getData();
    }
}
