1
This commit is contained in:
255
00.SDK/E_ZKEccTopSdk/Uitl/FileItem.cs
Normal file
255
00.SDK/E_ZKEccTopSdk/Uitl/FileItem.cs
Normal file
@@ -0,0 +1,255 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
|
||||
namespace E_ZKEccTopSdk.Uitl
|
||||
{
|
||||
/// <summary>
|
||||
/// 文件元数据。
|
||||
/// 可以使用以下几种构造方法:
|
||||
/// 本地路径:new FileItem("C:/temp.jpg");
|
||||
/// 本地文件:new FileItem(new FileInfo("C:/temp.jpg"));
|
||||
/// 字节数组:new FileItem("abc.jpg", bytes);
|
||||
/// 输入流:new FileItem("abc.jpg", stream);
|
||||
/// </summary>
|
||||
public class FileItem
|
||||
{
|
||||
private Contract contract;
|
||||
|
||||
/// <summary>
|
||||
/// 基于本地文件的构造器。
|
||||
/// </summary>
|
||||
/// <param name="fileInfo">本地文件</param>
|
||||
public FileItem(FileInfo fileInfo)
|
||||
{
|
||||
this.contract = new LocalContract(fileInfo);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 基于本地文件全路径的构造器。
|
||||
/// </summary>
|
||||
/// <param name="filePath">本地文件全路径</param>
|
||||
public FileItem(string filePath) : this(new FileInfo(filePath))
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 基于文件名和字节数组的构造器。
|
||||
/// </summary>
|
||||
/// <param name="fileName">文件名称(服务端持久化字节数组到磁盘时的文件名)</param>
|
||||
/// <param name="content">文件字节数组</param>
|
||||
public FileItem(string fileName, byte[] content) : this(fileName, content, null)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 基于文件名、字节数组和媒体类型的构造器。
|
||||
/// </summary>
|
||||
/// <param name="fileName">文件名(服务端持久化字节数组到磁盘时的文件名)</param>
|
||||
/// <param name="content">文件字字节数组</param>
|
||||
/// <param name="mimeType">媒体类型</param>
|
||||
public FileItem(string fileName, byte[] content, string mimeType)
|
||||
{
|
||||
this.contract = new ByteArrayContract(fileName, content, mimeType);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 基于文件名和输入流的构造器。
|
||||
/// </summary>
|
||||
/// <param name="fileName">文件名称(服务端持久化输入流到磁盘时的文件名)</param>
|
||||
/// <param name="content">文件输入流</param>
|
||||
public FileItem(string fileName, Stream stream) : this(fileName, stream, null)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 基于文件名、输入流和媒体类型的构造器。
|
||||
/// </summary>
|
||||
/// <param name="fileName">文件名(服务端持久化输入流到磁盘时的文件名)</param>
|
||||
/// <param name="content">文件输入流</param>
|
||||
/// <param name="mimeType">媒体类型</param>
|
||||
public FileItem(string fileName, Stream stream, string mimeType)
|
||||
{
|
||||
this.contract = new StreamContract(fileName, stream, mimeType);
|
||||
}
|
||||
|
||||
public bool IsValid()
|
||||
{
|
||||
return this.contract.IsValid();
|
||||
}
|
||||
|
||||
public long GetFileLength()
|
||||
{
|
||||
return this.contract.GetFileLength();
|
||||
}
|
||||
|
||||
public string GetFileName()
|
||||
{
|
||||
return this.contract.GetFileName();
|
||||
}
|
||||
|
||||
public string GetMimeType()
|
||||
{
|
||||
return this.contract.GetMimeType();
|
||||
}
|
||||
|
||||
public void Write(Stream output)
|
||||
{
|
||||
this.contract.Write(output);
|
||||
}
|
||||
}
|
||||
|
||||
internal interface Contract
|
||||
{
|
||||
bool IsValid();
|
||||
string GetFileName();
|
||||
string GetMimeType();
|
||||
long GetFileLength();
|
||||
void Write(Stream output);
|
||||
}
|
||||
|
||||
internal class LocalContract : Contract
|
||||
{
|
||||
private FileInfo fileInfo;
|
||||
|
||||
public LocalContract(FileInfo fileInfo)
|
||||
{
|
||||
this.fileInfo = fileInfo;
|
||||
}
|
||||
|
||||
public long GetFileLength()
|
||||
{
|
||||
return this.fileInfo.Length;
|
||||
}
|
||||
|
||||
public string GetFileName()
|
||||
{
|
||||
return this.fileInfo.Name;
|
||||
}
|
||||
|
||||
public string GetMimeType()
|
||||
{
|
||||
return Constants.CTYPE_DEFAULT;
|
||||
}
|
||||
|
||||
public bool IsValid()
|
||||
{
|
||||
return this.fileInfo != null && this.fileInfo.Exists;
|
||||
}
|
||||
|
||||
public void Write(Stream output)
|
||||
{
|
||||
using (BufferedStream bfs = new BufferedStream(this.fileInfo.OpenRead()))
|
||||
{
|
||||
int n = 0;
|
||||
byte[] buffer = new byte[Constants.READ_BUFFER_SIZE];
|
||||
while ((n = bfs.Read(buffer, 0, buffer.Length)) > 0)
|
||||
{
|
||||
output.Write(buffer, 0, n);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
internal class ByteArrayContract : Contract
|
||||
{
|
||||
private string fileName;
|
||||
private byte[] content;
|
||||
private string mimeType;
|
||||
|
||||
public ByteArrayContract(string fileName, byte[] content, string mimeType)
|
||||
{
|
||||
this.fileName = fileName;
|
||||
this.content = content;
|
||||
this.mimeType = mimeType;
|
||||
}
|
||||
|
||||
public bool IsValid()
|
||||
{
|
||||
return this.content != null && this.fileName != null;
|
||||
}
|
||||
|
||||
public long GetFileLength()
|
||||
{
|
||||
return this.content.Length;
|
||||
}
|
||||
|
||||
public string GetFileName()
|
||||
{
|
||||
return this.fileName;
|
||||
}
|
||||
|
||||
public string GetMimeType()
|
||||
{
|
||||
if (string.IsNullOrEmpty(this.mimeType))
|
||||
{
|
||||
return Constants.CTYPE_DEFAULT;
|
||||
}
|
||||
else
|
||||
{
|
||||
return this.mimeType;
|
||||
}
|
||||
}
|
||||
|
||||
public void Write(Stream output)
|
||||
{
|
||||
output.Write(this.content, 0, this.content.Length);
|
||||
}
|
||||
}
|
||||
|
||||
internal class StreamContract : Contract
|
||||
{
|
||||
private string fileName;
|
||||
private Stream stream;
|
||||
private string mimeType;
|
||||
|
||||
public StreamContract(string fileName, Stream stream, string mimeType)
|
||||
{
|
||||
this.fileName = fileName;
|
||||
this.stream = stream;
|
||||
this.mimeType = mimeType;
|
||||
}
|
||||
|
||||
public long GetFileLength()
|
||||
{
|
||||
return 0L;
|
||||
}
|
||||
|
||||
public string GetFileName()
|
||||
{
|
||||
return this.fileName;
|
||||
}
|
||||
|
||||
public string GetMimeType()
|
||||
{
|
||||
if (string.IsNullOrEmpty(mimeType))
|
||||
{
|
||||
return Constants.CTYPE_DEFAULT;
|
||||
}
|
||||
else
|
||||
{
|
||||
return this.mimeType;
|
||||
}
|
||||
}
|
||||
|
||||
public bool IsValid()
|
||||
{
|
||||
return this.stream != null && this.fileName != null;
|
||||
}
|
||||
|
||||
public void Write(Stream output)
|
||||
{
|
||||
using (this.stream)
|
||||
{
|
||||
int n = 0;
|
||||
byte[] buffer = new byte[Constants.READ_BUFFER_SIZE];
|
||||
while ((n = this.stream.Read(buffer, 0, buffer.Length)) > 0)
|
||||
{
|
||||
output.Write(buffer, 0, n);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
200
00.SDK/E_ZKEccTopSdk/Uitl/RequestValidator.cs
Normal file
200
00.SDK/E_ZKEccTopSdk/Uitl/RequestValidator.cs
Normal file
@@ -0,0 +1,200 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
|
||||
namespace E_ZKEccTopSdk.Uitl
|
||||
{
|
||||
/// <summary>
|
||||
/// 请求验证器
|
||||
/// </summary>
|
||||
public sealed class RequestValidator
|
||||
{
|
||||
private const string ERR_CODE_PARAM_MISSING = "40";
|
||||
private const string ERR_CODE_PARAM_INVALID = "41";
|
||||
private const string ERR_MSG_PARAM_MISSING = "client-error:Missing required arguments:{0}";
|
||||
private const string ERR_MSG_PARAM_INVALID = "client-error:Invalid arguments:{0}";
|
||||
|
||||
/// <summary>
|
||||
/// 验证参数是否为空。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
public static void ValidateRequired(string name, object value)
|
||||
{
|
||||
if (value == null)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_MISSING, string.Format(ERR_MSG_PARAM_MISSING, name));
|
||||
}
|
||||
else
|
||||
{
|
||||
if (value.GetType() == typeof(string))
|
||||
{
|
||||
string strValue = value as string;
|
||||
if (string.IsNullOrEmpty(strValue))
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_MISSING, string.Format(ERR_MSG_PARAM_MISSING, name));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证字符串参数的最大长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxLength">最大长度</param>
|
||||
public static void ValidateMaxLength(string name, string value, int maxLength)
|
||||
{
|
||||
if (value != null && value.Length > maxLength)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证上传文件的最大字节长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxLength">最大长度</param>
|
||||
public static void ValidateMaxLength(string name, FileItem value, int maxLength)
|
||||
{
|
||||
if (value != null && value.GetFileLength() > maxLength)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证以逗号分隔的字符串参数的最大列表长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxSize">最大列表长度</param>
|
||||
public static void ValidateMaxListSize(string name, string value, int maxSize)
|
||||
{
|
||||
if (value != null)
|
||||
{
|
||||
string[] data = value.Split(',');
|
||||
if (data != null && data.Length > maxSize)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证以逗号分隔的字符串参数的最大列表长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxSize">最大列表长度</param>
|
||||
public static void ValidateMaxListSize(string name, List<string> value, int maxSize)
|
||||
{
|
||||
if (value != null)
|
||||
{
|
||||
if (value != null && value.Count > maxSize)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, ERR_MSG_PARAM_INVALID);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证以逗号分隔的字符串参数的最大列表长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxSize">最大列表长度</param>
|
||||
public static void ValidateMaxListSize(string name, List<long> value, int maxSize)
|
||||
{
|
||||
if (value != null)
|
||||
{
|
||||
if (value != null && value.Count > maxSize)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, ERR_MSG_PARAM_INVALID);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证以逗号分隔的字符串参数的最大列表长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxSize">最大列表长度</param>
|
||||
public static void ValidateMaxListSize(string name, List<bool> value, int maxSize)
|
||||
{
|
||||
if (value != null)
|
||||
{
|
||||
if (value != null && value.Count > maxSize)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, ERR_MSG_PARAM_INVALID);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证复杂结构数组参数的最大列表长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxSize">最大列表长度</param>
|
||||
public static void ValidateObjectMaxListSize(string name, string value, int maxSize)
|
||||
{
|
||||
if (value != null)
|
||||
{
|
||||
IList list = JSON.Parse(value) as IList;
|
||||
if (list != null && list.Count > maxSize)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证字符串参数的最小长度。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="minLength">最小长度</param>
|
||||
public static void ValidateMinLength(string name, string value, int minLength)
|
||||
{
|
||||
if (value != null && value.Length < minLength)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证数字参数的最大值。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="maxValue">最大值</param>
|
||||
public static void ValidateMaxValue(string name, Nullable<long> value, long maxValue)
|
||||
{
|
||||
if (value != null && value > maxValue)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 验证数字参数的最小值。
|
||||
/// </summary>
|
||||
/// <param name="name">参数名</param>
|
||||
/// <param name="value">参数值</param>
|
||||
/// <param name="minValue">最小值</param>
|
||||
public static void ValidateMinValue(string name, Nullable<long> value, long minValue)
|
||||
{
|
||||
if (value != null && value < minValue)
|
||||
{
|
||||
throw new TopException(ERR_CODE_PARAM_INVALID, string.Format(ERR_MSG_PARAM_INVALID, name));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
271
00.SDK/E_ZKEccTopSdk/Uitl/TopUtils.cs
Normal file
271
00.SDK/E_ZKEccTopSdk/Uitl/TopUtils.cs
Normal file
@@ -0,0 +1,271 @@
|
||||
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();
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user