using Hotline.Share.Dtos.Snapshot;
using Hotline.Share.Tools;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Newtonsoft.Json.Serialization;
using Renci.SshNet;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http.Headers;
using System.Text;
using System.Threading.Tasks;
namespace TianQue.Sdk;
public class TQHttpClient
{
private readonly string AppSecret;
private readonly string AppKey;
private readonly IHttpClientFactory _httpClientFactory;
///
/// ssh服务器ip
///
private readonly string SSHHost;
///
/// ssh服务器端口
///
private readonly int SSHPort;
///
/// ssh账号
///
private readonly string SSHUserName;
///
/// ssh密码
///
private readonly string SSHPassword;
private readonly SshClient _sshClient;
private readonly ILogger _logger;
public TQHttpClient(string appSecret, string appKey, IHttpClientFactory httpClientFactory, ILogger logger)
{
AppSecret = appSecret;
AppKey = appKey;
_httpClientFactory = httpClientFactory;
_logger = logger;
}
public TQHttpClient(string appSecret, string appKey, string sshHost, int sshPort, string sshUserName, string sshPassword, IHttpClientFactory httpClientFactory, ILogger logger)
: this(appSecret, appKey, httpClientFactory, logger)
{
SSHHost = sshHost;
SSHPort = sshPort;
SSHUserName = sshUserName;
SSHPassword = sshPassword;
_sshClient = new SshClient(SSHHost, SSHPort, SSHUserName, SSHPassword);
}
public async Task PostAsync(Uri uri, object data)
{
try
{
var headers = new Dictionary { { "_timeStamp", DateTime.Now.ToUnixTimeMilliseconds() }, { "_nonce", SignUtils.GenerateNonce() } };
var sortedDic = new SortedDictionary(data.ToDictionary());
var body = sortedDic.ToJson(new JsonSerializerSettings
{
NullValueHandling = NullValueHandling.Ignore,
ContractResolver = new CamelCasePropertyNamesContractResolver(),
DateFormatString = "yyyy-MM-dd HH:mm:ss.fff"
});
var postJsonSign = SignUtils.Sign(AppSecret, headers, body);
headers.Add("_sign", postJsonSign);
headers.Add("_appKey", AppKey);
if (SSHHost.NotNullOrEmpty() && SSHPort != 0 && SSHUserName.NotNullOrEmpty() && SSHPassword.NotNullOrEmpty())
{
_sshClient.Connect();
var forwardedPort = new ForwardedPortLocal("127.0.0.1", 8090, uri.Host, (uint)uri.Port);
_sshClient.AddForwardedPort(forwardedPort);
forwardedPort.Start();
uri = new Uri("http://127.0.0.1:8090" + uri.AbsolutePath);
}
var content = new StringContent(body, Encoding.GetEncoding("UTF-8"));
content.Headers.ContentType = new MediaTypeHeaderValue("application/json") { CharSet = "UTF-8" };
foreach (var header in headers)
{
content.Headers.Add(header.Key, header.Value.ToString());
}
var resp = await (_httpClientFactory.CreateClient()).PostAsync(uri.ToString(), content);
resp.EnsureSuccessStatusCode();
var result = await resp.Content.ReadAsStringAsync();
_logger.LogInformation($"天阙交互; url: {uri.ToString()}, headers: {headers.ToJson()} request: {body}, response: {result}");
return result.FromJson();
}
catch (Exception e)
{
_logger.LogError(e.Message);
throw;
}
finally
{
if (_sshClient.IsConnected)
{
_sshClient.Disconnect();
}
}
}
}