You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

216 lines
7.1 KiB
C#

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using System;
using System.Collections.Generic;
using System.Security.Cryptography;
using System.Text;
using System.Data;
using System.Collections;
using JwKdsV.Entity.Common;
using JwKdsV.Core.HttpApi;
using JwKdsV.Core.LoadBalance;
namespace JwKdsV.Core.Utils
{
public class OpenApiUtils
{
static NLog.Logger logger = NLog.LogManager.GetCurrentClassLogger();
private static object _lock = new object();
private static OpenApiUtils _instance = null;
private Dictionary<string, Apis> _apis;
private Dictionary<string, List<OpenApi>> _urls;
public static OpenApiUtils Instance
{
get
{
if (_instance == null)
{
lock (_lock)
{
_instance = new OpenApiUtils();
_instance.Init();
}
}
return _instance;
}
}
private void Init()
{
this._apis = new Dictionary<string, Apis>();
this._urls = new Dictionary<string, List<OpenApi>>();
Tuple<List<Apis>, List<Urls>> result = null;
using(var db = Global.Instance.OpenDataBase)
{
result = db.FetchMultiple<Apis, Urls>(SqlConstant.ApisQueryAll + SqlConstant.UrlsQueryAll);
}
if(result != null)
{
var apis = result.Item1;
var urls = result.Item2;
foreach(var api in apis)
{
_apis[api.ApiType] = api;
var serverList = urls.FindAll(x => x.ApiType == api.ApiType);
if(serverList != null && serverList.Count > 0)
{
List<OpenApi> list = new List<OpenApi>();
foreach (var server in serverList)
{
OpenApi openApi = new OpenApi();
openApi.ApiType = (ApiType)Enum.Parse(typeof(ApiType), server.ApiType);
openApi.AppKey = api.AppKey;
openApi.AppSecret = api.AppSecret;
openApi.Url = string.Format("{0}://{1}/{2}/api", server.Protocol, server.Url, server.ContextPath);
openApi.Open = string.Format("{0}://{1}/{2}/open/api/extend", server.Protocol, server.Url, server.ContextPath);
openApi.Client = api.Client;
openApi.Locale = api.Locale;
openApi.Version = api.Version;
openApi.Format = api.Format;
openApi.Memo = server.Memo;
list.Add(openApi);
}
this._urls[api.ApiType] = list;
}
}
}
}
public OpenApi NextApi(ApiType api)
{
IRouting<OpenApi> routing = null;
string balance = this._apis[api.ToString()].Routing + "";
switch (balance)
{
case "0"://随机
routing = new RandomRouting<OpenApi>();
break;
case "1"://轮询
routing = new RoundRobinRouting<OpenApi>(this._urls.Values.Count);
break;
case "2"://一致性Hash
routing = new ConsistentHashRouting<OpenApi>(this._urls.Values.Count);
break;
default:
routing = new RandomRouting<OpenApi>();
break;
}
var apis = routing.select("juweiyun.cn", this._urls[api.ToString()].ToArray());
return apis;
}
public void Refresh()
{
lock (_lock)
{
//Global.Instance.ReloadConfig(ConfigConstant.CONFIG_GROUP_SYSTEM);
Init();
}
}
/// <summary>
/// 获取当前时间戳兼容Java服务端
/// </summary>
/// <returns></returns>
public string GetTimestamp()
{
TimeSpan ts = new TimeSpan(DateTime.UtcNow.Ticks - new DateTime(1970, 1, 1, 0, 0, 0).Ticks);
return Convert.ToString((long)ts.TotalMilliseconds);
}
public SortedList<string, string> NewParameters(OpenApi api)
{
SortedList<string, string> parameters = new SortedList<string, string>();
parameters.Add("appKey", api.AppKey);
parameters.Add("format", api.Format);
parameters.Add("locale", api.Locale);
parameters.Add("timestamp", GetTimestamp());
parameters.Add("client", api.Client);
parameters.Add("v", api.Version);
//parameters.Add("tenantId", api.TenantId);
//if (null != Global.Instance.Worker)
//{
// parameters.Add("sessionId", Global.Instance.Worker.SessionId);
//}
return parameters;
}
/// <summary>
/// 开放平台签名算法
/// </summary>
/// <param name="parameters"></param>
/// <returns></returns>
public string Sign(OpenApi api, SortedList<string, string> parameters)
{
return Sign(api, parameters, null);
}
/// <summary>
/// 开放平台签名算法
/// </summary>
/// <param name="parameters"></param>
/// <returns></returns>
public string Sign(OpenApi api, SortedList<string, string> parameters, List<string> ignoreParameters)
{
IList<string> keys = parameters.Keys;
var paramNames = new List<string>(keys.Count);
paramNames.AddRange(keys);
if (ignoreParameters != null && ignoreParameters.Count > 0)
{
foreach (string ignore in ignoreParameters)
{
paramNames.Remove(ignore);
}
}
StringBuilder input = new StringBuilder();
input.Append(api.AppSecret);
foreach (string key in paramNames)
{
input.Append(key + parameters[key]);
}
input.Append(api.AppSecret);
SHA1 sha1 = new SHA1CryptoServiceProvider();//建立一个SHA1
byte[] source = Encoding.UTF8.GetBytes(input.ToString());//将字符串转为Byte[]
byte[] crypto = sha1.ComputeHash(source);//进行SHA1加密
return ByteArrayToHexString(crypto);//把加密后的字符串从Byte[]转为字符串
}
/// <summary>
/// 字节数组转十六进制字符串
/// </summary>
/// <param name="data"></param>
/// <returns></returns>
public string ByteArrayToHexString(byte[] data)
{
StringBuilder sb = new StringBuilder(data.Length * 3);
foreach (byte b in data)
{
sb.Append(Convert.ToString(b, 16).PadLeft(2, '0'));
}
return sb.ToString().ToUpper();
}
}
}