package com.cool.store.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.cool.store.enums.ErrorCodeEnum;
import com.cool.store.exception.ServiceException;
import com.cool.store.request.oppty.*;
import com.cool.store.response.oppty.*;
import com.cool.store.service.ThirdOpportunityService;
import com.cool.store.utils.JsonUtils;
import com.cool.store.utils.SignatureUtils;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.extern.slf4j.Slf4j;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.io.IOException;
import java.lang.reflect.ParameterizedType;
import java.util.List;
import java.util.Map;

/**
 * @Author suzhuhong
 * @Date 2025/3/26 15:20
 * @Version 1.0
 */
@Service
@Slf4j
public class ThirdOpportunityServiceImpl implements ThirdOpportunityService {

    @Value("${zx.opportunity.url}")
    private String apiUrl;

    @Value("${third.party.appKey}")
    private String appKey;

    @Value("${third.party.appSecret}")
    private String appSecret;

    @Resource
    OkHttpClient okHttpClient;

    @Resource
    ObjectMapper objectMapper;


    @Override
    public OpportunityInfoPageResponse listOpportunities(OpportunityListRequest requestBody) {
        // 1. 发送POST请求
        String url = apiUrl+"open/oppty/v1/listOppty";
        return executeApiCall(url, requestBody, OpportunityInfoPageResponse.class);
    }

    @Override
    public OpportunityDetailResponse getOpportunitiesDetail(OpportunityDetailRequest requestBody) {
        String url = apiUrl + "open/oppty/v1/opptyDetail";
        return executeApiCall(url, requestBody, OpportunityDetailResponse.class);
    }


    @Override
    public String followOpportunity(FollowRequest requestBody) {
        String url = apiUrl+"open/oppty/v1/saveAtUser";
        return executeApiCall(url, requestBody, String.class);
    }

    @Override
    public String inspectionOpportunity(InspectionRequest requestBody) {
        String url = apiUrl+"open/oppty/v1/inspection";
        return executeApiCall(url, requestBody, String.class);
    }

    @Override
    public String berthOperation(BerthOperationRequest requestBody) {
        String url = apiUrl+"open/oppty/v1/addBerthInfo";
        return executeApiCall(url, requestBody, String.class);

    }

    @Override
    public String storeOperation(StoreOperationRequest requestBody) {
        String url = apiUrl+"open/oppty/v1/addStore";
        return executeApiCall(url, requestBody, String.class);
    }

    @Override
    public List<CityResponse> cityList(CityRequest requestBody) {
        // 1. 发送POST请求
        String url = apiUrl+"open/oppty/v1/listCity";
        return executeApiCall(url, requestBody, List.class);
    }


    private <T> T executeApiCall(String url, Object requestBody, Class<T> responseType) {
        // 1. 打印请求前日志
        logRequest(url, requestBody);

        try {
            Request request = buildRequest(requestBody, url);

            try (Response response = okHttpClient.newCall(request).execute()) {
                // 2. 获取原始响应内容
                String responseBody = response.body().string();

                // 3. 打印响应日志
                logResponse(url, response.code(), responseBody);

                if (!response.isSuccessful()) {
                    throw new ServiceException(ErrorCodeEnum.THIRD_API_ERROR,
                            "HTTP请求失败，状态码: " + response.code());
                }

                // 4. 解析响应
                JavaType javaType = objectMapper.getTypeFactory()
                        .constructParametricType(OpportunityApiResponse.class, responseType);

                OpportunityApiResponse<T> apiResponse = objectMapper.readValue(responseBody, javaType);

                if (apiResponse.getCode() != 200) {
                    throw new ServiceException(ErrorCodeEnum.THIRD_API_ERROR,apiResponse.getMsg());
                }

                return apiResponse.getData();
            }
        } catch (ServiceException e) {
            throw e;
        } catch (Exception e) {
            log.error("API调用异常 - URL: {}, 错误: {}", url, e.getMessage(), e);
            throw new ServiceException(ErrorCodeEnum.THIRD_API_ERROR, "接口调用异常: " + e.getMessage());
        }
    }


    private Request buildRequest(Object requestBody, String url) {
        Map<String, Object> params = JsonUtils.parseJsonToMap(JSONObject.toJSONString(requestBody));
        long timestamp = System.currentTimeMillis() / 1000;

        String signString = SignatureUtils.buildSignString(params, appKey, timestamp);
        String sign = SignatureUtils.hmacSha256(signString, appSecret);

        log.debug("签名生成 - 原始字符串: {}, 签名结果: {}", signString, sign);

        RequestBody body = RequestBody.create(okhttp3.MediaType.parse("application/json"),
                JSONObject.toJSONString(requestBody)
        );

        return new Request.Builder()
                .url(url)
                .post(body)
                .addHeader("Content-Type", "application/json")
                .addHeader("Accept", "application/json")
                .addHeader("sign", sign)
                .addHeader("timestamp", String.valueOf(timestamp))
                .addHeader("appkey", appKey)
                .build();
    }

    /**
     * 记录请求日志
     */
    private void logRequest(String url, Object requestBody) {
        if (log.isInfoEnabled()) {
            try {
                log.info("\n======= 请求开始 =======\n" +
                                "API地址: {}\n" +
                                "请求参数: {}\n" +
                                "======= 请求结束 =======",
                        url,
                        objectMapper.writerWithDefaultPrettyPrinter()
                                .writeValueAsString(requestBody));
            } catch (JsonProcessingException e) {
                log.warn("日志JSON序列化失败", e);
            }
        }
    }

    /**
     * 记录响应日志
     */
    private void logResponse(String url, int statusCode, String responseBody) {
        if (log.isInfoEnabled()) {
            try {
                // 尝试美化JSON输出
                Object json = objectMapper.readValue(responseBody, Object.class);
                String prettyResponse = objectMapper.writerWithDefaultPrettyPrinter()
                        .writeValueAsString(json);

                log.info("\n======= 响应开始 =======\n" +
                                "API地址: {}\n" +
                                "HTTP状态码: {}\n" +
                                "响应内容: {}\n" +
                                "======= 响应结束 =======",
                        url,
                        statusCode,
                        prettyResponse);
            } catch (Exception e) {
                // 非JSON响应或解析失败时直接输出原始内容
                log.info("\n======= 响应开始 =======\n" +
                                "API地址: {}\n" +
                                "HTTP状态码: {}\n" +
                                "原始响应: {}\n" +
                                "======= 响应结束 =======",
                        url,
                        statusCode,
                        responseBody);
            }
        }
    }

}
