예제 #1
0
        public void ReleaseDocProc(JournalEntry je, INRegister doc, INReleaseProcess_Extension.ReleaseDocProcDelegate baseMethod)
        {
            baseMethod(je, doc);

            foreach (INTranSplit row in this.Base.intransplit.Cache.Cached)
            {
                INTranSplit tranSplit = SelectINTranRcpSplit(Base, row.LotSerialNbr, row.InventoryID, row.SubItemID, row.SiteID, row.LocationID);

                if (tranSplit != null && row.DocType != INDocType.Receipt)
                {
                    INTranSplitExt tranSplitExt = tranSplit.GetExtension <INTranSplitExt>();

                    Base.intransplit.Cache.SetValue <INTranSplitExt.usrCOO>(row, tranSplitExt.UsrCOO);
                    Base.intransplit.Cache.SetValue <INTranSplitExt.usrDateCode>(row, tranSplitExt.UsrDateCode);
                }
                else
                {
                    SOShipLineSplit lineSplit = SelectSOShipLineSplit(Base, row.LotSerialNbr, row.InventoryID, row.SubItemID, row.SiteID, row.LocationID);

                    if (lineSplit == null)
                    {
                        continue;
                    }

                    SOShipLineSplitExt lineSplitExt = lineSplit.GetExtension <SOShipLineSplitExt>();

                    Base.intransplit.Cache.SetValue <INTranSplitExt.usrCOO>(row, lineSplitExt.UsrCOO);
                    Base.intransplit.Cache.SetValue <INTranSplitExt.usrDateCode>(row, lineSplitExt.UsrDateCode);
                }

                Base.Caches[typeof(INTranSplit)].PersistUpdated(this.Base.Caches[typeof(INTranSplit)].Update(row));

                PXTimeStampScope.PutPersisted(this.Base.Caches[typeof(INTranSplit)], row, PXDatabase.SelectTimeStamp());
            }
        }
예제 #2
0
 public static void ReleaseARDocument(IBqlTable aTable)
 {
     AR.ARRegister toProc = (AR.ARRegister)aTable;
     using (PXTimeStampScope scope = new PXTimeStampScope(null))
     {
         if (!(toProc.Released ?? false))
         {
             List <AR.ARRegister> list = new List <AR.ARRegister>(1);
             list.Add(toProc);
             ARDocumentRelease.ReleaseDoc(list, false);
         }
     }
 }
        public override POOrder CalculateExternalTax(POOrder order)
        {
            var  toAddress    = GetToAddress(order);
            bool isNonTaxable = IsNonTaxable(toAddress);

            if (isNonTaxable)
            {
                order.IsTaxValid         = true;
                order.IsUnbilledTaxValid = true;
                ApplyTax(order, GetTaxResult.Empty, GetTaxResult.Empty);

                return(order);
            }

            var service = TaxProviderFactory(Base, order.TaxZoneID);

            GetTaxRequest getRequest         = null;
            GetTaxRequest getRequestUnbilled = null;

            bool isValidByDefault = true;

            if (order.IsTaxValid != true)
            {
                getRequest = BuildGetTaxRequest(order);

                if (getRequest.CartItems.Count > 0)
                {
                    isValidByDefault = false;
                }
                else
                {
                    getRequest = null;
                }
            }

            if (order.IsUnbilledTaxValid != true)
            {
                getRequestUnbilled = BuildGetTaxRequestUnbilled(order);
                if (getRequestUnbilled.CartItems.Count > 0)
                {
                    isValidByDefault = false;
                }
                else
                {
                    getRequestUnbilled = null;
                }
            }

            if (isValidByDefault)
            {
                PXDatabase.Update <POOrder>(
                    new PXDataFieldAssign(nameof(POOrder.IsTaxValid), true),
                    new PXDataFieldAssign(nameof(POOrder.IsUnbilledTaxValid), true),
                    new PXDataFieldRestrict(nameof(POOrder.OrderType), PXDbType.VarChar, 2, order.OrderType, PXComp.EQ),
                    new PXDataFieldRestrict(nameof(POOrder.OrderNbr), PXDbType.NVarChar, 15, order.OrderNbr, PXComp.EQ)
                    );
                order.IsTaxValid         = true;
                order.IsUnbilledTaxValid = true;
                PXTimeStampScope.PutPersisted(Base.Document.Cache, order, PXDatabase.SelectTimeStamp());
                return(order);
            }

            GetTaxResult result         = null;
            GetTaxResult resultUnbilled = null;

            bool getTaxFailed = false;

            if (getRequest != null)
            {
                result = service.GetTax(getRequest);
                if (!result.IsSuccess)
                {
                    getTaxFailed = true;
                }
            }
            if (getRequestUnbilled != null)
            {
                resultUnbilled = service.GetTax(getRequestUnbilled);
                if (!resultUnbilled.IsSuccess)
                {
                    getTaxFailed = true;
                }
            }

            if (!getTaxFailed)
            {
                try
                {
                    ApplyTax(order, result, resultUnbilled);
                    PXDatabase.Update <POOrder>(
                        new PXDataFieldAssign(nameof(POOrder.IsTaxValid), true),
                        new PXDataFieldAssign(nameof(POOrder.IsUnbilledTaxValid), true),
                        new PXDataFieldRestrict(nameof(POOrder.OrderType), PXDbType.VarChar, 2, order.OrderType, PXComp.EQ),
                        new PXDataFieldRestrict(nameof(POOrder.OrderNbr), PXDbType.NVarChar, 15, order.OrderNbr, PXComp.EQ)
                        );
                    order.IsTaxValid         = true;
                    order.IsUnbilledTaxValid = true;
                    PXTimeStampScope.PutPersisted(Base.Document.Cache, order, PXDatabase.SelectTimeStamp());
                }
                catch (PXOuterException ex)
                {
                    string msg = TX.Messages.FailedToApplyTaxes;
                    foreach (string err in ex.InnerMessages)
                    {
                        msg += Environment.NewLine + err;
                    }

                    throw new PXException(ex, msg);
                }
                catch (Exception ex)
                {
                    string msg = TX.Messages.FailedToApplyTaxes;
                    msg += Environment.NewLine + ex.Message;

                    throw new PXException(ex, msg);
                }
            }
            else
            {
                ResultBase taxResult = result ?? resultUnbilled;
                if (taxResult != null)
                {
                    LogMessages(taxResult);
                }

                throw new PXException(TX.Messages.FailedToGetTaxes);
            }

            return(order);
        }
