package cn.anicert.secure.access.crypto.service.impl;

import cn.anicert.module.sign.bc.ICryptoService;
import cn.anicert.module.sign.bc.mix.MixCryptoFactory;
import cn.anicert.module.sign.bc.std.Asymmetric;
import cn.anicert.module.sign.bc.std.Symmetric;
import cn.anicert.secure.access.crypto.util.CertUtils;
import cn.anicert.secure.access.crypto.util.SM2Utils;
import cn.anicert.secure.access.crypto.util.SM3Utils;
import cn.anicert.secure.access.crypto.service.ISoftCryptoService;
import cn.hutool.core.io.FileUtil;


import java.io.File;
import java.nio.charset.StandardCharsets;
import java.util.Base64;

/**
 * @Description
 * @Date 2024/5/29 15:35
 * @Author yourongbin
 **/
public class SoftCryptoServiceImpl implements ISoftCryptoService {
    private ICryptoService signService = MixCryptoFactory.getInstance(Asymmetric.SM2, Symmetric.SM4);

    @Override
    public String encodeEnvelop(String cert, String data) throws Exception {
        return encodeEnvelop(cert, data.getBytes());
    }

    @Override
    public String encodeEnvelop(String cert, byte[] dataByte) throws Exception {
        return Base64.getEncoder().encodeToString(SM2Utils.encodeEnvelop(cert, dataByte));
    }

    @Override
    public String decodeEnvelop(String priKey, String envelop) throws Exception {
        return decodeEnvelop(priKey, Base64.getDecoder().decode(envelop));
    }

    @Override
    public String decodeEnvelop(String priKey, byte[] envelop) throws Exception {
        return new String(SM2Utils.decodeEnvelop(priKey, envelop), StandardCharsets.UTF_8);
    }

    @Override
    public String encrypt(String publicKey, String data) throws Exception {
        return SM2Utils.encrypt(publicKey, data);
    }

    @Override
    public String decrypt(String privateKey, String encryptedData) throws Exception {
        return SM2Utils.decrypt(privateKey, encryptedData);
    }

    @Override
    public String p7Sign(String prikey, String cert, String oriData) throws Exception {
        return SM2Utils.pkcs7SignDetach(prikey, cert, oriData);
    }

    @Override
    public Boolean p7Verify(String sign, String source) throws Exception {
        return SM2Utils.pkcs7Verify(Base64.getDecoder().decode(sign), source.getBytes());
    }

    @Override
    public String p1Sign(String prikey, String oriData) throws Exception {
        return SM2Utils.sign(prikey, oriData);
    }

    @Override
    public boolean verify(String publicKey, String data, String signature) throws Exception {
        return verify(publicKey, data, "utf-8", signature);
    }

    @Override
    public String sm2Sign(String prikey, String oriData) throws Exception {
        return Base64.getEncoder().encodeToString(
                signService.sign(prikey, oriData.getBytes(StandardCharsets.UTF_8)));
    }

    @Override
    public boolean sm2SignVerify(String publicKey, String data, String signature) throws Exception {
        byte[] byteSign = Base64.getDecoder().decode(signature);
        byte[] byteBody = data.getBytes(StandardCharsets.UTF_8);
        return signService.verifySign(publicKey, byteSign, byteBody);
    }


    @Override
    public boolean verify(String publicKey, String data, String charset, String signature) throws Exception {
        return SM2Utils.verify(publicKey, data, charset, signature);
    }

    @Override
    public String getCommonNameFromP7Sign(String signature) throws Exception {
        return CertUtils.getSubjectDn(signature);
    }

    @Override
    public String sm3Hash(String source) throws Exception {
        return SM3Utils.sm3Hash(source.getBytes("UTF-16LE"));
    }

}
