package com.nbport.zgwl.contractpush.utils;

import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.TypeReference;
import com.nbport.zgwl.exception.ServiceException;
import org.springframework.core.io.ByteArrayResource;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Component;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.Map;

/**
 * 最简单的 HTTP 调用工具
 * 当前只做 GET / POST JSON / POST MULTIPART 三种
 */
@Component
public class ContractPushHttpUtils {

    private final RestTemplate restTemplate;

    public ContractPushHttpUtils(RestTemplate contractPushRestTemplate) {
        this.restTemplate = contractPushRestTemplate;
    }

    /** GET 请求，queryParams 会自动拼接到 URL 上 */
    public Map<String, Object> get(String url, Map<String, String> queryParams) {
        String finalUrl = ContractPushUrlUtils.appendQuery(url, queryParams);
        ResponseEntity<String> response = restTemplate.getForEntity(finalUrl, String.class);
        return parseResponse(response.getBody());
    }

    /** POST JSON 请求，可自定义请求头 */
    public Map<String, Object> postJson(String url, Map<String, Object> body, Map<String, String> headers) {
        HttpHeaders httpHeaders = new HttpHeaders();
        httpHeaders.setContentType(MediaType.APPLICATION_JSON);
        addHeaders(httpHeaders, headers);
        HttpEntity<Map<String, Object>> entity = new HttpEntity<>(body, httpHeaders);
        ResponseEntity<String> response = restTemplate.exchange(url, HttpMethod.POST, entity, String.class);
        return parseResponse(response.getBody());
    }

    /** 上传文件（POST MULTIPART） */
    public Map<String, Object> postMultipart(String url, MultipartFile file, Map<String, String> headers) {
        if (file == null || file.isEmpty()) {
            throw new ServiceException("上传文件不能为空");
        }

        HttpHeaders httpHeaders = new HttpHeaders();
        httpHeaders.setContentType(MediaType.MULTIPART_FORM_DATA);
        addHeaders(httpHeaders, headers);

        MultiValueMap<String, Object> formData = new LinkedMultiValueMap<>();
        formData.add("file", toByteArrayResource(file));

        HttpEntity<MultiValueMap<String, Object>> entity = new HttpEntity<>(formData, httpHeaders);
        ResponseEntity<String> response = restTemplate.exchange(url, HttpMethod.POST, entity, String.class);
        return parseResponse(response.getBody());
    }

    public Map<String, Object> postMultipart(String url, byte[] fileBytes, String originalFilename, Map<String, String> headers) {
        if (fileBytes == null || fileBytes.length == 0) {
            throw new ServiceException("上传文件不能为空");
        }
        if (originalFilename == null || originalFilename.trim().isEmpty()) {
            throw new ServiceException("上传文件名不能为空");
        }

        HttpHeaders httpHeaders = new HttpHeaders();
        httpHeaders.setContentType(MediaType.MULTIPART_FORM_DATA);
        addHeaders(httpHeaders, headers);

        MultiValueMap<String, Object> formData = new LinkedMultiValueMap<>();
        formData.add("file", toByteArrayResource(fileBytes, originalFilename));

        HttpEntity<MultiValueMap<String, Object>> entity = new HttpEntity<>(formData, httpHeaders);
        ResponseEntity<String> response = restTemplate.exchange(url, HttpMethod.POST, entity, String.class);
        return parseResponse(response.getBody());
    }

    /** 将 MultipartFile 转为 ByteArrayResource（保留原始文件名） */
    private ByteArrayResource toByteArrayResource(MultipartFile file) {
        try {
            return new ByteArrayResource(file.getBytes()) {
                @Override
                public String getFilename() {
                    return file.getOriginalFilename();
                }
            };
        } catch (IOException e) {
            throw new ServiceException("读取上传文件失败: " + e.getMessage());
        }
    }

    private ByteArrayResource toByteArrayResource(byte[] bytes, String originalFilename) {
        return new ByteArrayResource(bytes) {
            @Override
            public String getFilename() {
                return originalFilename;
            }
        };
    }

    private void addHeaders(HttpHeaders httpHeaders, Map<String, String> headers) {
        if (headers == null || headers.isEmpty()) {
            return;
        }
        headers.forEach(httpHeaders::add);
    }

    private Map<String, Object> parseResponse(String responseBody) {
        if (responseBody == null || responseBody.trim().isEmpty()) {
            return Collections.emptyMap();
        }
        try {
            return JSON.parseObject(responseBody, new TypeReference<LinkedHashMap<String, Object>>() {
            });
        } catch (Exception ex) {
            Map<String, Object> fallback = new LinkedHashMap<>();
            fallback.put("raw", responseBody);
            return fallback;
        }
    }
}
