using SinochemCloudClient.Models;
using System;
using System.Collections.Generic;
using Wayne.Lib;
using Wayne.Lib.StateEngine;
using Wayne.Lib.StateEngine.Generic;

namespace SinochemInternetPlusApp.States.Shared
{
    class PayTrx : TimeoutState<FuelingPoint>
    {
        protected override void Enter(StateEntry stateEntry, ref Transition transition)
        {
            base.Enter(stateEntry, ref transition);

            if (Main.CurrentEpsTrx != null)
            {
                Main.CurrentEpsTrx.UpdateTrxStatusToDb(EpsTrxStatus.BeforePayment);

                //Need Pay Cloud, delete trx from xiaofei2, avoid POS lock it
                Main.LockTrxInXiaofei2AsEpsTrx();

                MultiFusionsSupport.DeleteXiaofei2FromTargetFusion(Main.CurrentEpsTrx.Model.jihao, Main.CurrentEpsTrx.Model.liushuino, Main.DebugLogger);
            }

            Main.SendPaymentToCloudAsync();

        }

        protected override void HandleNonTimeoutEvent(StateEngineEvent stateEngineEvent, ref Transition transition)
        {
            if (stateEngineEvent.Type is EventType)
            {
                var genericEvent = stateEngineEvent as GenericEvent<PaymentResponse>;
                switch ((EventType)stateEngineEvent.Type)
                {
                    case EventType.CloudPaymentOk:                        
                        if (genericEvent != null && genericEvent.EventArgs.result != null)
                        {
                            Main.CurrentEpsTrx.Model.real_pay_amount = genericEvent.EventArgs.result.real_Pay_Amount;
                            Main.CurrentEpsTrx.Model.bill_id = genericEvent.EventArgs.result.bill_ID;
                            Main.CurrentEpsTrx.Model.shift_id = genericEvent.EventArgs.result.shift_ID;
                            Main.CurrentEpsTrx.Model.business_date = genericEvent.EventArgs.result.business_Date;
                            Main.CurrentEpsTrx.Model.card_no = genericEvent.EventArgs.result.card_No;
                            Main.CurrentEpsTrx.Model.cardNo_masked = genericEvent.EventArgs.result.cardNo_Hide;
                            Main.CurrentEpsTrx.Model.invoiceUrl = genericEvent.EventArgs.result.invoiceUrl;
                            //Main.CurrentEpsTrx.Model.pay_url = genericEvent.EventArgs.result.pay_url;
                            Main.CurrentEpsTrx.Model.openId = genericEvent.EventArgs.result.openId;
                            Main.CurrentEpsTrx.Model.trx_status = EpsTrxStatus.PaymentOk;

                            //oilcard = 01, weixin = 07
                            if (genericEvent.EventArgs.result.payMethod != null && genericEvent.EventArgs.result.payMethod.Length == 1)
                                Main.CurrentEpsTrx.Model.payMethod = "0" + genericEvent.EventArgs.result.payMethod;
                            else if (genericEvent.EventArgs.result.payMethod != null && genericEvent.EventArgs.result.payMethod.Length == 2)
                                Main.CurrentEpsTrx.Model.payMethod = genericEvent.EventArgs.result.payMethod;

                            if (Main.CurrentEpsTrx.Model.payMethod == "07")
                                Main.CurrentEpsTrx.Model.cardType = CardType.WeiXin;
                            else
                                Main.CurrentEpsTrx.Model.cardType = CardType.OilCard;

                            Main.CurrentEpsTrx.SaveToDb();
                            transition = new Transition(this, TransitionType.CloudPaymentOk);
                        }
                        else
                        {
                            transition = HandleCloudPaymentFailed();
                        }
                        stateEngineEvent.Handled = true;
                        break;

                    case EventType.QRCodePayment:
                    case EventType.PlainUser_Unpaid:
                        //Main.CurrentEpsTrx.UpdateTrxStatusToDb(EpsTrxStatus.BeforePayment);
                        if (Main.CurrentEpsTrx != null)
                        {
                            Main.CurrentEpsTrx.MoveBackToXiaofei2(Main.DebugLogger);
                            // copy this failed trx to another fusion if neeeded
                            MultiFusionsSupport.CopyXiaofei2ToTargetFusion(Main.CurrentEpsTrx.Model.jihao, Main.CurrentEpsTrx.Model.liushuino, Main.DebugLogger);

                            if (genericEvent != null && genericEvent.EventArgs.result != null)
                            {
                               //Main.CurrentEpsTrx.Model.real_pay_amount = genericEvent.EventArgs.result.real_Pay_Amount;
                                Main.CurrentEpsTrx.Model.pay_url = genericEvent.EventArgs.result.pay_url;
                            }
                            transition = new Transition(this, TransitionType.QRCodePayment);
                        }
                        else
                        {
                            transition = HandleCloudPaymentFailed();
                        }

                        stateEngineEvent.Handled = true;
                        break;

                    case EventType.CloudPaymentFailed:
                        if (Main.CurrentEpsTrx != null && genericEvent != null && genericEvent.EventArgs.result != null)
                        {
                            //Main.CurrentEpsTrx.Model.trx_status = EpsTrxStatus.PaymentFailed;
                            //Main.CurrentEpsTrx.Model.real_pay_amount = genericEvent.EventArgs.result.real_Pay_Amount;
                            Main.CurrentEpsTrx.Model.bill_id = genericEvent.EventArgs.result.bill_ID;
                            Main.CurrentEpsTrx.Model.shift_id = genericEvent.EventArgs.result.shift_ID;
                            Main.CurrentEpsTrx.Model.business_date = genericEvent.EventArgs.result.business_Date;
                            Main.CurrentEpsTrx.Model.card_no = genericEvent.EventArgs.result.card_No;
                            Main.CurrentEpsTrx.Model.cardNo_masked = genericEvent.EventArgs.result.cardNo_Hide;
                            Main.CurrentEpsTrx.Model.pay_url = genericEvent.EventArgs.result.pay_url;

                            Main.CurrentEpsTrx.SaveToDb();
                        }
                        transition = HandleCloudPaymentFailed();             
                        stateEngineEvent.Handled = true;
                        break;                   
                }
            }
        }

