package com.easyproject.common.utils.map;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.date.TimeInterval;
import com.google.gson.Gson;
import lombok.extern.slf4j.Slf4j;

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.security.MessageDigest;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;

/**
* 方法说明: 腾讯地图 工具类
* 传入参数: 
* 返回的值: 
* 作者: java-002
* 日期: 2025/9/7 0007
*/
@Slf4j
public class TencentMapUtil {

    private static final String DIRECTION_API_HTTP = "https://apis.map.qq.com";
    private static final String DIRECTION_API_URL = "/ws/direction/v1/driving";

    private static final String API_KEY = "WUQBZ-ISRC4-AB7U3-K7YKA-G7B3K-UPFGL";
    private static final String SECRET_KEY = "7KyF7WAWkkqL3j5G0rmZu9ZTz3l1jsRh";

    public static void main(String[] args) throws Exception {

        double fromLat = 30.8281559245; // 起始点纬度
        double fromLng = 104.9548868815; // 起始点经度

        double destLat = 30.5933609009; // 目的地纬度
        double destLng = 104.0560379028; // 目的地经度

        DistanceApiResult distanceInfo = getDistanceAPI(fromLat,fromLng,destLat,destLng);

    }

    /**
    * 方法说明: 调用腾讯位置服务，获得距离信息 纬度在前，经度在后
    * 传入参数: fromLat 起始点纬度 30.533919
    * 传入参数: fromLng 起始点经度 104.068136
    * 传入参数: destLat 目的地纬度 30.547794
    * 传入参数: destLng 目的地经度 104.077119
    * 返回的值:
    * 作者: java-002
    * 日期: 2025/9/7 0007
    */
    public static DistanceApiResult getDistanceAPI(double fromLat,double fromLng,double destLat,double destLng) throws Exception{

        String fromLatLng = fromLat + "," + fromLng; // 起始点经纬度 纬度在前，经度在后，半角逗号分隔。
        String toLatLng = destLat + "," + destLng; // 目的地经纬度 纬度在前，经度在后，半角逗号分隔。

        // 构建参数Map
        Map<String, String> params = new TreeMap<>();
        params.put("from", fromLatLng);
        params.put("to", toLatLng);
        params.put("key", API_KEY);

        // 对参数进行签名
        String signature = signParams(params);
        //System.out.println("签名 =====>>> " + signature);

        // 将签名添加到参数Map中
        params.put("sig", signature);

        // 构建API请求URL
        StringBuilder apiUrlBuilder = new StringBuilder(DIRECTION_API_HTTP+DIRECTION_API_URL);
        apiUrlBuilder.append("?");
        for (Map.Entry<String, String> entry : params.entrySet()) {
            apiUrlBuilder.append(entry.getKey()).append("=").append(URLEncoder.encode(entry.getValue(), "UTF-8")).append("&");
        }
        String apiUrl = apiUrlBuilder.toString();

        TimeInterval timer = DateUtil.timer();

        // 发送HTTP请求并解析响应数据
        StringBuilder responseBuilder = new StringBuilder();
        URL url = new URL(apiUrl);
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        connection.setRequestMethod("GET");
        BufferedReader reader = new BufferedReader(new InputStreamReader(connection.getInputStream()));
        String line;
        while ((line = reader.readLine()) != null) {
            responseBuilder.append(line);
        }
        reader.close();

        //timer.interval();//花费毫秒数
        long timeNumber = timer.intervalRestart();//返回花费时间(毫秒)，并重置开始时间
        log.info("请求腾讯位置信息，获得两点导航距离，花费时间："+timeNumber + " 毫秒");
        //timer.intervalMinute();//花费分钟数

        // 解析响应数据
        Gson gson = new Gson();
        DirectionResponse directionResponse = gson.fromJson(responseBuilder.toString(), DirectionResponse.class);

        DistanceApiResult distanceApiResult = new DistanceApiResult();
        distanceApiResult.setStatus(directionResponse.getStatus());
        distanceApiResult.setMessage(directionResponse.getMessage());

        if(directionResponse.getStatus()==0){
            directionResponse.getResult().getRoutes().forEach(item->{
                log.info("请求腾讯位置信息，获得两点导航距离，fromLatLng：【{}】，toLatLng：【{}】，距离：【{} 米】，估算时间：【{} 分钟】，途经红绿灯个数：【{} 个】，预估打车费：【{} 元】",
                        fromLatLng,toLatLng,item.getDistance(),item.getDuration(),item.getTraffic_light_count(),item.getTaxi_fare().getFare());

                distanceApiResult.setDistance(item.getDistance());
                distanceApiResult.setDuration(item.getDuration());
                distanceApiResult.setTraffic_light_count(item.getTraffic_light_count());
                distanceApiResult.setFare(item.getTaxi_fare().getFare());
            });
        }
        return distanceApiResult;
    }

    private static String signParams(Map<String, String> params) throws Exception {
        StringBuilder stringBuilder = new StringBuilder();
        for (Map.Entry<String, String> entry : params.entrySet()) {
            stringBuilder.append(entry.getKey()).append("=").append(entry.getValue()).append("&");
        }
        String strToSign = stringBuilder.toString().substring(0,stringBuilder.length()-1) + SECRET_KEY;
        //System.out.println("strToSign ===>>>> " + strToSign);
        String strToSignEnd = DIRECTION_API_URL+"?"+strToSign;
        //System.out.println("strToSignEnd ===>>>> " + strToSignEnd);


        // 计算MD5哈希值
        MessageDigest md5 = MessageDigest.getInstance("MD5");
        byte[] digest = md5.digest(strToSignEnd.getBytes());

        // 将字节数组转换为十六进制字符串
        StringBuilder hexString = new StringBuilder();
        for (byte b : digest) {
            String hex = Integer.toHexString(0xFF & b);
            if (hex.length() == 1) {
                hexString.append('0');
            }
            hexString.append(hex);
        }

        return hexString.toString();
    }

}