예제 #4
0
        public static void ReleasePayments(List <APPayment> list, string Action)
        {
            APReleaseChecks releaseChecksGraph = CreateInstance <APReleaseChecks>();
            APPaymentEntry  pe        = CreateInstance <APPaymentEntry>();
            CABatchEntry    be        = CreateInstance <CABatchEntry>();
            bool            failed    = false;
            bool            successed = false;

            List <APRegister> docs = new List <APRegister>(list.Count);

            foreach (APPayment payment in list)
            {
                if (payment.Passed == true)
                {
                    releaseChecksGraph.TimeStamp = pe.TimeStamp = payment.tstamp;
                }

                switch (Action)
                {
                case ReleaseChecksFilter.action.ReleaseChecks:
                    payment.Printed = true;
                    break;

                case ReleaseChecksFilter.action.ReprintChecks:
                case ReleaseChecksFilter.action.VoidAndReprintChecks:
                    payment.ExtRefNbr = null;
                    payment.Printed   = false;
                    break;

                default:
                    continue;
                }

                PXProcessing <APPayment> .SetCurrentItem(payment);

                if (Action == ReleaseChecksFilter.action.ReleaseChecks)
                {
                    try
                    {
                        pe.Document.Current = pe.Document.Search <APPayment.refNbr>(payment.RefNbr, payment.DocType);
                        if (pe.Document.Current?.ExtRefNbr != payment.ExtRefNbr)
                        {
                            APPayment payment_copy = PXCache <APPayment> .CreateCopy(pe.Document.Current);

                            payment_copy.ExtRefNbr = payment.ExtRefNbr;
                            pe.Document.Update(payment_copy);
                        }

                        if (PaymentRefAttribute.PaymentRefMustBeUnique(pe.paymenttype.Current) && string.IsNullOrEmpty(payment.ExtRefNbr))
                        {
                            throw new PXException(ErrorMessages.FieldIsEmpty, typeof(APPayment.extRefNbr).Name);
                        }

                        payment.IsReleaseCheckProcess = true;

                        APPrintChecks.AssignNumbersWithNoAdditionalProcessing(pe, payment);
                        pe.Save.Press();

                        object[] persisted = PXTimeStampScope.GetPersisted(pe.Document.Cache, pe.Document.Current);
                        if (persisted == null || persisted.Length == 0)
                        {
                            //preserve timestamp which will be @@dbts after last record committed to db on previous Persist().
                            //otherwise another process updated APAdjust.
                            docs.Add(payment);
                        }
                        else
                        {
                            if (payment.Passed == true)
                            {
                                pe.Document.Current.Passed = true;
                            }
                            docs.Add(pe.Document.Current);
                        }
                        successed = true;
                    }
                    catch (PXException e)
                    {
                        PXProcessing <APPayment> .SetError(e);

                        docs.Add(null);
                        failed = true;
                    }
                }

                if (Action == ReleaseChecksFilter.action.ReprintChecks || Action == ReleaseChecksFilter.action.VoidAndReprintChecks)
                {
                    try
                    {
                        payment.IsPrintingProcess = true;
                        using (PXTransactionScope transactionScope = new PXTransactionScope())
                        {
                            #region Update CABatch if ReprintChecks
                            CABatch caBatch = PXSelectJoin <CABatch,
                                                            InnerJoin <CABatchDetail, On <CABatch.batchNbr, Equal <CABatchDetail.batchNbr> > >,
                                                            Where <CABatchDetail.origModule, Equal <Required <APPayment.origModule> >,
                                                                   And <CABatchDetail.origDocType, Equal <Required <APPayment.docType> >,
                                                                        And <CABatchDetail.origRefNbr, Equal <Required <APPayment.refNbr> > > > > > .
                                              Select(be, payment.OrigModule, payment.DocType, payment.RefNbr);

                            if (caBatch != null)
                            {
                                be.Document.Current = caBatch;
                                int           DetailCount = be.Details.Select().Count;                       // load
                                CABatchDetail detail      = be.Details.Locate(new CABatchDetail()
                                {
                                    BatchNbr    = be.Document.Current.BatchNbr,
                                    OrigModule  = payment.OrigModule,
                                    OrigDocType = payment.DocType,
                                    OrigRefNbr  = payment.RefNbr,
                                    OrigLineNbr = CABatchDetail.origLineNbr.DefaultValue,
                                });
                                if (detail != null)
                                {
                                    // payment.Status is recalculated in CABatchEntry.Delete
                                    if (DetailCount == 1)
                                    {
                                        be.Document.Delete(be.Document.Current);                                         // Details will delete by PXParent
                                    }
                                    else
                                    {
                                        be.Details.Delete(detail);                                          // recalculated batch totals
                                    }
                                }
                                be.Save.Press();
                            }
                            else
                            {
                                PXCache cacheAPPayment = releaseChecksGraph.APPaymentList.Cache;

                                cacheAPPayment.SetValueExt <APPayment.printed>(payment, false);
                                cacheAPPayment.SetValueExt <APPayment.hold>(payment, false);
                                cacheAPPayment.SetValueExt <APPayment.extRefNbr>(payment, null);
                                // APPayment.Status is recalculated by SetStatusCheckAttribute
                                cacheAPPayment.MarkUpdated(payment);

                                cacheAPPayment.PersistUpdated(payment);
                                cacheAPPayment.Persisted(false);
                            }
                            #endregion
                            // TODO: Need to rework. Use legal CRUD methods of caches!
                            releaseChecksGraph.TimeStamp = PXDatabase.SelectTimeStamp();

                            // delete check numbers only if Reprint (not Void and Reprint)
                            PaymentMethod pm = pe.paymenttype.Select(payment.PaymentMethodID);
                            if (pm.APPrintChecks == true && Action == ReleaseChecksFilter.action.ReprintChecks)
                            {
                                APPayment doc = payment;
                                new HashSet <string>(pe.Adjustments_Raw.Select(doc.DocType, doc.RefNbr)
                                                     .RowCast <APAdjust>()
                                                     .Select(adj => adj.StubNbr))
                                .ForEach(nbr => PaymentRefAttribute.DeleteCheck((int)doc.CashAccountID, doc.PaymentMethodID, nbr));

                                // sync PaymentMethodAccount.APLastRefNbr with actual last CashAccountCheck number
                                PaymentMethodAccount det = releaseChecksGraph.cashaccountdetail.SelectSingle(payment.CashAccountID, payment.PaymentMethodID);
                                PaymentRefAttribute.LastCashAccountCheckSelect.Clear(releaseChecksGraph);
                                CashAccountCheck cacheck = PaymentRefAttribute.LastCashAccountCheckSelect.SelectSingleBound(releaseChecksGraph, new object[] { det });
                                det.APLastRefNbr = cacheck?.CheckNbr;
                                releaseChecksGraph.cashaccountdetail.Cache.PersistUpdated(det);
                                releaseChecksGraph.cashaccountdetail.Cache.Persisted(false);
                            }
                            // END TODO
                            if (string.IsNullOrEmpty(payment.ExtRefNbr))
                            {
                                //try to get next number
                                releaseChecksGraph.APPaymentList.Cache.SetDefaultExt <APPayment.extRefNbr>(payment);
                            }
                            transactionScope.Complete();
                        }
                    }
                    catch (PXException e)
                    {
                        PXProcessing <APPayment> .SetError(e);
                    }
                    docs.Add(null);
                }
            }
            if (successed)
            {
                APDocumentRelease.ReleaseDoc(docs, true);
            }

            if (failed)
            {
                throw new PXOperationCompletedWithErrorException(GL.Messages.DocumentsNotReleased);
            }
        }
