Files
GateDge2023_ljy/00.SDK/E_ZKEccTopSdk/Uitl/TopUtils.cs
PastSaid 16fbd10312 1
2024-04-29 17:57:07 +08:00

272 lines
9.6 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.NetworkInformation;
using System.Net.Sockets;
using System.Security.Cryptography;
using System.Text;
namespace E_ZKEccTopSdk.Uitl
{
/// <summary>
/// TOP系统工具类。
/// </summary>
public abstract class TopUtils
{
private static readonly JSONParameters jp = new JSONParameters();
private static string intranetIp;
static TopUtils()
{
jp.UseApiNamingStyle = true;
jp.UseExtensions = false;
jp.SerializeNullValues = false;
}
/// <summary>
/// 给TOP请求签名。
/// </summary>
/// <param name="parameters">所有字符型的TOP请求参数</param>
/// <param name="secret">签名密钥</param>
/// <param name="signMethod">签名方法可选值md5, hmac</param>
/// <returns>签名</returns>
public static string SignTopRequest(IDictionary<string, string> parameters, string secret, string signMethod)
{
return SignTopRequest(parameters, null, secret, signMethod);
}
/// <summary>
/// 给TOP请求签名。
/// </summary>
/// <param name="parameters">所有字符型的TOP请求参数</param>
/// <param name="body">请求主体内容</param>
/// <param name="secret">签名密钥</param>
/// <param name="signMethod">签名方法可选值md5, hmac</param>
/// <returns>签名</returns>
public static string SignTopRequest(IDictionary<string, string> parameters, string body, string secret, string signMethod)
{
// 第一步把字典按Key的字母顺序排序
IDictionary<string, string> sortedParams = new SortedDictionary<string, string>(parameters, StringComparer.Ordinal);
// 第二步:把所有参数名和参数值串在一起
StringBuilder query = new StringBuilder();
if (Constants.SIGN_METHOD_MD5.Equals(signMethod))
{
query.Append(secret);
}
foreach (KeyValuePair<string, string> kv in sortedParams)
{
if (!string.IsNullOrEmpty(kv.Key) && !string.IsNullOrEmpty(kv.Value))
{
query.Append(kv.Key).Append(kv.Value);
}
}
// 第三步:把请求主体拼接在参数后面
if (!string.IsNullOrEmpty(body))
{
query.Append(body);
}
// 第四步使用MD5/HMAC加密
byte[] bytes;
if (Constants.SIGN_METHOD_HMAC.Equals(signMethod))
{
HMACMD5 hmac = new HMACMD5(Encoding.UTF8.GetBytes(secret));
bytes = hmac.ComputeHash(Encoding.UTF8.GetBytes(query.ToString()));
}
else if (Constants.SIGN_METHOD_HMAC_SHA256.Equals(signMethod))
{
HMACSHA256 hmac = new HMACSHA256(Encoding.UTF8.GetBytes(secret));
bytes = hmac.ComputeHash(Encoding.UTF8.GetBytes(query.ToString()));
}
else
{
query.Append(secret);
MD5 md5 = MD5.Create();
bytes = md5.ComputeHash(Encoding.UTF8.GetBytes(query.ToString()));
}
// 第五步:把二进制转化为大写的十六进制
StringBuilder result = new StringBuilder();
for (int i = 0; i < bytes.Length; i++)
{
result.Append(bytes[i].ToString("X2"));
}
return result.ToString();
}
/// <summary>
/// 清除字典中值为空的项。
/// </summary>
/// <param name="dict">待清除的字典</param>
/// <returns>清除后的字典</returns>
public static IDictionary<string, T> CleanupDictionary<T>(IDictionary<string, T> dict)
{
IDictionary<string, T> newDict = new Dictionary<string, T>(dict.Count);
foreach (KeyValuePair<string, T> kv in dict)
{
if (kv.Value != null)
{
newDict.Add(kv.Key, kv.Value);
}
}
return newDict;
}
/// <summary>
/// 把对象转换为JSON字符串。
/// </summary>
public static string ObjectToJson(object obj)
{
return JSON.ToJSON(obj, jp);
}
/// <summary>
/// 把对象转换为JSON字符串。
/// </summary>
public static string ObjectToJson(object obj, JSONParameters newjp)
{
return JSON.ToJSON(obj, newjp);
}
/// <summary>
/// 把JSON字符串转换为对象。
/// </summary>
public static object JsonToObject(string json)
{
return JSON.Parse(json);
}
/// <summary>
/// 把JSON解释为API响应对象。
/// </summary>
/// <typeparam name="T">API响应类型</typeparam>
/// <param name="json">JSON字符串</param>
/// <returns>API响应对象</returns>
public static T ParseResponse<T>(string json) where T : TopResponse
{
TopJsonParser<T> parser = new TopJsonParser<T>();
return parser.Parse(json);
}
/// <summary>
/// 获取从1970年1月1日到现在的毫秒总数。
/// </summary>
/// <returns>毫秒数</returns>
public static long GetCurrentTimeMillis()
{
return (long)DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1)).TotalMilliseconds;
}
/// <summary>
/// 获取本机的局域网IP。
/// </summary>
public static string GetIntranetIp()
{
if (intranetIp == null)
{
NetworkInterface[] nis = NetworkInterface.GetAllNetworkInterfaces();
foreach (NetworkInterface ni in nis)
{
if (OperationalStatus.Up == ni.OperationalStatus && (NetworkInterfaceType.Ethernet == ni.NetworkInterfaceType || NetworkInterfaceType.Wireless80211 == ni.NetworkInterfaceType))
{
foreach (UnicastIPAddressInformation info in ni.GetIPProperties().UnicastAddresses)
{
if (AddressFamily.InterNetwork == info.Address.AddressFamily)
{
intranetIp = info.Address.ToString();
break;
}
}
if (intranetIp != null) break;
}
}
}
if (intranetIp == null)
{
intranetIp = "127.0.0.1";
}
return intranetIp;
}
public const string CHARSET_UTF8 = "UTF-8";
public const string SIGN_METHOD_SHA256 = "sha256";
public const string SIGN_METHOD_HMAC_SHA256 = "HmacSHA256";
public static string SignApiRequest(IDictionary<string, string> aparams, string appSecret, string signMethod, string apiName)
{
// 如果是调用原平台迁移方法请将方法名作为请求参数放入params中参与排序
// 第一步:检查参数是否已经排序
string[]
keys = aparams.Keys.ToArray();
Array.Sort(keys);
// 第二步:把所有参数名和参数值串在一起
StringBuilder query = new StringBuilder();
// 如果是调用新平台注册方法,请执行第三步,直接拼接方法名
// 第三步将API名拼接在字符串开头
query.Append(apiName);
foreach (string key in keys)
{
string value = aparams[key];
if (aparams.ContainsKey(key))
{
query.Append(key).Append(value);
}
}
// 第四步:使用加密算法
byte[] bytes = null;
//var ttt = query.ToString();
if (signMethod.Equals(SIGN_METHOD_SHA256))
{
bytes = encryptHMACSHA256(query.ToString(), appSecret);
}
// 第五步:把二进制转化为大写的十六进制(正确签名应该为32大写字符串此方法需要时使用)
return byte2hex(bytes);
}
private static byte[] encryptHMACSHA256(string data, string secret)
{
byte[] bytes = null;
try
{
HMACSHA256 hmac = new HMACSHA256(Encoding.UTF8.GetBytes(secret));
bytes = hmac.ComputeHash(Encoding.UTF8.GetBytes(data));
//SecretKey secretKey = new SecretKeySpec(secret.(CHARSET_UTF8), SIGN_METHOD_HMAC_SHA256);
//Mac mac = Mac.getInstance(hmac.getAlgorithm());
//mac.init(secretKey);
//bytes = Encoding.UTF8.GetBytes(secret);
}
catch (Exception ex)
{
throw;
}
return bytes;
}
/**
* Transfer binary array to HEX string.
*/
public static String byte2hex(byte[] bytes)
{
// 第五步:把二进制转化为大写的十六进制
StringBuilder result = new StringBuilder();
for (int i = 0; i < bytes.Length; i++)
{
result.Append(bytes[i].ToString("X2"));
}
return result.ToString();
}
}
}