        private Transition HandleCloudPaymentFailed()
        {
            DebugLog("HandleCloudPaymentFailed");
            if (Main.CurrentEpsTrx != null)
            {
                DebugLog("HandleCloudPaymentFailed MoveBack To xiaofei2");
                Main.CurrentEpsTrx.UpdateTrxStatusToDb(EpsTrxStatus.PaymentNeedConfirm);

                Main.CurrentEpsTrx.MoveBackToXiaofei2(Main.DebugLogger);
                // copy this failed trx to another fusion if neeeded
                MultiFusionsSupport.CopyXiaofei2ToTargetFusion(Main.CurrentEpsTrx.Model.jihao, Main.CurrentEpsTrx.Model.liushuino, Main.DebugLogger);

                //Broadcast trxlist to bigScreen
                var validTrx = EpsTransactionQuery.GetValidCarPlateEpsTrxModels(
                            Main.GetAllNozzlesOnThisSide(),
                            ConfigurationValues.AlreadyDoneEpsTrxCountPerDisplay,
                            Main.DebugLogger);


                if (Main.Eps.NozzleMappingGradeName() != null)
                {
                    foreach (var trx in validTrx)
                    {
                        if (trx.trx_status == EpsTrxStatus.BeforeFueling || trx.trx_status == EpsTrxStatus.Fueling)
                        {
                            trx.AvailableNozzleGrade = Main.GetAvailableNozzleInfo();
                        }

                    }
                }

                int requestId = 0 ;
                var text = Main.Eps.CreateDisplayTrxCommand(validTrx, out requestId, 3);
                if (Main.Eps.CarPlateHandler != null)
                {
                    DebugLog(text);
                    Main.Eps.CarPlateHandler.BroadcastMessageViaFdc(text);

                }
            }


            return new Transition(this, TransitionType.CloudPaymentFailed);
        }

        protected override void Timeout(ref Transition transition)
        {
            transition = HandleCloudPaymentFailed();
        }

        protected override int TimeoutInterval =>
            TimeoutValues.GetValueInMilliSec(TimeoutValues.FuelingPoint.Shared_PayTrx, 15);
    }
}