using System;
using SuperSocket.Facility.Protocol;
using SuperSocket.SocketBase.Protocol;
using log4net;
using Newtonsoft.Json.Linq;
using Newtonsoft.Json;
using System.IO;
using System.Runtime.Caching;

namespace BRServer
{
    public class TelecomReceiveFilter : BeginEndMarkReceiveFilter<StringRequestInfo>
    {
        //开始和结束标记也可以是两个或两个以上的字节
        private readonly static byte[] BeginMark = new byte[] { (byte)'P', (byte)'O', (byte)'S', (byte)'T' };
        private readonly static byte[] EndMark = new byte[] { (byte)'}', (byte)'}' };
        //private static MemoryCache memoryCache = new MemoryCache("Cache");

        public TelecomReceiveFilter()
            : base(BeginMark, EndMark) //传入开始标记和结束标记
        {

        }

        protected override StringRequestInfo ProcessMatchedRequest(byte[] readBuffer, int offset, int length)
        {
            //TODO: 通过解析到的数据来构造请求实例，并返回
            String dataJson = System.Text.Encoding.Default.GetString(readBuffer);
            dataJson = dataJson.Substring(dataJson.LastIndexOf('\n') + 1);
            JObject jo = (JObject)JsonConvert.DeserializeObject(dataJson);
            String deviceId_Telecom = jo["deviceId"].ToString();//电信平台设备id
            String Value = jo["service"]["data"]["Value"].ToString();
            byte[] src = Convert.FromBase64String(Value);
            String result;

            //String cacheValue = (String)memoryCache.Get(deviceId_Telecom);
            //if (cacheValue == Value)
            //{
            //    //有相同数据之前上传过，丢弃此数据
            //    return null;
            //}
            //else 
            //{
            //    DateTimeOffset absoluteExpiration = DateTimeOffset.Now.AddSeconds(60);
            //    memoryCache.Set(deviceId_Telecom, Value, absoluteExpiration);
            //}

            Array.Reverse(src, src.Length - 2, 2);
            String strCrc =
                StringUtil.To16HexString((String.Format("{0:X}", (int)CodeUtils.CRC16_AD(src))));
            if (!strCrc.Equals("0000"))
            {
                result = "Casic:CRCERROR," + BitConverter.ToString(src, 0, src.Length).Replace("-", "");
            }
            else 
            {
                String data = BitConverter.ToString(src, 0, src.Length).Replace("-", "");

                //TODO: construct the receving casic data
                String preamble = data.Substring(0, 2);
                String version = data.Substring(2, 2);
                String leng = data.Substring(4, 4);
                String deviceId = data.Substring(8, 12);
                
                String routeFlag = data.Substring(20, 2);
                String dstNodeAddr = data.Substring(22, 4);
                String pduType = data.Substring(26, 4);
                String seq = data.Substring(30, 2);

                //对tag进行TEA解密
                Byte[] dat = new Byte[data.Length / 2 - 18];
                Array.Copy(src, 16, dat, 0, data.Length / 2 - 18);

                TEA.decrypt(ref dat, dat.Length);
                String settings = BitConverter.ToString(dat, 0, dat.Length).Replace("-", "").Substring(0, Convert.ToInt32(leng, 16) * 2 - 12 * 2);

                result = "Casic:" + preamble + "," + version + "," +
                    leng + "," + deviceId + "," + routeFlag + "," + dstNodeAddr + "," + pduType + "," +
                    seq + "," + settings + "," + deviceId_Telecom;
            }
       
            BasicRequestInfoParser m_Parser = new BasicRequestInfoParser(":", ",");
            return m_Parser.ParseRequestInfo(result);    
        }
    }  
}
