package com.usky.vpp.crypto;

import cn.hutool.core.codec.Base64;
import cn.hutool.crypto.SmUtil;
import cn.hutool.crypto.asymmetric.KeyType;
import cn.hutool.crypto.asymmetric.SM2;
import com.usky.vpp.config.VppUnProperties;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import java.nio.charset.StandardCharsets;

/**
 * 运管平台 UN/DN 国密加解密与签名（SM2/SM3withSM2）
 */
@Service
public class VppUnCryptoService {

    private static final Logger log = LoggerFactory.getLogger(VppUnCryptoService.class);

    @Autowired
    private VppUnProperties properties;

    public boolean isActive() {
        return Boolean.TRUE.equals(properties.getCryptoEnabled())
                && StringUtils.hasText(properties.getUnPublicKey())
                && StringUtils.hasText(properties.getDnPrivateKey());
    }

    public String encryptRequest(String plainJson) {
        SM2 sm2 = SmUtil.sm2(null, properties.getUnPublicKey());
        return sm2.encryptBase64(plainJson, KeyType.PublicKey);
    }

    public String signRequest(String cipherBase64) {
        SM2 sm2 = SmUtil.sm2(properties.getDnPrivateKey(), null);
        byte[] sign = sm2.sign(cipherBase64.getBytes(StandardCharsets.UTF_8));
        return Base64.encode(sign);
    }

    public String decryptResponse(String cipherBase64) {
        SM2 sm2 = SmUtil.sm2(properties.getDnPrivateKey(), properties.getDnPublicKey());
        return sm2.decryptStr(cipherBase64, KeyType.PrivateKey);
    }

    public boolean verifyResponse(String cipherBase64, String signBase64) {
        return verifyInbound(cipherBase64, signBase64);
    }

    /** UN→DN 请求验签 */
    public boolean verifyInbound(String cipherBase64, String signBase64) {
        if (!StringUtils.hasText(signBase64)) {
            log.warn("UN 请求缺少 X-Sign，跳过验签");
            return true;
        }
        SM2 sm2 = SmUtil.sm2(null, properties.getUnPublicKey());
        return sm2.verify(cipherBase64.getBytes(StandardCharsets.UTF_8), Base64.decode(signBase64));
    }

    /** UN→DN 请求解密 */
    public String decryptInbound(String cipherBase64) {
        return decryptResponse(cipherBase64);
    }

    /** DN→UN 响应加密 */
    public String encryptOutbound(String plainJson) {
        return encryptRequest(plainJson);
    }

    /** DN→UN 响应签名 */
    public String signOutbound(String cipherBase64) {
        return signRequest(cipherBase64);
    }
}
