using Microsoft.Extensions.Configuration;
using System;
using System.Net;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Text;
using System.Threading.Tasks;
using ZeroD.Util;

namespace LifePayment.Domain
{
    public class CommonManager : ICommonManager
    {
        private readonly IConfiguration _configuration;
        private readonly IHttpClientFactory _httpClientFactory;

        public CommonManager(
                IConfiguration configuration,
                IHttpClientFactory httpClientFactory)
        {
            _configuration = configuration;
            _httpClientFactory = httpClientFactory;
        }

        public string GetOssUrl(string path, string fileName, byte[] bytes, string ext)
        {
            var ossHelper = new OssHelper(_configuration);
            return ossHelper.GetOssUrl($"{path}{fileName}.{ext}", bytes);
        }

        public string GetOssUrl(string path, string fileName, string base64Str, string ext)
        {
            var ossHelper = new OssHelper(_configuration);
            return ossHelper.GetOssUrl($"{path}{fileName}.{ext}", Convert.FromBase64String(base64Str.Replace("data:image/png;base64,", string.Empty)));
        }

        public async Task<TResult> PostAsync<TResult>(string url, dynamic input, int? timeout = null)
        {
            TimeSpan defaultTimeout = TimeSpan.FromSeconds(90);
            var cookieContainer = new CookieContainer();
            using (var handler = new HttpClientHandler { CookieContainer = cookieContainer })
            {
                using (var apiClient = new HttpClient(handler))
                {
                    apiClient.Timeout = timeout.HasValue ? TimeSpan.FromMilliseconds(timeout.Value) : defaultTimeout;
                    apiClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
                    using (var requestContent = new StringContent(JsonString.Object2Json(input), Encoding.UTF8, "application/json"))
                    {
                        using (var response = await apiClient.PostAsync(url, requestContent))
                        {
                            if (!response.IsSuccessStatusCode)
                            {
                                return default;
                            }

                            if (typeof(TResult) == typeof(byte[]))
                            {
                                using (var res = await response.Content.ReadAsStreamAsync())
                                {
                                    int counts = (int)res.Length;
                                    int offset = 0;
                                    byte[] returnByte = new byte[counts];
                                    while (counts > 0)
                                    {
                                        int n = res.Read(returnByte, offset, counts);
                                        if (n == 0)
                                        {
                                            break;
                                        }

                                        counts -= n;
                                        offset += n;
                                    }

                                    return (TResult)Convert.ChangeType(returnByte, typeof(TResult));
                                }
                            }

                            var ajaxResponse = JsonString.JsonString2Object<TResult>(await response.Content.ReadAsStringAsync());
                            return ajaxResponse;
                        }
                    }
                }
            }
        }

    }
}