using Microsoft.VisualBasic;
using System.Security.Cryptography;
using System.Text;

namespace RB_MES_API.Context
{
    /// <summary>
    /// 密码管理
    /// </summary>
    public class AESHelp
    {
        private static string appkey = "RB@8636926";
        /// <summary>
        /// 加密
        /// </summary>
        /// <param name="sourceText">原文</param>
        /// <returns>密文(Base64字符串)</returns>
        public static string Encrypt(string sourceText)
        {
            return Encrypt(sourceText, appkey);
        }
        /// <summary>
        /// 加密
        /// Key和IV将被转换为MD5值
        /// </summary>
        /// <param name="sourceText">原文</param>
        /// <param name="sKey">密匙</param>
        /// <returns>密文(Base64字符串)</returns>
        private static string Encrypt(string sourceText, string sKey)
        {
            var des = DES.Create();
            byte[] inputByteArray;
            inputByteArray = Encoding.Default.GetBytes(sourceText);
            des.Key = Encoding.ASCII.GetBytes(Md5Hash(sKey).Substring(0, 8));
            des.IV = Encoding.ASCII.GetBytes(Md5Hash(sKey).Substring(0, 8));
            MemoryStream ms = new MemoryStream();
            CryptoStream cs = new CryptoStream(ms, des.CreateEncryptor(), CryptoStreamMode.Write);
            cs.Write(inputByteArray, 0, inputByteArray.Length);
            cs.FlushFinalBlock();
            StringBuilder ret = new StringBuilder();
            foreach (byte b in ms.ToArray())
            {
                ret.AppendFormat("{0:X2}", b);
            }
            ms.Dispose();
            cs.Dispose();
            des.Dispose();
            return ret.ToString();
        }


        /// <summary>
        /// 解密
        /// </summary>
        /// <param name="cipherText">密文</param>
        /// <returns>原文</returns>
        public static string Decrypt(string cipherText)
        {
            if (!string.IsNullOrEmpty(cipherText))
            {
                return Decrypt(cipherText, appkey);
            }
            else
            {
                return "";
            }
        }
        /// <summary>
        /// 解密
        /// </summary>
        /// <param name="sourceText">加密文本</param>
        /// <param name="sKey">密匙</param>
        /// <returns></returns>
        private static string Decrypt(string sourceText, string sKey)
        {
            var des = DES.Create();
            int len;
            len = sourceText.Length / 2;
            byte[] inputByteArray = new byte[len];
            int x, i;
            for (x = 0; x < len; x++)
            {
                i = Convert.ToInt32(sourceText.Substring(x * 2, 2), 16);
                inputByteArray[x] = (byte)i;
            }
            des.Key = Encoding.ASCII.GetBytes(Md5Hash(sKey).Substring(0, 8));
            des.IV = Encoding.ASCII.GetBytes(Md5Hash(sKey).Substring(0, 8));
            MemoryStream ms = new MemoryStream();
            CryptoStream cs = new CryptoStream(ms, des.CreateDecryptor(), CryptoStreamMode.Write);
            cs.Write(inputByteArray, 0, inputByteArray.Length);
            cs.FlushFinalBlock();
            byte[] msstr = ms.ToArray();
            cs.Dispose();
            ms.Dispose();
            des.Dispose();
            return Encoding.Default.GetString(msstr);
        }
        /// <summary>
        /// 32位MD5加密
        /// </summary>
        /// <param name="input">要转为byte[]的文本</param>
        /// <returns></returns>
        private static string Md5Hash(string input)
        {
            MD5 md5Hasher = MD5.Create();
            byte[] data = md5Hasher.ComputeHash(Encoding.Default.GetBytes(input));
            StringBuilder sBuilder = new StringBuilder();
            for (int i = 0; i < data.Length; i++)
            {
                sBuilder.Append(data[i].ToString("x2"));
            }
            md5Hasher.Dispose();
            return sBuilder.ToString();
        }
        /// <summary>
        /// 金蝶K3、KIS系列用户解密。想要加密算法的，联系13823037922
        /// </summary>
        /// <param name="password"></param>
        /// <returns></returns>
        public static string K3Decrypt(string password)
        {
            if (password == null) return string.Empty;
            int lenint, ASCInt1, ASCInt2, iMod, i;
            string UnEncryptStrt, sMidStr;
            UnEncryptStrt = "";
            i = 1;
            iMod = 1;

            password = Strings.Mid(password, 51, (Strings.Len(password) - 50));
            lenint = Strings.Len(password);
            while (i < lenint)
            {
                sMidStr = Strings.Mid(password, i, 1);
                ASCInt1 = Strings.Asc(sMidStr);
                i = i + 1;

                sMidStr = Strings.Mid(password, i, 1);
                ASCInt2 = Strings.Asc(sMidStr);

                iMod = iMod % 3;

                if (iMod == 1)
                {
                    UnEncryptStrt = UnEncryptStrt + Strings.Chr((ASCInt1 - 32) * 64 + ASCInt2 - 32);
                    i = i + 1;
                }

                if (iMod == 2)
                {
                    UnEncryptStrt = UnEncryptStrt + Strings.Chr((int)((ASCInt1 - 32) * 16 + (ASCInt2 - 32) / (double)4));
                    i = i + 1;
                }

                if (iMod == 0)
                    UnEncryptStrt = UnEncryptStrt + Strings.Chr((int)((ASCInt1 - 32) * 4 + (ASCInt2 - 32) / (double)16));

                i = i + 1;
                iMod = iMod + 1;
            }

            return UnEncryptStrt;
        }

        /// <summary>
        /// AES 加密
        /// </summary>
        /// <param name="str">明文（待加密）</param>
        /// <param name="key">密文</param>
        /// <returns></returns>
        public static string AesEncrypt(string str, string key)
        {
            if (string.IsNullOrEmpty(str)) return null;
            Byte[] toEncryptArray = Encoding.UTF8.GetBytes(str);

            var rm = Aes.Create();
            rm.Key = Encoding.UTF8.GetBytes(key);
            rm.Mode = CipherMode.ECB;
            rm.Padding = PaddingMode.PKCS7;

            ICryptoTransform cTransform = rm.CreateEncryptor();
            Byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);

            return Convert.ToBase64String(resultArray, 0, resultArray.Length);
        }

        /// <summary>
        /// AES 解密
        /// </summary>
        /// <param name="str">明文（待解密）</param>
        /// <param name="key">密文</param>
        /// <returns></returns>
        public static string AesDecrypt(string str, string key)
        {
            if (string.IsNullOrEmpty(str)) return null;
            Byte[] toEncryptArray = Convert.FromBase64String(str);

            var rm = Aes.Create();
            rm.Key = Encoding.UTF8.GetBytes(key);
            rm.Mode = CipherMode.ECB;
            rm.Padding = PaddingMode.PKCS7;

            ICryptoTransform cTransform = rm.CreateDecryptor();
            Byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);

            return Encoding.UTF8.GetString(resultArray);
        }
    }
}
