using Binance.TradeRobot.Common.Extensions; using Newtonsoft.Json; using System; using System.Collections.Generic; using System.Net.Http; using System.Text; namespace Binance.TradeRobot.Common.Http { public class RestApiService { public const string ContentType_Json = "application/json"; public const string ContentType_Form = "application/x-www-form-urlencoded"; public TimeSpan TimeOut { get; set; } = new TimeSpan(0, 0, 20); private IHttpClientFactory httpClientFactory; public RestApiService(IHttpClientFactory httpClientFactory) { this.httpClientFactory = httpClientFactory; } /// /// 发送请求 /// /// /// /// /// /// /// /// /// /// public string SendRequest(string apiHost, string apiPath, object param, IDictionary headers, HttpMethod httpMethod, string contentType = ContentType_Json, ParamPosition paramPosition = ParamPosition.Body, bool enableRandomTimeStamp = false) { //Get和Delete强制使用QueryString形式传参 if (httpMethod == HttpMethod.Get || httpMethod == HttpMethod.Delete) paramPosition = ParamPosition.Query; //拼接Url var url = $"{apiHost}{(apiHost.EndsWith("/") ? string.Empty : "/")}{(apiPath.StartsWith("/") ? apiPath.Substring(1) : apiPath)}"; var isCombineParam = false; if (paramPosition == ParamPosition.Query && param != null) { url = $"{url}{(param.ToString().StartsWith("?") ? string.Empty : "?")}{param}"; isCombineParam = true; } //使用时间戳绕过CDN if (enableRandomTimeStamp) url = $"{url}{(isCombineParam ? "&" : "?")}t={DateTime.Now.DateTimeToStamp()}"; using (var httpClient = httpClientFactory.CreateClient()) { httpClient.Timeout = TimeOut; using (var request = new HttpRequestMessage(httpMethod, url)) { if (headers != null && headers.Count > 0) foreach (var key in headers.Keys) request.Headers.Add(key, headers[key]); if (paramPosition == ParamPosition.Body && param != null) request.Content = new StringContent(contentType == ContentType_Json ? JsonConvert.SerializeObject(param) : param.ToString(), Encoding.UTF8, contentType); using (var response = httpClient.SendAsync(request).Result) { if (!response.IsSuccessStatusCode) throw new Exception($"HttpCode {response.StatusCode}"); return response.Content.ReadAsStringAsync().Result; } } } } } /// /// 参数传递位置 /// public enum ParamPosition { Query, Body } }