예제 #5
0
        public static void ReleasePayments(List <APPayment> list, string Action)
        {
            APReleaseChecks graph     = PXGraph.CreateInstance <APReleaseChecks>();
            APPaymentEntry  pe        = PXGraph.CreateInstance <APPaymentEntry>();
            bool            failed    = false;
            bool            successed = false;

            string NextCheckNbr = null;

            List <APRegister>        docs    = new List <APRegister>(list.Count);
            List <string>            numbers = new List <string>();
            Dictionary <string, int> stubs   = new Dictionary <string, int>();

            for (int i = 0; i < list.Count; i++)
            {
                if (list[i].Passed == true)
                {
                    graph.TimeStamp = pe.TimeStamp = list[i].tstamp;
                }

                switch (Action)
                {
                case "R":
                    list[i].Printed = true;
                    break;

                case "D":
                    PaymentMethodAccount det = PXSelect <PaymentMethodAccount, Where <PaymentMethodAccount.cashAccountID, Equal <Required <PaymentMethodAccount.cashAccountID> >, And <PaymentMethodAccount.paymentMethodID, Equal <Required <PaymentMethodAccount.paymentMethodID> > > > > .Select(graph, list[i].CashAccountID, list[i].PaymentMethodID);

                    if (det == null || det.APAutoNextNbr == false)
                    {
                        numbers.Add(list[i].ExtRefNbr);
                        stubs[list[i].ExtRefNbr] = (int)list[i].StubCntr;
                        //null out Check Number and delete used check number if StubCounter == 1
                        list[i].ExtRefNbr = null;
                    }
                    list[i].Printed = false;
                    break;

                case "V":
                    //null out Check Number but do not delete it
                    list[i].StubCntr  = -1;
                    list[i].ExtRefNbr = null;
                    list[i].Printed   = false;
                    break;

                default:
                    continue;
                }

                if ((bool)list[i].Printed)
                {
                    try
                    {
                        APPrintChecks.AssignNumbers(pe, list[i], ref NextCheckNbr);
                        pe.Save.Press();

                        object[] persisted = PXTimeStampScope.GetPersisted(pe.Document.Cache, pe.Document.Current);
                        if (persisted == null || persisted.Length == 0)
                        {
                            //preserve timestamp which will be @@dbts after last record committed to db on previous Persist().
                            //otherwise another process updated APAdjust.
                            docs.Add(list[i]);
                        }
                        else
                        {
                            if (list[i].Passed == true)
                            {
                                pe.Document.Current.Passed = true;
                            }
                            docs.Add(pe.Document.Current);
                        }
                        successed = true;
                    }
                    catch (Exception e)
                    {
                        PXProcessing <APPayment> .SetError(i, e);

                        docs.Add(null);
                        failed = true;
                    }
                }
                else
                {
                    try
                    {
                        list[i].Hold = true;

                        graph.APPaymentList.Cache.PersistUpdated(list[i]);
                        graph.APPaymentList.Cache.Persisted(false);

                        graph.TimeStamp = PXDatabase.SelectTimeStamp();

                        if (string.IsNullOrEmpty(list[i].ExtRefNbr))
                        {
                            //try to get next number
                            graph.APPaymentList.Cache.SetDefaultExt <APPayment.extRefNbr>(list[i]);
                            if (string.IsNullOrEmpty(list[i].ExtRefNbr) == false)
                            {
                                list[i].StubCntr = 1;
                                graph.APPaymentList.Cache.PersistUpdated(list[i]);
                                graph.APPaymentList.Cache.Persisted(false);
                            }
                        }
                    }
                    catch (Exception e)
                    {
                        PXProcessing <APPayment> .SetError(i, e);
                    }
                    docs.Add(null);
                }
            }
            if (successed)
            {
                APDocumentRelease.ReleaseDoc(docs, true);
            }

            numbers.Sort();
            for (int i = numbers.Count - 1; i >= 0; i--)
            {
                PaymentMethodAccount det = PXSelect <PaymentMethodAccount, Where <PaymentMethodAccount.cashAccountID, Equal <Required <PaymentMethodAccount.cashAccountID> >, And <PaymentMethodAccount.paymentMethodID, Equal <Required <PaymentMethodAccount.paymentMethodID> > > > > .Select(graph, list[0].CashAccountID, list[0].PaymentMethodID);

                string lastnumber = AutoNumberAttribute.NextNumber(numbers[i], stubs[numbers[i]] - 1);

                if (string.Equals(lastnumber, det.APLastRefNbr))
                {
                    det.APLastRefNbr = AutoNumberAttribute.NextNumber(det.APLastRefNbr, -stubs[numbers[i]]);
                    graph.cashaccountdetail.Cache.PersistUpdated(det);
                    graph.cashaccountdetail.Cache.Persisted(false);
                }
            }

            if (failed)
            {
                throw new PXException(GL.Messages.DocumentsNotReleased);
            }
        }
