/**发布环境 使用发布环境 发布的正式签名KEY**/
|
#define Distribution
|
|
///**测试环境 使用测试环境 使用测试的签名KEY**/
|
//#undef Distribution
|
|
using System;
|
using System.Collections.Generic;
|
using System.Linq;
|
using System.Net;
|
using System.Security.Cryptography;
|
using System.Text;
|
//using HDL_ON.Entity;
|
using RestSharp;
|
using Shared.SimpleControl;
|
|
|
|
namespace Shared
|
{
|
public class HttpUtil
|
{
|
|
#region **********全局常量**********
|
///// <summary>
|
///// API_HTTPS
|
///// </summary>
|
//public const string API_HTTPS = "https://";
|
/// <summary>
|
/// RegionMark
|
/// </summary>
|
public const string RegionMark = "HDL";
|
/// <summary>
|
/// 请求超时时间
|
/// </summary>
|
public const int TIME_OUT = 10;
|
/// <summary>
|
/// 特殊接口请求超时时间
|
/// </summary>
|
public const int TIME_OUT_LONG = 20;
|
/////// <summary>
|
/////// Bearer 暂时设为空,从登陆成功的返回的headerPrefix参数动态获取
|
/////// </summary>
|
//public const string TOKEN_BEARER = "Bearer ";
|
|
#endregion
|
|
#region **********网络请求封装**********
|
|
|
|
|
#if Distribution
|
///**********正式环境**********
|
/// <summary>
|
/// 固定域名,正式环境
|
/// 公共域名就近解析
|
/// </summary>
|
#if DEBUG1
|
public const string GlobalRequestHttpsHost = "https://test-gz.hdlcontrol.com";
|
#else
|
public const string GlobalRequestHttpsHost = "https://bahrain-gateway.hdlcontrol.com";
|
#endif
|
/// <summary>
|
///
|
/// </summary>
|
const string APP_KEY = "HDL-HOME-IND-APP";
|
/// <summary>
|
///
|
/// </summary>
|
const string SECRET_KEY = "yPL345bn68gHnvilG4tYbq3cTYkiHu";
|
|
#else
|
///**********测试环境**********
|
/// <summary>
|
/// 固定域名,测试境
|
/// 公共域名就近解析
|
/// </summary>
|
public const string GlobalRequestHttpsHost = "https://china-gateway.hdlcontrol.com";
|
/// <summary>
|
///
|
/// </summary>
|
const string APP_KEY = "HDL-APP-TENANT";
|
/// <summary>
|
///
|
/// </summary>
|
const string SECRET_KEY = "CeL345bn28gHnvi9G4tYcq3cTYkiiC";
|
#endif
|
|
/// <summary>
|
/// Get 请求服务器方法
|
/// </summary>
|
/// <param name="apiPath"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlSegmentDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static ResponsePackNew RequestHttpsGet (string apiPath, Dictionary<string, object> queryDictionary = null, Dictionary<string, object> urlSegmentDictionary = null, string urlHead = "", string replaceToken = "", int mTimeout = 10)
|
{
|
return RequestHttps (Method.GET, apiPath, null, queryDictionary, urlSegmentDictionary, urlHead, replaceToken, mTimeout);
|
}
|
|
///// <summary>
|
///// 通用 请求服务器方法
|
///// </summary>
|
///// <param name="method">请求类型</param>
|
///// <param name="apiPath"></param>
|
///// <param name="bodyParameterJson"></param>
|
///// <param name="queryDictionary"></param>
|
///// <param name="urlSegmentDictionary"></param>
|
///// <param name="urlHead"></param>
|
///// <param name="mTimeout">请求超时时间,默认10</param>
|
///// <param name="urlHead"></param>
|
///// <returns></returns>
|
//public static ResponsePackNew RequestHttpsBase(Method method, string apiPath, string bodyParameterJson = null, Dictionary<string, object> queryDictionary = null, Dictionary<string, object> urlSegmentDictionary = null, string urlHead = "", string replaceToken = "", int mTimeout = 10, bool needErrorTip = true)
|
//{
|
// var mResponsePackNew = RequestHttps(method, apiPath, bodyParameterJson, queryDictionary, urlSegmentDictionary, urlHead, replaceToken, mTimeout);
|
// if (needErrorTip)
|
// {
|
// if (mResponsePackNew.Code.ToUpper() != SUCCESS_CODE)
|
// {
|
// IMessageCommon.Current.ShowErrorInfoAlter(apiPath, mResponsePackNew.Code);
|
// }
|
// }
|
// return mResponsePackNew;
|
//}
|
|
/// <summary>
|
/// POST请求方法 body参数
|
/// 针对住宅相关接口封装
|
/// 调用住宅当前所在区域域名
|
/// 如果是分享住宅,使用主人的token进行相关操作
|
/// </summary>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterJson"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static ResponsePackNew RequestHttpsPostFroHome (string apiPath, string bodyParameterJson, int mTimeout = 10)
|
{
|
//string urlHead2 = UserConfig.Instance.CurrentRegion.regionUrl;
|
string urlHead = GlobalRequestHttpsHost;
|
//var replaceToken = "";
|
//if (DB_ResidenceData.residenceData.residecenInfo.IsOthreShare)
|
//{
|
// replaceToken = DB_ResidenceData.residenceData.MasterToken;
|
//}
|
return RequestHttps (Method.POST, apiPath, bodyParameterJson, null, null, urlHead, "", mTimeout);
|
}
|
|
/// <summary>
|
/// POST请求方法 body参数
|
/// </summary>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterJson"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="needErrorTip"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static ResponsePackNew RequestHttpsPost (string apiPath, string bodyParameterJson, string urlHead = "", string replaceToken = "", int mTimeout = 10)
|
{
|
return RequestHttps (Method.POST, apiPath, bodyParameterJson, null, null, urlHead, replaceToken, mTimeout);
|
}
|
|
/// <summary>
|
/// POST请求方法 queryDictionary
|
/// </summary>
|
/// <param name="apiPath"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="needErrorTip"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static ResponsePackNew RequestHttpsPost (string apiPath, Dictionary<string, object> queryDictionary, string urlHead = "", string replaceToken = "", int mTimeout = 10)
|
{
|
return RequestHttps (Method.POST, apiPath, null, queryDictionary, null, urlHead, replaceToken, mTimeout);
|
}
|
|
/// <summary>
|
/// 通用 请求服务器方法
|
/// </summary>
|
/// <param name="method"></param>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterJson"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlSegmentDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
static ResponsePackNew RequestHttpsBase (Method method, string apiPath, string bodyParameterJson = null, Dictionary<string, object> queryDictionary = null, Dictionary<string, object> urlSegmentDictionary = null, string urlHead = "", string replaceToken = "", int mTimeout = 10)
|
{
|
#region HttpWebRequest
|
try {
|
|
if (string.IsNullOrEmpty (urlHead)) {
|
urlHead = GlobalRequestHttpsHost;
|
}
|
string requestFullUrl = urlHead + apiPath;
|
|
|
////**************测试**************
|
//string requestFullUrl = GlobalRequestHttpsHost + apiPath;
|
////**************测试**************
|
|
RestClient client = new RestClient (requestFullUrl);
|
|
RestRequest request = new RestRequest (method);
|
request.Timeout = mTimeout * 1000;
|
request.AddHeader ("content-type", "application/json");
|
|
if (string.IsNullOrEmpty (replaceToken)) {
|
if (MainPage.LoginUser != null) {/* 如果不需要验证Token可以不用传入 */
|
request.AddHeader ("Authorization", MainPage.LoginUser.LoginTokenString);
|
}
|
} else {
|
request.AddHeader ("Authorization", replaceToken);
|
}
|
|
if (bodyParameterJson != null) {
|
request.AddParameter ("application/json", bodyParameterJson, ParameterType.RequestBody);
|
}
|
|
if (queryDictionary != null) {
|
foreach (var data in queryDictionary) {
|
request.AddQueryParameter (data.Key, data.Value.ToString ());
|
}
|
}
|
|
if (urlSegmentDictionary != null) {
|
foreach (var data in urlSegmentDictionary) {
|
request.AddUrlSegment (data.Key, data.Value.ToString ());
|
}
|
}
|
|
IRestResponse response = client.Execute (request);
|
if (response.StatusCode == HttpStatusCode.OK) {
|
try {
|
ResponsePackNew revertObj = new ResponsePackNew () { };
|
revertObj = Newtonsoft.Json.JsonConvert.DeserializeObject<ResponsePackNew> (response.Content);
|
//*****一些判空处理*****************
|
if (revertObj.Code == null) {
|
revertObj.Code = StateCode.DATA_EXCEPTION;
|
}
|
|
if (revertObj.Data == null) {
|
revertObj.Data = "";
|
}
|
//*****一些判空处理*****************
|
|
return revertObj;
|
} catch (Exception ex) {
|
Utlis.WriteLine (ex.Message);
|
return new ResponsePackNew () { Code = StateCode.DATA_EXCEPTION };
|
}
|
} else {
|
Utlis.WriteLine (response.Content);
|
return new ResponsePackNew () { Code = StateCode.NETWORK_ERROR };
|
}
|
|
} catch (Exception ex) {
|
Utlis.WriteLine (ex.Message);
|
return new ResponsePackNew () { Code = StateCode.NETWORK_ERROR };
|
}
|
|
#endregion
|
|
}
|
|
/// <summary>
|
/// 通用 请求服务器方法
|
/// 增加token过期处理
|
/// </summary>
|
/// <param name="method"></param>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterJson"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlSegmentDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static ResponsePackNew RequestHttps (Method method, string apiPath, string bodyParameterJson = null, Dictionary<string, object> queryDictionary = null, Dictionary<string, object> urlSegmentDictionary = null, string urlHead = "", string replaceToken = "", int mTimeout = 10)
|
{
|
var responsePackNew = RequestHttpsBase (method, apiPath, bodyParameterJson, queryDictionary, urlSegmentDictionary, urlHead, replaceToken, mTimeout);
|
//*****************Token过期处理*****************
|
if (responsePackNew.Code == StateCode.TOKEN_EXPIRED) {
|
//刷新Token
|
if (RefreshToken ()) {
|
return RequestHttpsBase (method, apiPath, bodyParameterJson, queryDictionary, urlSegmentDictionary, urlHead, replaceToken, mTimeout);
|
} else {
|
return responsePackNew;
|
}
|
}
|
//*****************Token过期处理*****************
|
return responsePackNew;
|
}
|
|
|
/// <summary>
|
/// 刷新Token
|
/// </summary>
|
/// <returns></returns>
|
static bool RefreshToken ()
|
{
|
try {
|
var requestJson = GetSignRequestJson (new RefreshTokenObj () {
|
refreshToken = MainPage.LoginUser.RefreshToken,
|
});
|
var revertObj = RequestHttpsBase (Method.POST, NewAPI.API_POST_Login, requestJson);
|
if (revertObj.Code == StateCode.SUCCESS) {
|
var revertData = Newtonsoft.Json.JsonConvert.DeserializeObject<UserLoginRes> (revertObj.Data.ToString ());
|
MainPage.LoginUser.LoginTokenString = revertData.headerPrefix + revertData.accessToken;
|
MainPage.LoginUser.RefreshToken = revertData.refreshToken;
|
MainPage.LoginUser.LastTime = DateTime.Now;
|
MainPage.LoginUser.SaveUserInfo ();
|
return true;
|
}
|
return false;
|
} catch {
|
return false;
|
}
|
}
|
|
/// <summary>
|
/// 下载文件 请求服务器方法
|
/// </summary>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterJson"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static byte [] RequestHttpsDownload (string apiPath, string bodyParameterJson = null, Dictionary<string, object> queryDictionary = null, string urlHead = "", string replaceToken = "", int mTimeout = 20)
|
{
|
#region RestRequest
|
try {
|
if (string.IsNullOrEmpty (urlHead)) {
|
urlHead = GlobalRequestHttpsHost;
|
}
|
string requestFullUrl = urlHead + apiPath;
|
|
////**************测试**************
|
//string requestFullUrl = GlobalRequestHttpsHost + apiPath;
|
////**************测试**************
|
|
RestClient client = new RestClient (requestFullUrl);
|
RestRequest request = new RestRequest (Method.POST);
|
request.Timeout = mTimeout * 1000;
|
request.AddHeader ("content-type", "application/json");
|
|
if (string.IsNullOrEmpty (replaceToken)) {
|
if (MainPage.LoginUser != null) {/* 如果不需要验证Token可以不用传入 */
|
request.AddHeader ("Authorization", MainPage.LoginUser.LoginTokenString);
|
}
|
} else {
|
request.AddHeader ("Authorization", replaceToken);
|
}
|
|
if (bodyParameterJson != null) {
|
request.AddParameter ("application/json", bodyParameterJson, ParameterType.RequestBody);
|
}
|
|
if (queryDictionary != null) {
|
foreach (var data in queryDictionary) {
|
request.AddQueryParameter (data.Key, data.Value.ToString ());
|
}
|
}
|
|
IRestResponse response = client.Execute (request);
|
return response.RawBytes;
|
} catch (Exception ex) {
|
Utlis.WriteLine (ex.Message);
|
return null;
|
}
|
#endregion
|
|
}
|
|
/// <summary>
|
/// 上传 请求服务器方法
|
/// </summary>
|
/// <param name="method"></param>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterObject"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlSegmentDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static ResponsePackNew RequestHttpsUpload (Method method, string apiPath, object bodyParameterObject = null, Dictionary<string, object> queryDictionary = null, Dictionary<string, object> urlSegmentDictionary = null, string urlHead = "", string replaceToken = "", int mTimeout = 20)
|
{
|
#region HttpWebRequest
|
try {
|
|
if (string.IsNullOrEmpty (urlHead)) {
|
urlHead = GlobalRequestHttpsHost;
|
}
|
string requestFullUrl = urlHead + apiPath;
|
|
////**************测试**************
|
//string requestFullUrl = GlobalRequestHttpsHost + apiPath;
|
////**************测试**************
|
|
RestClient client = new RestClient (requestFullUrl);
|
RestRequest request = new RestRequest (method);
|
request.Timeout = mTimeout * 1000;
|
//request.AddHeader ("content-type", "application/json");
|
request.AddHeader ("content-type", "application/octet-stream");
|
|
if (string.IsNullOrEmpty (replaceToken)) {
|
if (MainPage.LoginUser != null) {/* 如果不需要验证Token可以不用传入 */
|
request.AddHeader ("Authorization", MainPage.LoginUser.LoginTokenString);
|
}
|
} else {
|
request.AddHeader ("Authorization", replaceToken);
|
}
|
|
if (bodyParameterObject != null) {
|
request.AddParameter ("application/octet-stream", bodyParameterObject, ParameterType.RequestBody);
|
}
|
|
if (queryDictionary != null) {
|
foreach (var data in queryDictionary) {
|
request.AddQueryParameter (data.Key, data.Value.ToString ());
|
}
|
}
|
|
if (urlSegmentDictionary != null) {
|
foreach (var data in urlSegmentDictionary) {
|
request.AddUrlSegment (data.Key, data.Value.ToString ());
|
}
|
}
|
|
IRestResponse response = client.Execute (request);
|
if (response.StatusCode == HttpStatusCode.OK) {
|
try {
|
ResponsePackNew revertObj = new ResponsePackNew () { };
|
revertObj = Newtonsoft.Json.JsonConvert.DeserializeObject<ResponsePackNew> (response.Content);
|
if (revertObj.Code == null) {
|
revertObj.Code = StateCode.DATA_EXCEPTION;
|
}
|
////统一转成大写
|
//revertObj.StateCode = revertObj.StateCode.ToUpper ();
|
return revertObj;
|
} catch (Exception ex) {
|
Utlis.WriteLine (ex.Message);
|
return new ResponsePackNew () { Code = StateCode.DATA_EXCEPTION };
|
}
|
} else {
|
Utlis.WriteLine (response.Content);
|
return new ResponsePackNew () { Code = StateCode.NETWORK_ERROR };
|
}
|
|
} catch (Exception ex) {
|
Utlis.WriteLine (ex.Message);
|
return new ResponsePackNew () { Code = StateCode.NETWORK_ERROR };
|
}
|
|
#endregion
|
|
}
|
|
/// <summary>
|
/// 下载文件 请求服务器方法
|
/// </summary>
|
/// <param name="apiPath"></param>
|
/// <param name="bodyParameterJson"></param>
|
/// <param name="queryDictionary"></param>
|
/// <param name="urlHead"></param>
|
/// <param name="replaceToken"></param>
|
/// <param name="mTimeout"></param>
|
/// <returns></returns>
|
public static byte [] HttpsDownload (string requestFullUrl, int mTimeout = 30)
|
{
|
#region RestRequest
|
try {
|
RestClient client = new RestClient (requestFullUrl);
|
RestRequest request = new RestRequest (Method.GET);
|
request.Timeout = mTimeout * 1000;
|
|
IRestResponse response = client.Execute (request);
|
return response.RawBytes;
|
} catch (Exception ex) {
|
Utlis.WriteLine (ex.Message);
|
return null;
|
}
|
#endregion
|
|
}
|
|
#endregion
|
|
#region **********签名校验**********
|
///// <summary>
|
/////
|
///// </summary>
|
//const string APP_KEY = "HDL-HOME-APP-TEST";
|
///// <summary>
|
/////
|
///// </summary>
|
//const string SECRET_KEY = "WeJ8TY88vbakCcnvH8G1tDUqzLWY8yss";
|
|
|
|
/// <summary>
|
/// 获取当前时间戳值
|
/// </summary>
|
/// <returns></returns>
|
static string GetTimestamp ()
|
{
|
System.DateTime startTime = TimeZone.CurrentTimeZone.ToLocalTime (new System.DateTime (1970, 1, 1)); // 当地时区
|
return ((long)(DateTime.Now - startTime).TotalMilliseconds).ToString (); // 相差秒数
|
//return ((long)(DateTime.Now - startTime).TotalSeconds).ToString(); // 相差秒数
|
}
|
|
/// <summary>
|
///
|
/// </summary>
|
/// <param name="signstr"></param>
|
/// <returns></returns>
|
static string SignMD5Encrypt (string s)
|
{
|
byte [] sign = MD5.Create ().ComputeHash (UTF8Encoding.UTF8.GetBytes (s));
|
string signstr = string.Empty;
|
foreach (byte item in sign) {
|
signstr += item.ToString ("X2");
|
}
|
return signstr.ToLower ();
|
}
|
|
/// <summary>
|
/// 判断当前值是否需要参与签名,保持跟云端一致
|
/// 空字符串不参与
|
/// 数组,集合,对象不参与
|
/// </summary>
|
/// <param name="valueStr"></param>
|
/// <returns></returns>
|
static bool IfValueNeedSign (string valueStr)
|
{
|
if (string.IsNullOrEmpty (valueStr) || valueStr.StartsWith ("{") || valueStr.StartsWith ("[")) {
|
return false;
|
}
|
return true;
|
}
|
|
/// <summary>
|
/// 2020-11-02
|
/// 基础服务的接口都要校验sign
|
/// 计算sign签名
|
/// </summary>
|
/// <returns></returns>
|
public static string GetSignRequestJson (object requestObj)
|
{
|
try {
|
//1. 将model实体转为Dictionary<string, object>
|
var paramDictionary = Newtonsoft.Json.JsonConvert.DeserializeObject<Dictionary<string, object>> (Newtonsoft.Json.JsonConvert.SerializeObject (requestObj));
|
//2. 计算sign
|
if (paramDictionary != null) {
|
paramDictionary.Add ("appKey", APP_KEY);
|
paramDictionary.Add ("timestamp", GetTimestamp ());
|
//2.1 字典升序
|
paramDictionary = paramDictionary.OrderBy (o => o.Key).ToDictionary (o => o.Key, p => p.Value);
|
//2.2 拼接按URL键值对
|
string str = string.Empty;
|
foreach (KeyValuePair<string, object> item in paramDictionary) {
|
//Value为null不参加校验
|
if (item.Value != null) {
|
//检测当前参数是否需要参与校验
|
if (IfValueNeedSign (item.Value.ToString ())) {
|
//如果是bool类型,要转小写
|
if (item.Value is bool) {
|
str += item.Key + "=" + item.Value.ToString ().ToLower () + "&";
|
} else {
|
str += item.Key + "=" + item.Value.ToString () + "&";
|
}
|
}
|
}
|
}
|
|
//2.3 拼接SECRET_KEY
|
str = str.Substring (0, str.Length - 1) + SECRET_KEY;
|
//2.4 MD5转换+转小写
|
var signstr = SignMD5Encrypt (str);
|
paramDictionary.Add ("sign", signstr);
|
var signResult = Newtonsoft.Json.JsonConvert.SerializeObject (paramDictionary);
|
return signResult;
|
} else {
|
return "";
|
}
|
} catch {
|
return "";
|
}
|
}
|
|
#endregion
|
}
|
|
/// <summary>
|
/// 响应参数
|
/// </summary>
|
[Serializable]
|
public class ResponsePackNew
|
{
|
/// <summary>
|
/// 响应状态码
|
/// </summary>
|
public string Code;
|
|
/// <summary>
|
/// 响应内容
|
/// </summary>
|
public object Data;
|
|
/// <summary>
|
/// 响应错误信息
|
/// </summary>
|
public string message;
|
|
/// <summary>
|
/// 这个是请求错误时的扩展数据,以后所有的附带扩展数据都会放在这里面动态维护
|
/// </summary>
|
public object extra;
|
|
///// <summary>
|
///// isSuccess
|
///// </summary>
|
//public bool isSuccess;
|
|
///// <summary>
|
///// timestamp
|
///// </summary>
|
//public string timestamp;
|
|
|
}
|
|
}
|