using System;
using System.IO;
using System.IO.Compression;
using System.Runtime.Serialization.Json;
using System.Text;
using MOH_CRA_XCRMS_Service.Entities.DBEntities;

namespace MOH_CRA_XCRMS_Service.Entities
{
    //todo შესაცვლელია ბაზა !!!
    public class RequestsEntity
    {

        public static void AddRequest(Request_XCRMS_LOG request, object obj)
        {

            //todo VAJAs metodit, magram ar shekumsha XMLDocument
            ////  obj.GetType() != byte[]
            //var compressBytes = new byte[] { };
            //if (obj != null)
            //{
            //    var jsonBytes = ConvertToJson(obj);
            //    // var jsonBytes = obj is byte[] ? (byte[])obj : ConvertToJson(obj);
            //    compressBytes = CompressBytes(jsonBytes);
            //}
            //
            var jSON_Result_Str = Newtonsoft.Json.JsonConvert.SerializeObject(obj);

            using (var db = new dbLogDataContext())
            {
                db.ADD_REQUESTS_V01(Guid.NewGuid(), request.UserHost, DateTime.Now, request.Parametri,
                    request.RequestReason, request.Organization, request.Unit, request.Useri,
                    request.MetodName, request.UserAddress, request.UserAgent, null, jSON_Result_Str);

                //var reqLog = new REQUESTS_V01
                //{
                //    ID = Guid.NewGuid(),
                //    USER_AGENT = request.UserAgent,
                //    USER_HOST = request.UserHost,
                //    USER_ADDRESS = request.UserAddress,
                //    METOD_NAME = request.MetodName,
                //    REQUEST_DATE = DateTime.Now,
                //    PARAMETER = request.Parametri,
                //    REQUEST_REASON = request.RequestReason,
                //    ORGANIZATION = request.Organization,
                //    UNIT = request.Unit,
                //    USER_NAME = request.Useri,
                //    DATA = jSON_Result  // compressBytes - VAJAs metodit
                //};
                //db.REQUESTS_V01s.InsertOnSubmit(reqLog);
                //db.SubmitChanges();
            }

        }

        //todo vajas gaketebuli
        private static byte[] CompressBytes(byte[] bytes)
        {
            using (var memoryStream = new MemoryStream())
            {
                using (var deflateStream = new DeflateStream(memoryStream, CompressionMode.Compress))
                {
                    deflateStream.Write(bytes, 0, bytes.Length);
                }
                return memoryStream.ToArray();
            }
        }

        //todo vajas gaketebuli
        private static byte[] ConvertToJson(Object obj)
        {
            using (var stream = new MemoryStream())
            {
                var serializer = new DataContractJsonSerializer(obj.GetType());
                serializer.WriteObject(stream, obj);
                var bytes = stream.ToArray();
                return bytes;
            }
        }

        private static byte[] Zip(string str)
        {
            var bytes = Encoding.UTF8.GetBytes(str);

            using (var msi = new MemoryStream(bytes))
            using (var mso = new MemoryStream())
            {
                using (var gs = new GZipStream(mso, CompressionMode.Compress))
                {
                    //msi.CopyTo(gs);
                    CopyTo(msi, gs);
                }

                return mso.ToArray();
            }
        }

        private static string Unzip(byte[] bytes)
        {
            using (var msi = new MemoryStream(bytes))
            using (var mso = new MemoryStream())
            {
                using (var gs = new GZipStream(msi, CompressionMode.Decompress))
                {
                    //gs.CopyTo(mso);
                    CopyTo(gs, mso);
                }

                return Encoding.UTF8.GetString(mso.ToArray());
            }
        }

        private static void CopyTo(Stream src, Stream dest)
        {
            var bytes = new byte[4096];

            int cnt;

            while ((cnt = src.Read(bytes, 0, bytes.Length)) != 0)
            {
                dest.Write(bytes, 0, cnt);
            }
        }
    }
}