예제 #6
0
        public virtual PMProforma CalculateExternalTax(PMProforma doc, bool forceRecalculate)
        {
            var toAddress = GetToAddress(doc);

            GetTaxRequest getRequest       = null;
            bool          isValidByDefault = true;

            if ((doc.IsTaxValid != true || forceRecalculate) && !IsNonTaxable(toAddress))
            {
                getRequest = BuildGetTaxRequest(doc);

                if (getRequest.CartItems.Count > 0)
                {
                    isValidByDefault = false;
                }
                else
                {
                    getRequest = null;
                }
            }

            if (isValidByDefault)
            {
                doc.CuryTaxTotal = 0;
                doc.IsTaxValid   = true;
                Base.Document.Update(doc);

                foreach (PMTaxTran item in Base.Taxes.Select())
                {
                    Base.Taxes.Delete(item);
                }

                using (var ts = new PXTransactionScope())
                {
                    Base.Persist(typeof(PMTaxTran), PXDBOperation.Delete);
                    Base.Persist(typeof(PMProforma), PXDBOperation.Update);
                    PXTimeStampScope.PutPersisted(Base.Document.Cache, doc, PXDatabase.SelectTimeStamp());
                    ts.Complete();
                }
                return(doc);
            }

            GetTaxResult result       = null;
            var          service      = TaxProviderFactory(Base, doc.TaxZoneID);
            bool         getTaxFailed = false;

            if (getRequest != null)
            {
                result = service.GetTax(getRequest);
                if (!result.IsSuccess)
                {
                    getTaxFailed = true;
                }
            }

            if (!getTaxFailed)
            {
                try
                {
                    ApplyTax(doc, result);
                    using (var ts = new PXTransactionScope())
                    {
                        doc.IsTaxValid = true;
                        Base.Document.Update(doc);
                        Base.Persist(typeof(PMProforma), PXDBOperation.Update);
                        PXTimeStampScope.PutPersisted(Base.Document.Cache, doc, PXDatabase.SelectTimeStamp());
                        ts.Complete();
                    }
                }
                catch (PXOuterException ex)
                {
                    string msg = TX.Messages.FailedToApplyTaxes;
                    foreach (string err in ex.InnerMessages)
                    {
                        msg += Environment.NewLine + err;
                    }

                    throw new PXException(ex, msg);
                }
                catch (Exception ex)
                {
                    string msg = TX.Messages.FailedToApplyTaxes;
                    msg += Environment.NewLine + ex.Message;

                    throw new PXException(ex, msg);
                }
            }
            else
            {
                LogMessages(result);

                throw new PXException(TX.Messages.FailedToGetTaxes);
            }

            return(doc);
        }
