package com.sikey.wa04.common.utils;

import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import okhttp3.*;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Map;
import java.util.TreeMap;

/**
 * @Author: qin
 * @Date: 2025/3/21
 * @Description: 百度地图
 */
public class SearchHttpSN {
    // OkHttp client instance
    private static final OkHttpClient client = new OkHttpClient();
    // Baidu Location API endpoint
    private static final String API_URL = "https://api.map.baidu.com/locapi/v2";
    // Replace with your actual SK (secret key)
    private static final String SK = "6CfgCLhELNytFjX9YbUx7uIfkCGWFTCk";

    /**
     * 将对象转换为按字段名排序的 Map
     *
     * @param obj 实体对象
     * @return
     */
    public static Map<String, Object> convertToSortedMap(Object obj) {
        // 将对象转换为 JSONObject（Hutool 默认使用有序的 LinkedHashMap）
        JSONObject jsonObject = JSONUtil.parseObj(obj);
        // 转换为 TreeMap 实现按键名排序
        return new TreeMap<>(jsonObject);
    }

    public static void main(String[] args) {
        try {
            // Define request parameters in a TreeMap for alphabetical sorting
            TreeMap<String, Object> params = new TreeMap<>();
            params.put("address", "百度大厦"); // Address to locate
            params.put("ak", "yourak");       // Your AK (access key)
            params.put("output", "json");     // Response format

            // Send the POST request and print the response
            String response = sendPostRequest(params);
            System.out.println("Response: " + response);
        } catch (IOException | NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
    }

    public static String sendPostRequest(Map<String, Object> params)
            throws IOException, NoSuchAlgorithmException {
        // Step 1: Calculate SN
        String paramsStr = toQueryString(params);
        String wholeStr = "/locapi/v2/?" + paramsStr + SK;
        String tempStr = URLEncoder.encode(wholeStr, "UTF-8");
        String sn = MD5(tempStr);

        // Step 2: Add SN to parameters
        params.put("sn", sn);

        // Step 3: Build JSON request body
        String requestBodyJson = toJson(params);

        // Step 4: Create POST request
        RequestBody body = RequestBody.create(requestBodyJson, MediaType.parse("application/json"));
        Request request = new Request.Builder()
                .url(API_URL)
                .post(body)
                .build();

        // Step 5: Execute request and return response
        try (Response response = client.newCall(request).execute()) {
            if (!response.isSuccessful()) {
                throw new IOException("Unexpected code " + response);
            }
            return response.body().string();
        }
    }

    // Convert Map to query string with UTF-8 encoding
    public static String toQueryString(Map<String, Object> data)
            throws UnsupportedEncodingException {
        StringBuilder queryString = new StringBuilder();
        for (Map.Entry<String, Object> pair : data.entrySet()) {
            queryString.append(pair.getKey()).append("=");
            queryString.append(URLEncoder.encode((String) pair.getValue(), "UTF-8")).append("&");
        }
        if (queryString.length() > 0) {
            queryString.deleteCharAt(queryString.length() - 1);
        }
        return queryString.toString();
    }

    // Convert Map to JSON string (simple implementation)
    public static String toJson(Map<String, Object> data) {
        StringBuilder json = new StringBuilder("{");
        for (Map.Entry<String, Object> pair : data.entrySet()) {
            json.append("\"").append(pair.getKey()).append("\":\"")
                    .append(pair.getValue()).append("\",");
        }
        if (json.length() > 1) {
            json.deleteCharAt(json.length() - 1);
        }
        json.append("}");
        return json.toString();
    }

    // Calculate MD5 hash
    public static String MD5(String input) throws NoSuchAlgorithmException {
        MessageDigest md = MessageDigest.getInstance("MD5");
        byte[] array = md.digest(input.getBytes());
        StringBuilder sb = new StringBuilder();
        for (byte b : array) {
            sb.append(Integer.toHexString((b & 0xFF) | 0x100).substring(1, 3));
        }
        return sb.toString();
    }
}
