using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Platform.Common.RunningParameters;
using Platform.Common.LogSystem;
using System.Xml;
using System.IO;

namespace TellerSystem.Communication.Package
{
    class MsgXml01 : IPackage
    {
        //定义静态实例
        public static MsgXml01 Instance;
        /// <summary>
        ///静态实例初始化函数
        /// </summary>
        static public MsgXml01 GetInstance()
        {
            if (Instance == null)
            {
                Instance = new MsgXml01();
            }
            return Instance;
        }

        public byte[] Integrate(Message msg)
        {
            //整个发送包的byte数组，是下面两个的总和，= 8位 + 报文体
            byte[] totalMsgData;
            //8位报文体长度的byte数组
            byte[] dataPartLength;
            //报文体的byte数组
            byte[] dataPart;
            try
            {
                string xmlFirstLine = "<?xml version=\"1.0\" encoding=\"GBK\"?>";
                string upTagBegin = "<service>";
                string xmlHeader = Msg8583ToHeader(msg);
                string xmlData = msg.FileData;
                string upTagEnd = "</service>";
                //报文体（string类型）
                string dataPartStr = xmlFirstLine + upTagBegin + xmlHeader + xmlData + upTagEnd;
                dataPart = PlatformSettings.Encoding.GetBytes(dataPartStr);
                //报文体长度（Int类型）
                int dataPartLengthInt = dataPart.Length;
                //报文体长度（string类型，且左边用0补齐8位）
                string dataPartLengthStr = dataPartLengthInt.ToString().PadLeft(8, '0');
                dataPartLength = PlatformSettings.Encoding.GetBytes(dataPartLengthStr);
                totalMsgData = new byte[8 + dataPartLengthInt];
                for (int j = 0; j < totalMsgData.Length; j++)
                {
                    if (j < 8)
                    {
                        totalMsgData[j] = dataPartLength[j];
                    }
                    else
                    {
                        totalMsgData[j] = dataPart[j - 8];
                    }
                }
            }
            catch (Exception ex)
            {
                PlatformLogger.SystemErrorInfo("组包发生异常！", ex);
                throw;
            }

            return totalMsgData;
        }

        private string Msg8583ToHeader(Message msg)
        {
            var result = new StringBuilder();
            result.Append("<SysHead>");
            //交易码
            result.Append(string.Format("<Txcode>{0}</Txcode>", msg.Fd16.Trim()));
            //前台流水
            result.Append(string.Format("<FrontTrace>{0}</FrontTrace>", msg.Fd96_Q.Trim()));
            //交易日期
            result.Append(string.Format("<Txdate>{0}</Txdate>", msg.Fd5.Trim()));
            //交易时间
            result.Append(string.Format("<Txtime>{0}</Txtime>", msg.Fd6.Trim()));
            //机构编号
            result.Append(string.Format("<InstNo>{0}</InstNo>", msg.Fd2.Trim()));
            //柜员号
            result.Append(string.Format("<UserNo>{0}</UserNo>", msg.Fd7.Trim()));
            
            result.Append("</SysHead>");
            return result.ToString();
        }

        public bool Analyze(Message msg, byte[] data)
        {
            try
            {
                //进行解包处理
                DoAnalyze(msg, data);
            }
            catch (Exception ex)
            {
                return false;
            }
            return true;
        }
        /// <summary>
        /// 解包操作
        /// </summary>
        /// <param name="msg"></param>
        /// <param name="returnData"></param>
        /// <returns></returns>
        public void DoAnalyze(Message msg, byte[] returnData)
        {
            try
            {
                //报文XML区长度        
                int xmlDataLen = 0;
                //报文数据区长度 
                byte[] tmpLen = new byte[8];
                Array.Copy(returnData, 0, tmpLen, 0, 8);
                xmlDataLen = Convert.ToInt32(PlatformSettings.Encoding.GetString(tmpLen));

                //丢弃前8位
                var ret = new byte[xmlDataLen];
                Array.Copy(returnData, 8, ret, 0, xmlDataLen);
                returnData = ret;
                XmlDocument doc = new XmlDocument();
                string xmlStr=PlatformSettings.Encoding.GetString(returnData);
                //日志
                PlatformLogger.CommunicationInfo("\n返回报文数据:\n" + xmlStr);

                doc.LoadXml(xmlStr);
                var node = doc.SelectSingleNode("/service/SysHead");
                msg.Fd16 = node.ChildNodes[0].InnerText;
                msg.Fd5 = node.ChildNodes[1].InnerText;
                msg.Fd6 = node.ChildNodes[2].InnerText;
                msg.Fd2 = node.ChildNodes[3].InnerText;
                msg.Fd7 = node.ChildNodes[4].InnerText;

                msg.Fd12 = node.ChildNodes[5].InnerText;
                //msg.Fd13 = node.ChildNodes[6].InnerText;
                var nodeOfBody=doc.SelectSingleNode("/service/Body");
                if(nodeOfBody != null)
                msg.FileData = doc.SelectSingleNode("/service/Body").OuterXml;
                //var fileLen = returnData.Length - 8 - xmlDataLen ;
                //if (fileLen > 0)
                //{
                //    byte[] fileData = new byte[fileLen];
                //    Array.Copy(returnData, 8 + xmlDataLen, fileData, 0, fileLen);
                //    //返回解包后文件数据
                //    msg.FileData = PlatformSettings.Encoding.GetString(fileData);
                //    //写调试日志
                //    PlatformLogger.CommunicationInfo("\n文件数据:\n" + PlatformSettings.Encoding.GetString(fileData));
                //}
            }
            catch (Exception ex)
            {
                //写错误信息
                PlatformLogger.SystemErrorInfo("解析报文失败！", ex);
                throw;
            }
        }
    }
}