예제 #7
0
        public virtual void RowPersisted(PXCache sender, PXRowPersistedEventArgs e)
        {
            PXCache cache = sender.Graph.Caches[typeof(CATran)];

            if (e.TranStatus == PXTranStatus.Open)
            {
                object key = sender.GetValue(e.Row, _FieldOrdinal);
            }
            else if (e.TranStatus == PXTranStatus.Aborted)
            {
                object key = sender.GetValue(e.Row, _FieldOrdinal);
                if (_KeyToAbort != null && (long)_KeyToAbort < 0L)
                {
                    sender.SetValue(e.Row, _FieldOrdinal, _KeyToAbort);
                    foreach (CATran data in cache.Inserted)
                    {
                        if (Equals(key, data.TranID))
                        {
                            data.TranID = (long)_KeyToAbort;
                            cache.ResetPersisted(data);
                            break;
                        }
                    }
                }
                else
                {
                    foreach (CATran data in cache.Updated)
                    {
                        if (object.Equals(key, data.TranID))
                        {
                            cache.ResetPersisted(data);
                        }
                    }
                }

                cache.Normalize();
            }
            else
            {
                object key = sender.GetValue(e.Row, _FieldOrdinal);
                foreach (CATran data in cache.Inserted)
                {
                    if (object.Equals(key, data.TranID))
                    {
                        cache.RaiseRowPersisted(data, PXDBOperation.Insert, e.TranStatus, e.Exception);
                        cache.SetStatus(data, PXEntryStatus.Notchanged);
                        PXTimeStampScope.PutPersisted(cache, data, sender.Graph.TimeStamp);
                        cache.ResetPersisted(data);
                    }
                }
                foreach (CATran data in cache.Updated)
                {
                    if (object.Equals(key, data.TranID))
                    {
                        cache.RaiseRowPersisted(data, PXDBOperation.Update, e.TranStatus, e.Exception);
                        cache.SetStatus(data, PXEntryStatus.Notchanged);
                        PXTimeStampScope.PutPersisted(cache, data, sender.Graph.TimeStamp);
                        cache.ResetPersisted(data);
                    }
                }
                foreach (CATran data in cache.Deleted)
                {
                    cache.RaiseRowPersisted(data, PXDBOperation.Delete, e.TranStatus, e.Exception);
                    cache.SetStatus(data, PXEntryStatus.Notchanged);
                    PXTimeStampScope.PutPersisted(cache, data, sender.Graph.TimeStamp);
                    cache.ResetPersisted(data);
                }
                cache.IsDirty = false;
                cache.Normalize();
            }
        }
        public static void ReleasePayments(List <APPayment> list, string Action)
        {
            APReleaseChecks releaseChecksGraph = CreateInstance <APReleaseChecks>();
            APPaymentEntry  pe        = CreateInstance <APPaymentEntry>();
            bool            failed    = false;
            bool            successed = false;

            List <APRegister> docs = new List <APRegister>(list.Count);

            foreach (APPayment payment in list)
            {
                if (payment.Passed == true)
                {
                    releaseChecksGraph.TimeStamp = pe.TimeStamp = payment.tstamp;
                }

                switch (Action)
                {
                case ReleaseChecksFilter.action.ReleaseChecks:
                    payment.Printed = true;
                    break;

                case ReleaseChecksFilter.action.ReprintChecks:
                case ReleaseChecksFilter.action.VoidAndReprintChecks:
                    payment.ExtRefNbr = null;
                    payment.Printed   = false;
                    break;

                default:
                    continue;
                }

                PXProcessing <APPayment> .SetCurrentItem(payment);

                if (Action == ReleaseChecksFilter.action.ReleaseChecks)
                {
                    try
                    {
                        pe.Document.Current = pe.Document.Search <APPayment.refNbr>(payment.RefNbr, payment.DocType);
                        if (PaymentRefAttribute.PaymentRefMustBeUnique(pe.paymenttype.Current) && string.IsNullOrEmpty(payment.ExtRefNbr))
                        {
                            throw new PXException(ErrorMessages.FieldIsEmpty, typeof(APPayment.extRefNbr).Name);
                        }

                        payment.IsReleaseCheckProcess = true;

                        APPrintChecks.AssignNumbersWithNoAdditionalProcessing(pe, payment);
                        pe.Save.Press();

                        object[] persisted = PXTimeStampScope.GetPersisted(pe.Document.Cache, pe.Document.Current);
                        if (persisted == null || persisted.Length == 0)
                        {
                            //preserve timestamp which will be @@dbts after last record committed to db on previous Persist().
                            //otherwise another process updated APAdjust.
                            docs.Add(payment);
                        }
                        else
                        {
                            if (payment.Passed == true)
                            {
                                pe.Document.Current.Passed = true;
                            }
                            docs.Add(pe.Document.Current);
                        }
                        successed = true;
                    }
                    catch (PXException e)
                    {
                        PXProcessing <APPayment> .SetError(e);

                        docs.Add(null);
                        failed = true;
                    }
                }

                if (Action == ReleaseChecksFilter.action.ReprintChecks || Action == ReleaseChecksFilter.action.VoidAndReprintChecks)
                {
                    try
                    {
                        payment.IsPrintingProcess = true;

                        releaseChecksGraph.APPaymentList.Cache.SetValueExt <APPayment.printed>(payment, false);
                        releaseChecksGraph.APPaymentList.Cache.SetValueExt <APPayment.hold>(payment, false);
                        releaseChecksGraph.APPaymentList.Cache.SetValueExt <APPayment.extRefNbr>(payment, null);

                        releaseChecksGraph.APPaymentList.Cache.RaiseRowSelected(payment);                         //We need payment's status to be set correctly before persisting
                        // TODO: Need to rework. Use legal CRUD methods of caches!
                        releaseChecksGraph.APPaymentList.Cache.PersistUpdated(payment);
                        releaseChecksGraph.APPaymentList.Cache.Persisted(false);

                        releaseChecksGraph.TimeStamp = PXDatabase.SelectTimeStamp();

                        // delete check numbers only if Reprint (not Void and Reprint)
                        PaymentMethod pm = pe.paymenttype.Select(payment.PaymentMethodID);
                        if (pm.APPrintChecks == true && Action == ReleaseChecksFilter.action.ReprintChecks)
                        {
                            APPayment doc = payment;
                            new HashSet <string>(pe.Adjustments_Raw.Select(doc.DocType, doc.RefNbr)
                                                 .RowCast <APAdjust>()
                                                 .Select(adj => adj.StubNbr))
                            .ForEach(nbr => PaymentRefAttribute.DeleteCheck((int)doc.CashAccountID, doc.PaymentMethodID, nbr));

                            // sync PaymentMethodAccount.APLastRefNbr with actual last CashAccountCheck number
                            PaymentMethodAccount det = releaseChecksGraph.cashaccountdetail.SelectSingle(payment.CashAccountID, payment.PaymentMethodID);
                            PaymentRefAttribute.LastCashAccountCheckSelect.Clear(releaseChecksGraph);
                            CashAccountCheck cacheck = PaymentRefAttribute.LastCashAccountCheckSelect.SelectSingleBound(releaseChecksGraph, new object[] { det });
                            det.APLastRefNbr = cacheck?.CheckNbr;
                            releaseChecksGraph.cashaccountdetail.Cache.PersistUpdated(det);
                            releaseChecksGraph.cashaccountdetail.Cache.Persisted(false);
                        }
                        // END TODO
                        if (string.IsNullOrEmpty(payment.ExtRefNbr))
                        {
                            //try to get next number
                            releaseChecksGraph.APPaymentList.Cache.SetDefaultExt <APPayment.extRefNbr>(payment);
                        }
                    }
                    catch (PXException e)
                    {
                        PXProcessing <APPayment> .SetError(e);
                    }
                    docs.Add(null);
                }
            }
            if (successed)
            {
                APDocumentRelease.ReleaseDoc(docs, true);
            }

            if (failed)
            {
                throw new PXOperationCompletedWithErrorException(GL.Messages.DocumentsNotReleased);
            }
        }
        public virtual IEnumerable Action(
            PXAdapter adapter,
            [PXInt]
            [PXIntList(new int[] { 1, 2, 3, 4, 5 }, new string[] { "Create Shipment", "Apply Assignment Rules", "Create Invoice", "Post Invoice to IN", "Create Purchase Order" })]
            int?actionID,
            [PXDate]
            DateTime?shipDate,
            [PXSelector(typeof(INSite.siteCD))]
            string siteCD,
            [SOOperation.List]
            string operation,
            [PXString()]
            string ActionName,
            Func <PXAdapter, int?, DateTime?, string, string, string, IEnumerable> baseMtd)
        {
            switch (actionID)
            {
            case 1:
            {
                if (!string.IsNullOrEmpty(ActionName))
                {
                    PXAction action = Base.Actions[ActionName];

                    if (action != null)
                    {
                        Base.Save.Press();
                        List <object> result = new List <object>();
                        foreach (object data in action.Press(adapter))
                        {
                            result.Add(data);
                        }
                        return(result);
                    }
                }

                List <SOOrder> list = new List <SOOrder>();
                foreach (SOOrder order in adapter.Get <SOOrder>())
                {
                    list.Add(order);
                }

                if (shipDate != null)
                {
                    Base.soparamfilter.Current.ShipDate = shipDate;
                }

                if (Base.soparamfilter.Current.ShipDate == null)
                {
                    Base.soparamfilter.Current.ShipDate = Base.Accessinfo.BusinessDate;
                }

                if (siteCD != null)
                {
                    Base.soparamfilter.Cache.SetValueExt <SOParamFilter.siteID>(Base.soparamfilter.Current, siteCD);
                }

                if (!adapter.MassProcess)
                {
                    if (Base.soparamfilter.Current.SiteID == null)
                    {
                        Base.soparamfilter.Current.SiteID = GetPreferedSiteID();
                    }
                    if (adapter.ExternalCall)
                    {
                        Base.soparamfilter.AskExt(true);
                    }
                }
                if (Base.soparamfilter.Current.SiteID != null || adapter.MassProcess)
                {
                    try
                    {
                        Base.RecalculateExternalTaxesSync = true;
                        Base.Save.Press();
                    }
                    finally
                    {
                        Base.RecalculateExternalTaxesSync = false;
                    }
                    PXAutomation.RemovePersisted(Base, typeof(SOOrder), new List <object>(list));

                    SOParamFilter filter = Base.soparamfilter.Current;
                    PXLongOperation.StartOperation(Base, delegate()
                        {
                            bool anyfailed                    = false;
                            SOShipmentEntry docgraph          = PXGraph.CreateInstance <SOShipmentEntry>();
                            SOOrderEntry ordgraph             = PXGraph.CreateInstance <SOOrderEntry>();
                            DocumentList <SOShipment> created = new DocumentList <SOShipment>(docgraph);

                            //address AC-92776
                            for (int i = 0; i < list.Count; i++)
                            {
                                SOOrder order = list[i];
                                if (adapter.MassProcess)
                                {
                                    PXProcessing <SOOrder> .SetCurrentItem(order);
                                }

                                SOOrder ordercopy = (SOOrder)Base.Caches[typeof(SOOrder)].CreateCopy(order);
                                try
                                {
                                    if (operation == SOOperation.Issue)
                                    {
                                        ReviewWarehouseAvailability(ordgraph, order);
                                    }
                                }
                                catch (SOShipmentException ex)
                                {
                                    Base.Caches[typeof(SOOrder)].RestoreCopy(order, ordercopy);
                                    if (!adapter.MassProcess)
                                    {
                                        throw;
                                    }

                                    order.LastShipDate = filter.ShipDate;
                                    order.Status       = SOOrderStatus.Shipping; //Automation will set the order to back order since no shipments were created

                                    docgraph.Clear();

                                    var ordergraph = PXGraph.CreateInstance <SOOrderEntry>();
                                    ordergraph.Clear();

                                    ordergraph.Document.Cache.MarkUpdated(order);
                                    PXAutomation.CompleteSimple(ordergraph.Document.View);
                                    try
                                    {
                                        ordergraph.Save.Press();
                                        PXAutomation.RemovePersisted(ordergraph, order);

                                        PXTrace.WriteInformation(ex);
                                        PXProcessing <SOOrder> .SetWarning(ex);
                                    }
                                    catch (Exception inner)
                                    {
                                        Base.Caches[typeof(SOOrder)].RestoreCopy(order, ordercopy);
                                        PXProcessing <SOOrder> .SetError(inner);
                                        anyfailed = true;
                                    }
                                    continue;     //Stop there for this order
                                }
                                catch (Exception ex)
                                {
                                    if (!adapter.MassProcess)
                                    {
                                        throw;
                                    }
                                    PXProcessing <SOOrder> .SetError(ex);
                                    anyfailed = true;
                                    continue;
                                }

                                List <int?> sites = new List <int?>();

                                if (filter.SiteID != null)
                                {
                                    sites.Add(filter.SiteID);
                                }
                                else
                                {
                                    foreach (SOShipmentPlan plan in PXSelectGroupBy <SOShipmentPlan, Where <SOShipmentPlan.orderType, Equal <Current <SOOrder.orderType> >, And <SOShipmentPlan.orderNbr, Equal <Current <SOOrder.orderNbr> > > >, Aggregate <GroupBy <SOShipmentPlan.siteID> >, OrderBy <Asc <SOShipmentPlan.siteID> > > .SelectMultiBound(docgraph, new object[] { order }))
                                    {
                                        sites.Add(plan.SiteID);
                                    }
                                }

                                foreach (int?SiteID in sites)
                                {
                                    ordercopy = (SOOrder)Base.Caches[typeof(SOOrder)].CreateCopy(order);
                                    try
                                    {
                                        using (var ts = new PXTransactionScope())
                                        {
                                            PXTimeStampScope.SetRecordComesFirst(typeof(SOOrder), true);
                                            docgraph.CreateShipment(order, SiteID, filter.ShipDate, adapter.MassProcess, operation, created, adapter.QuickProcessFlow);
                                            ts.Complete();
                                        }

                                        if (adapter.MassProcess)
                                        {
                                            PXProcessing <SOOrder> .SetProcessed();
                                        }
                                    }
                                    catch (SOShipmentException ex)
                                    {
                                        Base.Caches[typeof(SOOrder)].RestoreCopy(order, ordercopy);
                                        if (!adapter.MassProcess)
                                        {
                                            throw;
                                        }
                                        order.LastSiteID   = SiteID;
                                        order.LastShipDate = filter.ShipDate;
                                        order.Status       = SOOrderStatus.Shipping;

                                        docgraph.Clear();

                                        var ordergraph = PXGraph.CreateInstance <SOOrderEntry>();
                                        ordergraph.Clear();

                                        ordergraph.Document.Cache.MarkUpdated(order);
                                        PXAutomation.CompleteSimple(ordergraph.Document.View);
                                        try
                                        {
                                            ordergraph.Save.Press();
                                            PXAutomation.RemovePersisted(ordergraph, order);

                                            PXTrace.WriteInformation(ex);
                                            PXProcessing <SOOrder> .SetWarning(ex);
                                        }
                                        catch (Exception inner)
                                        {
                                            Base.Caches[typeof(SOOrder)].RestoreCopy(order, ordercopy);
                                            PXProcessing <SOOrder> .SetError(inner);
                                            anyfailed = true;
                                        }
                                    }
                                    catch (Exception ex)
                                    {
                                        Base.Caches[typeof(SOOrder)].RestoreCopy(order, ordercopy);
                                        docgraph.Clear();

                                        if (!adapter.MassProcess)
                                        {
                                            throw;
                                        }
                                        PXProcessing <SOOrder> .SetError(ex);
                                        anyfailed = true;
                                    }
                                }
                            }

                            if (adapter.AllowRedirect && !adapter.MassProcess && created.Count > 0)
                            {
                                using (new PXTimeStampScope(null))
                                {
                                    docgraph.Clear();
                                    docgraph.Document.Current = docgraph.Document.Search <SOShipment.shipmentNbr>(created[0].ShipmentNbr);
                                    throw new PXRedirectRequiredException(docgraph, "Shipment");
                                }
                            }

                            if (anyfailed)
                            {
                                throw new PXOperationCompletedWithErrorException(ErrorMessages.SeveralItemsFailed);
                            }
                        });
                }
                return(list);
            }

            default:
                return(baseMtd(adapter, actionID, shipDate, siteCD, operation, ActionName));
            }
        }
        public static void ReleasePayments(List <APPayment> list, string Action)
        {
            APReleaseChecks graph     = CreateInstance <APReleaseChecks>();
            APPaymentEntry  pe        = CreateInstance <APPaymentEntry>();
            bool            failed    = false;
            bool            successed = false;

            List <APRegister> docs = new List <APRegister>(list.Count);

            for (int i = 0; i < list.Count; i++)
            {
                if (list[i].Passed == true)
                {
                    graph.TimeStamp = pe.TimeStamp = list[i].tstamp;
                }

                switch (Action)
                {
                case "R":
                    list[i].Printed = true;
                    break;

                case "D":
                case "V":
                    list[i].ExtRefNbr = null;
                    list[i].Printed   = false;
                    break;

                default:
                    continue;
                }

                if ((bool)list[i].Printed)
                {
                    try
                    {
                        APPrintChecks.AssignNumbersWithNoAdditionalProcessing(pe, list[i]);
                        pe.Save.Press();

                        object[] persisted = PXTimeStampScope.GetPersisted(pe.Document.Cache, pe.Document.Current);
                        if (persisted == null || persisted.Length == 0)
                        {
                            //preserve timestamp which will be @@dbts after last record committed to db on previous Persist().
                            //otherwise another process updated APAdjust.
                            docs.Add(list[i]);
                        }
                        else
                        {
                            if (list[i].Passed == true)
                            {
                                pe.Document.Current.Passed = true;
                            }
                            docs.Add(pe.Document.Current);
                        }
                        successed = true;
                    }
                    catch (Exception e)
                    {
                        PXProcessing <APPayment> .SetError(i, e);

                        docs.Add(null);
                        failed = true;
                    }
                }
                else
                {
                    try
                    {
                        list[i].Hold = true;
                        // TODO: Need to rework. Use legal CRUD methods of caches!
                        graph.APPaymentList.Cache.PersistUpdated(list[i]);
                        graph.APPaymentList.Cache.Persisted(false);

                        graph.TimeStamp = PXDatabase.SelectTimeStamp();

                        // delete check numbers only if Reprint (not Void and Reprint)
                        PaymentMethod pm = pe.paymenttype.Select(list[i].PaymentMethodID);
                        if (pm.APPrintChecks == true && Action == "D")
                        {
                            APPayment doc = list[i];
                            new HashSet <string>(pe.Adjustments_Raw.Select(doc.DocType, doc.RefNbr, doc.LineCntr)
                                                 .RowCast <APAdjust>()
                                                 .Select(adj => adj.StubNbr))
                            .ForEach(nbr => PaymentRefAttribute.DeleteCheck((int)doc.CashAccountID, doc.PaymentMethodID, nbr));

                            // sync PaymentMethodAccount.APLastRefNbr with actual last CashAccountCheck number
                            PaymentMethodAccount det = graph.cashaccountdetail.SelectSingle(list[i].CashAccountID, list[i].PaymentMethodID);
                            PaymentRefAttribute.LastCashAccountCheckSelect.Clear(graph);
                            CashAccountCheck cacheck = PaymentRefAttribute.LastCashAccountCheckSelect.SelectSingleBound(graph, new object[] { det });
                            det.APLastRefNbr = cacheck == null ? null : cacheck.CheckNbr;
                            graph.cashaccountdetail.Cache.PersistUpdated(det);
                            graph.cashaccountdetail.Cache.Persisted(false);
                        }
                        // END TODO
                        if (string.IsNullOrEmpty(list[i].ExtRefNbr))
                        {
                            //try to get next number
                            graph.APPaymentList.Cache.SetDefaultExt <APPayment.extRefNbr>(list[i]);
                        }
                    }
                    catch (Exception e)
                    {
                        PXProcessing <APPayment> .SetError(i, e);
                    }
                    docs.Add(null);
                }
            }
            if (successed)
            {
                APDocumentRelease.ReleaseDoc(docs, true);
            }

            if (failed)
            {
                throw new PXException(GL.Messages.DocumentsNotReleased);
            }
        }
        public FSAppointment CalculateExternalTax(FSAppointment fsAppointment, FSServiceOrder order, bool forceRecalculate)
        {
            var toAddress = GetToAddress(order);

            var service = TaxProviderFactory(Base, fsAppointment.TaxZoneID);

            GetTaxRequest getRequest         = null;
            GetTaxRequest getRequestOpen     = null;
            GetTaxRequest getRequestUnbilled = null;
            GetTaxRequest getRequestFreight  = null;

            bool isValidByDefault = false;

            FSSrvOrdType srvOrdType = PXSelect <FSSrvOrdType, Where <FSSrvOrdType.srvOrdType, Equal <Required <FSAppointment.srvOrdType> > > > .Select(this.Base, fsAppointment.SrvOrdType);

            if (/*srvOrdType.INDocType != INTranType.Transfer &&*/ !IsNonTaxable(toAddress))
            {
                if (fsAppointment.IsTaxValid != true || forceRecalculate)
                {
                    getRequest = BuildGetTaxRequest(fsAppointment, order);

                    if (getRequest.CartItems.Count > 0)
                    {
                        isValidByDefault = false;
                    }
                    else
                    {
                        getRequest = null;
                    }
                }

                /*if (order.IsOpenTaxValid != true || forceRecalculate)
                 * {
                 *  getRequestOpen = BuildGetTaxRequestOpen(order);
                 *  if (getRequestOpen.CartItems.Count > 0)
                 *  {
                 *      isValidByDefault = false;
                 *  }
                 *  else
                 *  {
                 *      getRequestOpen = null;
                 *  }
                 * }*/

                /*if (order.IsUnbilledTaxValid != true || forceRecalculate)
                 * {
                 *  getRequestUnbilled = BuildGetTaxRequestUnbilled(order);
                 *  if (getRequestUnbilled.CartItems.Count > 0)
                 *  {
                 *      isValidByDefault = false;
                 *  }
                 *  else
                 *  {
                 *      getRequestUnbilled = null;
                 *  }
                 * }*/

                /*if (order.IsFreightTaxValid != true || forceRecalculate)
                 * {
                 *  getRequestFreight = BuildGetTaxRequestFreight(order);
                 *  if (getRequestFreight.CartItems.Count > 0)
                 *  {
                 *      isValidByDefault = false;
                 *  }
                 *  else
                 *  {
                 *      getRequestFreight = null;
                 *  }
                 * }*/
            }

            if (isValidByDefault)
            {
                fsAppointment.CuryTaxTotal = 0;
                //order.CuryOpenTaxTotal = 0;
                //order.CuryUnbilledTaxTotal = 0;
                fsAppointment.IsTaxValid = true;
                //order.IsOpenTaxValid = true;
                //order.IsUnbilledTaxValid = true;
                //order.IsFreightTaxValid = true;

                Base.AppointmentRecords.Update(fsAppointment);

                foreach (FSAppointmentTaxTran item in Base.Taxes.Select())
                {
                    Base.Taxes.Delete(item);
                }

                using (var ts = new PXTransactionScope())
                {
                    Base.Persist(typeof(FSAppointmentTaxTran), PXDBOperation.Delete);
                    Base.Persist(typeof(FSAppointment), PXDBOperation.Update);
                    PXTimeStampScope.PutPersisted(Base.AppointmentRecords.Cache, fsAppointment, PXDatabase.SelectTimeStamp());
                    ts.Complete();
                }
                return(fsAppointment);
            }

            GetTaxResult result         = null;
            GetTaxResult resultOpen     = null;
            GetTaxResult resultUnbilled = null;
            GetTaxResult resultFreight  = null;

            bool getTaxFailed = false;

            if (getRequest != null)
            {
                result = service.GetTax(getRequest);

                if (!result.IsSuccess)
                {
                    getTaxFailed = true;
                }
            }
            if (getRequestOpen != null)
            {
                if (getRequest != null && IsSame(getRequest, getRequestOpen))
                {
                    resultOpen = result;
                }
                else
                {
                    resultOpen = service.GetTax(getRequestOpen);

                    if (!resultOpen.IsSuccess)
                    {
                        getTaxFailed = true;
                    }
                }
            }
            if (getRequestUnbilled != null)
            {
                if (getRequest != null && IsSame(getRequest, getRequestUnbilled))
                {
                    resultUnbilled = result;
                }
                else
                {
                    resultUnbilled = service.GetTax(getRequestUnbilled);

                    if (!resultUnbilled.IsSuccess)
                    {
                        getTaxFailed = true;
                    }
                }
            }
            if (getRequestFreight != null)
            {
                resultFreight = service.GetTax(getRequestFreight);

                if (!resultFreight.IsSuccess)
                {
                    getTaxFailed = true;
                }
            }

            if (!getTaxFailed)
            {
                try
                {
                    ApplyTax(fsAppointment, result, resultOpen, resultUnbilled, resultFreight);
                }
                catch (PXOuterException ex)
                {
                    string msg = PX.Objects.TX.Messages.FailedToApplyTaxes;
                    foreach (string err in ex.InnerMessages)
                    {
                        msg += Environment.NewLine + err;
                    }

                    throw new PXException(ex, msg);
                }
                catch (Exception ex)
                {
                    string msg = PX.Objects.TX.Messages.FailedToApplyTaxes;
                    msg += Environment.NewLine + ex.Message;

                    throw new PXException(ex, msg);
                }
            }
            else
            {
                ResultBase taxResult = result ?? resultOpen ?? resultUnbilled ?? resultFreight;
                if (taxResult != null)
                {
                    LogMessages(taxResult);
                }

                throw new PXException(PX.Objects.TX.Messages.FailedToGetTaxes);
            }

            return(fsAppointment);
        }