CryptoService.cs 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315
  1. using Alchemy.Core.Extensions;
  2. using System.Security.Cryptography;
  3. using System.Security.Cryptography.X509Certificates;
  4. using System.Text;
  5. namespace Alchemy.Core.Services
  6. {
  7. public class CryptoService
  8. {
  9. /// <summary>
  10. /// 将一条十六进制字符串转换为ASCII
  11. /// </summary>
  12. /// <param name="hexstring">一条十六进制字符串</param>
  13. /// <returns>返回一条ASCII码</returns>
  14. public static string HexStringToASCII(string hexstring)
  15. {
  16. byte[] bt = HexStringToBinary(hexstring);
  17. string lin = "";
  18. for (int i = 0; i < bt.Length; i++)
  19. {
  20. lin = lin + bt[i] + " ";
  21. }
  22. string[] ss = lin.Trim().Split(new char[] { ' ' });
  23. char[] c = new char[ss.Length];
  24. int a;
  25. for (int i = 0; i < c.Length; i++)
  26. {
  27. a = Convert.ToInt32(ss[i]);
  28. c[i] = Convert.ToChar(a);
  29. }
  30. string b = new string(c);
  31. return b;
  32. }
  33. /**/
  34. /// <summary>
  35. /// 16进制字符串转换为二进制数组
  36. /// </summary>
  37. /// <param name="hexstring">字符串每个字节之间都应该有空格,大多数的串口通讯资料上面的16进制都是字节之间都是用空格来分割的。</param>
  38. /// <returns>返回一个二进制字符串</returns>
  39. public static byte[] HexStringToBinary(string hexstring)
  40. {
  41. string[] tmpary = hexstring.Trim().Split(' ');
  42. byte[] buff = new byte[tmpary.Length];
  43. for (int i = 0; i < buff.Length; i++)
  44. {
  45. buff[i] = Convert.ToByte(tmpary[i], 16);
  46. }
  47. return buff;
  48. }
  49. /// <summary>
  50. /// AES 解密
  51. /// </summary>
  52. /// <param name="strEncoded"></param>
  53. /// <param name="strKey"></param>
  54. /// <returns></returns>
  55. public static string DecodeAes(string strEncoded, string strKey)
  56. {
  57. string strResult = string.Empty;
  58. byte[] encryptedBytes = Convert.FromBase64String(strEncoded);
  59. byte[] keyBytes = Encoding.UTF8.GetBytes(strKey);
  60. using (Aes aes = Aes.Create())
  61. {
  62. aes.Key = keyBytes;
  63. aes.IV = new byte[aes.BlockSize / 8];
  64. using (MemoryStream memStream = new MemoryStream())
  65. {
  66. using (CryptoStream cryptoStream = new CryptoStream(memStream, aes.CreateDecryptor(), CryptoStreamMode.Write))
  67. {
  68. cryptoStream.Write(encryptedBytes, 0, encryptedBytes.Length);
  69. cryptoStream.FlushFinalBlock();
  70. byte[] decryptedBytes = memStream.ToArray();
  71. strResult = Encoding.UTF8.GetString(decryptedBytes);
  72. }
  73. }
  74. }
  75. return strResult;
  76. }
  77. /// <summary>
  78. /// 唯一识别ID加密算法
  79. /// </summary>
  80. /// <param name="numID"></param>
  81. /// <param name="strString"></param>
  82. /// <returns></returns>
  83. public static string EncodeUniqId(int numID, string strString)
  84. {
  85. string strUserIDHashed = EncodeMD5(numID.ToString());
  86. string strUserNameHashed = EncodeMD5(strString);
  87. string strDatetimeHashed = EncodeMD5(DateTimeService.Now());
  88. string value = EncodeMD5(EncodeBase64(strUserIDHashed + strUserNameHashed + strDatetimeHashed));
  89. return value;
  90. }
  91. /// <summary>
  92. /// 用户密码加密算法,使用基础加密算法
  93. /// </summary>
  94. /// <param name="strPwd">输入未加密的密码</param>
  95. /// <returns></returns>
  96. public static string EncodeUserPwd(string strPwd)
  97. {
  98. //string value = EncodeMD5(EncodeBase64(EncodeMD5(strPwd)));
  99. return EncodeMD5(strPwd);
  100. }
  101. /// <summary>
  102. /// 基础加密算法,先MD5再Base64再MD5
  103. /// </summary>
  104. /// <param name="strData">输入未加密的数据</param>
  105. /// <returns></returns>
  106. public static string EncodeBasicCrypto(string strData)
  107. {
  108. string value = EncodeMD5(EncodeBase64(EncodeMD5(strData)));
  109. return value;
  110. }
  111. /// <summary>
  112. /// 不安全加密算法,3次Base64
  113. /// </summary>
  114. /// <param name="strData"></param>
  115. /// <returns></returns>
  116. public static string EncodeUnsafeCrypto(string strData)
  117. {
  118. string value = EncodeBase64(EncodeBase64(EncodeBase64(strData)));
  119. return value;
  120. }
  121. public static string DecodeUnsafeCrypto(string strData)
  122. {
  123. string value = DecodeBase64(DecodeBase64(DecodeBase64(strData)));
  124. return value;
  125. }
  126. /// <summary>
  127. /// MD5加密,输出32位小写
  128. /// </summary>
  129. /// <param name="strData">输入字符串</param>
  130. /// <returns></returns>
  131. public static string EncodeMD5(string strData)
  132. {
  133. MD5CryptoServiceProvider md5 = new MD5CryptoServiceProvider();
  134. byte[] bytValue, bytHash;
  135. bytValue = Encoding.UTF8.GetBytes(strData);
  136. bytHash = md5.ComputeHash(bytValue);
  137. md5.Clear();
  138. string sTemp = "";
  139. for (int i = 0; i < bytHash.Length; i++)
  140. {
  141. sTemp += bytHash[i].ToString("X").PadLeft(2, '0');
  142. }
  143. return sTemp.ToLower();
  144. }
  145. /// <summary>
  146. /// Base64加密
  147. /// </summary>
  148. /// <param name="strData">输入字符串</param>
  149. /// <returns></returns>
  150. public static string EncodeBase64(string strData)
  151. {
  152. byte[] arrData = Encoding.UTF8.GetBytes(strData);
  153. string strBase64 = Convert.ToBase64String(arrData);
  154. return strBase64;
  155. }
  156. /// <summary>
  157. /// Base64解密
  158. /// </summary>
  159. /// <param name="strData">输入字符串</param>
  160. /// <returns></returns>
  161. public static string DecodeBase64(string strData)
  162. {
  163. string strRaw = string.Empty;
  164. try
  165. {
  166. byte[] bytes = Convert.FromBase64String(strData);
  167. strRaw = Encoding.UTF8.GetString(bytes);
  168. }
  169. catch (Exception ex)
  170. {
  171. //throw new Exception(ex.Message);
  172. strRaw = strData;
  173. }
  174. return strRaw;
  175. }
  176. /// <summary>
  177. /// HMACSHA256加密算法
  178. /// </summary>
  179. /// <param name="strData"></param>
  180. /// <param name="strSecret"></param>
  181. /// <returns></returns>
  182. public static string EncodeHMACSHA256forWx(string strSecret)
  183. {
  184. return EncodeHMACSHA256("", strSecret);
  185. }
  186. /// <summary>
  187. ///
  188. /// </summary>
  189. /// <param name="strData"></param>
  190. /// <param name="strSecret"></param>
  191. /// <returns></returns>
  192. public static string EncodeHMACSHA256(string strData, string strSecret)
  193. {
  194. // 1. 将密钥字符串转换为UTF-8字节数组(不进行Base64解码)
  195. byte[] keyBytes = Encoding.UTF8.GetBytes(strSecret);
  196. // 2. 处理空字符串:使用空字节数组
  197. byte[] dataBytes = string.IsNullOrEmpty(strData)
  198. ? new byte[0]
  199. : Encoding.UTF8.GetBytes(strData);
  200. // 3. 计算HMAC-SHA256
  201. using var hmac = new HMACSHA256(keyBytes);
  202. byte[] hashBytes = hmac.ComputeHash(dataBytes);
  203. // 4. 转换为小写十六进制字符串
  204. return Convert.ToHexString(hashBytes).ToLowerInvariant();
  205. }
  206. /// <summary>
  207. /// 生成短链接
  208. /// </summary>
  209. /// <param name="strKey"></param>
  210. /// <param name="len"></param>
  211. /// <returns></returns>
  212. public static string EncodeShortUrl(string strKey, int len = 6)
  213. {
  214. string value = string.Empty;
  215. List<string> listFilter = new List<string>();
  216. listFilter.Add("o");
  217. listFilter.Add("0");
  218. listFilter.Add("O");
  219. listFilter.Add("I");
  220. listFilter.Add("l");
  221. listFilter.Add("i");
  222. listFilter.Add("1");
  223. for (int i = 0; i < len; i++)
  224. {
  225. string strChar = EncodeMD5(strKey + Guid.NewGuid().ToString()).ToUpper().Substring(i, 1);
  226. while (!listFilter.Contains(strChar))
  227. {
  228. strChar = EncodeMD5(strKey + Guid.NewGuid().ToString()).ToUpper().Substring(i, 1);
  229. }
  230. value += strChar;
  231. }
  232. return value;
  233. }
  234. /// <summary>
  235. /// 生成外部订单号
  236. /// </summary>
  237. /// <param name="strPrefix"></param>
  238. /// <returns></returns>
  239. public static string EncodeOutTradeNo(string strPrefix)
  240. {
  241. return strPrefix + EncodeUniqId(9999, Guid.NewGuid().ToString()).ToUpper();
  242. }
  243. /// <summary>
  244. /// RSA加密
  245. /// </summary>
  246. /// <param name="text"></param>
  247. /// <param name="publicKey"></param>
  248. /// <returns></returns>
  249. public static string EncodeRSA(string text, byte[] publicKey)
  250. {
  251. using (var x509 = new X509Certificate2(publicKey))
  252. {
  253. using (var rsa = (RSACryptoServiceProvider)x509.PublicKey.Key)
  254. {
  255. var buff = rsa.Encrypt(Encoding.UTF8.GetBytes(text), true);
  256. return Convert.ToBase64String(buff);
  257. }
  258. }
  259. }
  260. /// <summary>
  261. /// 计算文件的 MD5 值
  262. /// </summary>
  263. /// <param name="fileName">要计算 MD5 值的文件名和路径</param>
  264. /// <returns>MD5 值16进制字符串</returns>
  265. //public static string EncodeMd5FileHash(string fileName)
  266. //{
  267. // return HashFile(fileName, "md5");
  268. //}
  269. /// <summary>
  270. /// 计算文件的哈希值
  271. /// </summary>
  272. /// <param name="fileName">要计算哈希值的文件名和路径</param>
  273. /// <param name="algName">算法:sha1,md5</param>
  274. /// <returns>哈希值16进制字符串</returns>
  275. //private static string HashFile(string fileName, string algName)
  276. //{
  277. // if (!File.Exists(fileName))
  278. // return string.Empty;
  279. // FileStream fs = new FileStream(fileName, FileMode.Open, FileAccess.Read);
  280. // byte[] hashBytes = HashData(fs, algName);
  281. // fs.Close();
  282. // return ConvertService.ByteArrayToHexString(hashBytes);
  283. //}
  284. /// <summary>
  285. /// 计算哈希值
  286. /// </summary>
  287. /// <param name="stream">要计算哈希值的 Stream</param>
  288. /// <param name="algName">算法:sha1,md5</param>
  289. /// <returns>哈希值字节数组</returns>
  290. private static byte[] HashData(Stream stream, string algName)
  291. {
  292. HashAlgorithm algorithm;
  293. if (algName.IsNull())
  294. {
  295. throw new ArgumentNullException("algName 不能为 null");
  296. }
  297. if (string.Compare(algName, "sha1", true) == 0)
  298. {
  299. algorithm = SHA1.Create();
  300. }
  301. else
  302. {
  303. if (string.Compare(algName, "md5", true) != 0)
  304. {
  305. throw new Exception("algName 只能使用 sha1 或 md5");
  306. }
  307. algorithm = MD5.Create();
  308. }
  309. return algorithm.ComputeHash(stream);
  310. }
  311. }
  312. }