예제 #1
0
        /// <summary>
        /// Search for the customer and add to the retailtransaction
        /// </summary>
        /// <param name="retailTransaction">The retail tranaction</param>
        public void Search(DE.IPosTransaction posTransaction)
        {
            // Show the search dialog
            DE.ICustomer customer = this.Search();

            AddCustomerToTransaction(customer, posTransaction);
        }
예제 #2
0
 public void SetProperties(DE.ICustomer parameterCustomer, DE.IAddress address)
 {
     this.viewModel = new AddressViewModel(address, parameterCustomer);
     this.customer  = parameterCustomer;
     this.viewAddressBindingSource.Clear();
     this.viewAddressBindingSource.Add(this.viewModel);
 }
예제 #3
0
 public void SetProperties(DE.ICustomer parameterCustomer, AddressViewModel parameterViewModel)
 {
     this.viewModel = parameterViewModel;
     this.customer  = parameterCustomer;
     this.viewAddressBindingSource.Clear();
     this.viewAddressBindingSource.Add(this.viewModel);
 }
예제 #4
0
        public void AuthorizeCustomerAccountPayment(ref bool valid, ref string comment, ref string manualAuthenticationCode, string customerId, decimal amount, DE.IRetailTransaction retailTransaction)
        {
            try
            {
                LSRetailPosis.ApplicationLog.Log(this.ToString(), "Customer.AuthorizeCustomerAccountPayment()", LSRetailPosis.LogTraceLevel.Trace);
                //Get the customer information for the customer
                DM.CustomerDataManager customerDataManager = new DM.CustomerDataManager(
                    ApplicationSettings.Database.LocalConnection, ApplicationSettings.Database.DATAAREAID);
                DE.ICustomer tempCust = customerDataManager.GetTransactionalCustomer(customerId);

                if (!string.IsNullOrEmpty(tempCust.InvoiceAccount))
                {
                    DE.ICustomer tempInvCust = customerDataManager.GetTransactionalCustomer(tempCust.InvoiceAccount);
                    if (tempInvCust.Blocked == DE.BlockedEnum.All)
                    {
                        tempCust.Blocked = tempInvCust.Blocked;
                    }
                    else if (tempInvCust.Blocked == DE.BlockedEnum.Invoice && tempCust.Blocked != DE.BlockedEnum.All)
                    {
                        tempCust.Blocked = DE.BlockedEnum.Invoice;
                    }
                }

                valid = true;

                if (LSRetailPosis.Settings.ApplicationSettings.Terminal.Standalone == true)
                {
                    decimal balance = customerDataManager.GetBalance(tempCust.CustomerId);
                    if (((balance * -1) + Convert.ToDecimal(amount)) > tempCust.CreditLimit)
                    {
                        valid   = false;
                        comment = LSRetailPosis.ApplicationLocalizer.Language.Translate(51007);  // The amount charged is higher than existing creditlimit
                    }
                    return;
                }

                // Using the transaction services to validate the transaction
                this.Application.TransactionServices.ValidateCustomerStatus(ref valid, ref comment, customerId, amount, retailTransaction.StoreCurrencyCode);
                if (comment.Length > 0)
                {
                    if (comment.Substring(0, 1) == "\t")
                    {
                        comment = comment.Remove(0, 1);
                    }
                }
            }
            catch (LSRetailPosis.PosisException px)
            {
                LSRetailPosis.ApplicationExceptionHandler.HandleException(this.ToString(), px);
                throw;
            }
            catch (Exception x)
            {
                LSRetailPosis.ApplicationExceptionHandler.HandleException(this.ToString(), x);
                throw;
            }
        }
예제 #5
0
        public DE.ICustomer AddNew(out string CustId, out string CustName, out string CustCurrency)
        {
            DE.ICustomer customer = null;
            DE.IAddress  address  = null;

            if (Application != null)
            {
                CustomerData custData = new CustomerData(Application.Settings.Database.Connection, Application.Settings.Database.DataAreaID);
            }
            else
            {
                CustomerData custData = new CustomerData(LSRetailPosis.Settings.ApplicationSettings.Database.LocalConnection, LSRetailPosis.Settings.ApplicationSettings.Database.DATAAREAID);
            }

            //CustomerData custData = new CustomerData(Application.Settings.Database.Connection, Application.Settings.Database.DataAreaID);

            customer = GetNewCustomerDefaults();
            address  = GetNewAddressDefaults(customer);
            using (frmNewCustomer newCustDialog = new frmNewCustomer(customer, address))
            {
                if (Application != null)
                {
                    this.Application.ApplicationFramework.POSShowForm(newCustDialog);
                    // customer = newCustDialog.Customer;
                    //address = newCustDialog.Address;
                }
                else
                {
                    Customer.InternalApplication.ApplicationFramework.POSShowForm(newCustDialog);

                    customer     = newCustDialog.Customer;
                    CustId       = customer.CustomerId;
                    CustName     = customer.Name;
                    CustCurrency = customer.Currency;
                    address      = newCustDialog.Address;
                }

                // this.Application.ApplicationFramework.POSShowForm(newCustDialog);

                if (newCustDialog.DialogResult == DialogResult.OK)
                {
                    customer     = newCustDialog.Customer;
                    CustId       = customer.CustomerId;
                    CustName     = customer.Name;
                    CustCurrency = customer.Currency;
                    address      = newCustDialog.Address;
                }
            }
            CustName     = customer.Name;
            CustId       = customer.CustomerId;
            CustCurrency = customer.Currency;
            return(customer);
        }
예제 #6
0
        public DE.IAddress SearchShippingAddress(DE.ICustomer customer)
        {
            DE.IAddress address = null;

            using (frmShippingAddressSearch searchShippingAddressDialog = new frmShippingAddressSearch(customer))
            {
                this.Application.ApplicationFramework.POSShowForm(searchShippingAddressDialog);

                if (searchShippingAddressDialog.DialogResult == DialogResult.OK)
                {
                    address = searchShippingAddressDialog.SelectedAddress;
                }
            }

            return(address);
        }
예제 #7
0
        public static DE.IAddress AddNewShippingAddress(DE.ICustomer customer)
        {
            DE.IAddress address = null;

            address = GetNewAddressDefaults(customer);
            using (frmNewShippingAddress dlg = new frmNewShippingAddress(customer, address))
            {
                InternalApplication.ApplicationFramework.POSShowForm(dlg);

                if (dlg.DialogResult == DialogResult.OK)
                {
                    address = dlg.Address;
                }
            }

            return(address);
        }
예제 #8
0
        private static DE.ICustomer GetNewCustomerDefaults()
        {
            DE.ICustomer customer = Customer.InternalApplication.BusinessLogic.Utility.CreateCustomer();

            SettingsData settingsData = new SettingsData(ApplicationSettings.Database.LocalConnection, ApplicationSettings.Database.DATAAREAID);

            using (DataTable storeData = settingsData.GetStoreInformation(ApplicationSettings.Terminal.StoreId))
            {
                if (storeData.Rows.Count > 0)
                {
                    customer.Country = storeData.Rows[0]["COUNTRYREGIONID"].ToString();
                }
            }
            customer.Currency     = ApplicationSettings.Terminal.StoreCurrency;
            customer.Language     = ApplicationSettings.Terminal.CultureName;
            customer.RelationType = DE.RelationType.Person;

            return(customer);
        }
예제 #9
0
        /// <summary>
        /// Invoke the 'Add Shipping Address' dialog to edit an existing address
        /// </summary>
        /// <param name="addressRecId">address rec id</param>
        /// <param name="existingCustomer">customer that this address is to be associated with</param>
        internal static DE.IAddress EditShippingAddress(long addressRecId, DE.ICustomer existingCustomer)
        {
            DM.CustomerDataManager customerDataManager = new DM.CustomerDataManager(
                ApplicationSettings.Database.LocalConnection,
                ApplicationSettings.Database.DATAAREAID);

            DE.IAddress address = customerDataManager.GetAddress(addressRecId);

            using (frmNewShippingAddress dlg = new frmNewShippingAddress(existingCustomer, address))
            {
                InternalApplication.ApplicationFramework.POSShowForm(dlg);

                if (dlg.DialogResult == DialogResult.OK)
                {
                    address = dlg.Address;
                }
            }
            return(address);
        }
예제 #10
0
        /// <summary>
        /// Updates the customer information in the database
        /// </summary>
        /// <param name="customerId">The customer id</param>
        /// <returns>Returns the updated customer if succeded, null otherwise</returns>
        public DE.ICustomer UpdateCustomer(string customerId)
        {
            DM.CustomerDataManager customerDataManager = new DM.CustomerDataManager(
                ApplicationSettings.Database.LocalConnection, ApplicationSettings.Database.DATAAREAID);

            DE.ICustomer customer = customerDataManager.GetTransactionalCustomer(customerId);
            DE.IAddress  address  = customerDataManager.GetAddress(customer.PrimaryAddress.Id);

            using (frmNewCustomer newCustDialog = new frmNewCustomer(customer, address))
            {
                this.Application.ApplicationFramework.POSShowForm(newCustDialog);

                if (newCustDialog.DialogResult == DialogResult.OK)
                {
                    return(customer);
                }
            }

            return(null);
        }
예제 #11
0
        /// <summary>
        /// Register information about a new customer into the database
        /// </summary>
        /// <returns>Returns new customer of successful, null otherwise</returns>
        public DE.ICustomer AddNew()
        {
            DE.ICustomer customer = null;
            DE.IAddress  address  = null;

            CustomerData custData = new CustomerData(Application.Settings.Database.Connection, Application.Settings.Database.DataAreaID);

            customer = GetNewCustomerDefaults();
            address  = GetNewAddressDefaults(customer);
            using (frmNewCustomer newCustDialog = new frmNewCustomer(customer, address))
            {
                this.Application.ApplicationFramework.POSShowForm(newCustDialog);

                if (newCustDialog.DialogResult == DialogResult.OK)
                {
                    customer = newCustDialog.Customer;
                    address  = newCustDialog.Address;
                }
            }

            return(customer);
        }
예제 #12
0
        /// <summary>
        /// Displays UI to enter a customer ID and returns the customer based on the customer ID entered.
        /// </summary>
        /// <returns>Customer if found, otherwise null</returns>
        public DE.ICustomer GetCustomer()
        {
            DE.ICustomer customer = null;

            InputConfirmation inputConfirmation = new InputConfirmation()
            {
                MaxLength  = 30,
                PromptText = LSRetailPosis.ApplicationLocalizer.Language.Translate(3060), // "Enter a customer id.";
            };

            InteractionRequestedEventArgs request = new InteractionRequestedEventArgs(inputConfirmation, () =>
            {
                if (inputConfirmation.Confirmed)
                {
                    customer = this.CustomerSystem.GetCustomerInfo(inputConfirmation.EnteredText);
                }
            }
                                                                                      );

            InternalApplication.Services.Interaction.InteractionRequest(request);

            return(customer);
        }
예제 #13
0
        private static DE.IAddress GetNewAddressDefaults(DE.ICustomer customer)
        {
            DE.IAddress address = Customer.InternalApplication.BusinessLogic.Utility.CreateAddress();

            address.AddressType        = DE.AddressType.Home;
            address.BuildingComplement = (customer.AddressComplement) ?? string.Empty;
            address.City          = (customer.City) ?? string.Empty;
            address.CNPJCPFNumber = (customer.CNPJCPFNumber) ?? string.Empty;
            address.Country       = (customer.Country) ?? string.Empty;
            address.County        = string.Empty;       // We don't allow user to input/modify this field in UI; so keep this empty.
            address.DistrictName  = (customer.DistrictName) ?? string.Empty;
            address.Email         = (customer.Email) ?? string.Empty;
            address.OrgId         = (customer.OrgId) ?? string.Empty;
            address.PostalCode    = (customer.PostalCode) ?? string.Empty;
            address.State         = (customer.State) ?? string.Empty;
            address.Telephone     = (customer.Telephone) ?? string.Empty;
            address.SalesTaxGroup = (customer.SalesTaxGroup) ?? string.Empty;
            address.StreetName    = (customer.StreetName) ?? string.Empty;
            address.StreetNumber  = (customer.AddressNumber) ?? string.Empty;
            address.URL           = (customer.WwwAddress) ?? string.Empty;

            return(address);
        }
예제 #14
0
        internal static void UpdateCustomer(ref bool retValue, ref string comment, ref DE.ICustomer customer, ref IList <Int64> entityKeys)
        {
            if (customer == null)
            {
                throw new ArgumentNullException("customer");
            }

            string partyName = null;

            switch (customer.RelationType)
            {
            case DE.RelationType.Person:
                // send party name in fixed format
                partyName = string.Format("{0} {1} {2}",
                                          (customer.FirstName) ?? string.Empty,
                                          (customer.MiddleName) ?? string.Empty,
                                          (customer.LastName) ?? string.Empty);

                if (string.IsNullOrWhiteSpace(partyName))
                {
                    partyName = customer.Name;
                }
                break;

            default:
                partyName = customer.Name;
                break;
            }

            // Some of the parameters has been disabled, as they don't currently have corresponding values in the SDK, only the party name is being set.
            object[] parameterList = new object[]
            {
                customer.RecordId,
                partyName,
                customer.CustGroup,
                customer.Currency,
                customer.Language,
                customer.Telephone,
                customer.TelephoneId,
                customer.MobilePhone,
                customer.Email,
                customer.EmailId,
                customer.WwwAddress,
                customer.UrlId,
                customer.MultiLineDiscountGroup,
                customer.TotalDiscountGroup,
                customer.LineDiscountGroup,
                customer.PriceGroup,
                customer.SalesTaxGroup,
                customer.CreditLimit,
                (int)customer.Blocked,
                (customer.OrgId) ?? string.Empty,
                customer.UsePurchRequest,
                customer.VatNum,
                customer.InvoiceAccount == null ? string.Empty : customer.InvoiceAccount,
                customer.MandatoryCreditLimit,
                customer.ContactPerson,
                customer.UseOrderNumberReference,
                (int)customer.ReceiptSettings,
                customer.ReceiptEmailAddress,
                (customer.IdentificationNumber) ?? string.Empty
            };

            ReadOnlyCollection <object> containerArray = InternalApplication.TransactionServices.Invoke("UpdateCustomer", parameterList);

            try
            {
                retValue = (bool)containerArray[1];
                comment  = (string)containerArray[2];

                if (retValue && containerArray.Count > 3)   //container array puts data starting at index 3 - check for data being present
                {
                    customer.CustomerId    = Utility.ToStr(containerArray[3]);
                    customer.SalesTaxGroup = Utility.ToStr(containerArray[4]);
                    customer.PartyId       = Utility.ToInt64(containerArray[5]);
                    customer.RecordId      = Utility.ToStr(containerArray[6]);

                    if (entityKeys == null)
                    {
                        entityKeys = new List <Int64>(containerArray.Count - 5);
                    }

                    entityKeys.Clear();

                    // save into entity keys collection, the data needed for saving the customer starting @ PartyId
                    for (int i = 5; i < containerArray.Count; i++)
                    {
                        entityKeys.Add(Utility.ToInt64(containerArray[i]));
                    }
                }
            }
            catch (Exception ex)
            {
                LSRetailPosis.ApplicationExceptionHandler.HandleException("LSRetailPosis.TransactionServices.UpdateCustomer", ex);
            }
        }
예제 #15
0
        /// <summary>
        /// Add customer to transaction
        /// </summary>
        /// <param name="customer">Customer to add</param>
        /// <param name="posTransaction">Transaction</param>
        public void AddCustomerToTransaction(DE.ICustomer customer, DE.IPosTransaction posTransaction)
        {
            // !! Note - this code should follow the same steps to set the customer as PosProcesses\Customer.cs :: Execute()
            //Get information about the selected customer and add it to the transaction
            if (customer != null)
            {
                SalesOrderTransaction soTransaction = posTransaction as SalesOrderTransaction;
                if (soTransaction != null)
                {
                    // Must check for ISalesOrderTransaction before IRetailTransaction because it derives from IRetailTransaction
                    soTransaction.Customer = customer as LSRetailPosis.Transaction.Customer;
                }
                else
                {
                    RetailTransaction asRetailTransaction = posTransaction as RetailTransaction;
                    if (asRetailTransaction != null)
                    {
                        if (!asRetailTransaction.IsCustomerAllowed())
                        {
                            LSRetailPosis.POSProcesses.POSFormsManager.ShowPOSMessageDialog(4544);
                            return;
                        }

                        DE.ICustomer invoicedCustomer = customer;
                        string       invoiceAccount   = customer.InvoiceAccount;

                        //If the customer has another account as invoice account
                        if (!string.IsNullOrWhiteSpace(invoiceAccount))
                        {
                            invoicedCustomer = this.CustomerSystem.GetCustomerInfo(invoiceAccount);
                        }

                        // Trigger: PreCustomerSet trigger for the operation
                        var preTriggerResult = new PreTriggerResult();

                        PosApplication.Instance.Triggers.Invoke <ICustomerTrigger>(t => t.PreCustomerSet(preTriggerResult, posTransaction, customer.CustomerId));

                        if (!TriggerHelpers.ProcessPreTriggerResults(preTriggerResult))
                        {
                            return;
                        }

                        this.CustomerSystem.SetCustomer(asRetailTransaction, customer, invoicedCustomer);

                        //If CheckCustomer returns false then the customer isn't allowed to be added to the transaction. Msg has already been displayed
                        if (!CheckCustomer(posTransaction))
                        {
                            return;
                        }

                        //If CheckInvoicedCustomer removed the customer then it isn't allowed to be added to the transaction. Msg has already been displayed
                        if (!CheckInvoicedCustomer(posTransaction))
                        {
                            return;
                        }

                        if (asRetailTransaction.Customer.UsePurchRequest)
                        {
                            asRetailTransaction.CustomerPurchRequestId = GetPurchRequestId();
                        }
                    }
                    else if (posTransaction is CustomerPaymentTransaction)
                    {
                        // Customer is not allowed to be changed  (or cleared) once a customer account deposit has been made.
                        LSRetailPosis.POSProcesses.POSFormsManager.ShowPOSMessageDialog(3084);
                    }
                }
            }
            else
            {
                NetTracer.Warning("Customer::AddCustomerToTransaction: customer parameter is null");
            }
        }
예제 #16
0
        internal static CustomerOrderTransaction GetTransactionFromInfo(CustomerOrderInfo orderInfo, SalesOrder salesOrderService)
        {
            CustomerOrderTransaction transaction = (CustomerOrderTransaction)SalesOrder.InternalApplication.BusinessLogic.Utility.CreateCustomerOrderTransaction(
                ApplicationSettings.Terminal.StoreId,
                ApplicationSettings.Terminal.StoreCurrency,
                ApplicationSettings.Terminal.TaxIncludedInPrice,
                SalesOrder.InternalApplication.Services.Rounding,
                salesOrderService);

            // Get all the defaults
            SalesOrder.InternalApplication.BusinessLogic.TransactionSystem.LoadTransactionStatus(transaction);

            // General header properties
            transaction.OrderId   = orderInfo.Id;
            transaction.OrderType = orderInfo.OrderType;

            if (orderInfo.OrderType == CustomerOrderType.Quote)
            {
                transaction.QuotationId = orderInfo.Id;
            }

            transaction.OriginalOrderType = orderInfo.OrderType;

            switch (orderInfo.OrderType)
            {
            case CustomerOrderType.Quote:
                transaction.OrderStatus = GetSalesStatus((SalesQuotationStatus)orderInfo.Status);
                break;

            case CustomerOrderType.SalesOrder:
                transaction.OrderStatus = GetSalesStatus((SalesOrderStatus)orderInfo.Status, (DocumentStatus)orderInfo.DocumentStatus);
                break;

            default:
                transaction.OrderStatus = SalesStatus.Unknown;
                NetTracer.Information("SalesOrder::CustomerOrderTransaction: CustomerOrderInfo OrderType is unknown: {0}", orderInfo.OrderType);
                break;
            }

            transaction.LockPrices = true;

            transaction.ExpirationDate = ParseDateString(orderInfo.ExpiryDateString, DateTime.Today);

            // RequestedDeliveryDate is directly input from user. It is stored in the local timezone
            transaction.RequestedDeliveryDate = ParseDateString(orderInfo.RequestedDeliveryDateString, DateTime.Today);

            // CreationDate is stored in UTC. It needs to be converted to local time zone where order is accessed.
            ((IPosTransactionV2)transaction).BeginDateTime = ParseDateString(orderInfo.CreationDateString, DateTime.UtcNow, DateTimeStyles.AdjustToUniversal).ToLocalTime();
            transaction.LocalHourOfDay = orderInfo.LocalHourOfDay;

            ((IPosTransactionV2)transaction).Comment = orderInfo.Comment;

            // Header delivery
            DM.StoreDataManager storeDataManager = new DM.StoreDataManager(
                SalesOrder.InternalApplication.Settings.Database.Connection,
                SalesOrder.InternalApplication.Settings.Database.DataAreaID);

            transaction.WarehouseId  = orderInfo.WarehouseId;
            transaction.DeliveryMode = storeDataManager.GetDeliveryMode(orderInfo.DeliveryMode);
            transaction.CurrencyCode = orderInfo.CurrencyCode;

            foreach (var code in orderInfo.DiscountCodes)
            {
                transaction.DiscountCodes.AddLast(code);
            }

            // Header affiliation
            DM.AffiliationDataManager affiliationDataManager = new DM.AffiliationDataManager(
                SalesOrder.InternalApplication.Settings.Database.Connection,
                SalesOrder.InternalApplication.Settings.Database.DataAreaID);

            if (orderInfo.Affiliations != null && orderInfo.Affiliations.Any())
            {
                foreach (AffiliationInfo affiliationInfo in orderInfo.Affiliations)
                {
                    transaction.AffiliationLines.AddLast(
                        new AffiliationItem()
                    {
                        RecId           = affiliationInfo.AffiliationId,
                        LoyaltyTier     = affiliationInfo.LoyaltyTierId,
                        AffiliationType = affiliationInfo.AffiliationType
                    });
                }
            }

            // Customer info
            ICustomerSystem customerSystem = SalesOrder.InternalApplication.BusinessLogic.CustomerSystem;

            DM.CustomerDataManager customerDataManager = new DM.CustomerDataManager(
                SalesOrder.InternalApplication.Settings.Database.Connection,
                SalesOrder.InternalApplication.Settings.Database.DataAreaID);

            DE.ICustomer customer = customerSystem.GetCustomerInfo(orderInfo.CustomerAccount);

            // try to get the customer from transaction service
            if (customer == null || customer.IsEmptyCustomer())
            {
                DE.ICustomer tempCustomer = SalesOrder.GetCustomerFromAX(orderInfo.CustomerAccount, customerSystem, customerDataManager);
                if (tempCustomer != null)
                {
                    customer = tempCustomer;
                }
            }

            DE.ICustomer invoicedCustomer = customerSystem.GetCustomerInfo(customer.InvoiceAccount);

            // try to get the invoicedCustomer from transaction service
            if (invoicedCustomer == null || invoicedCustomer.IsEmptyCustomer())
            {
                DE.ICustomer tempinvoicedCustomer = SalesOrder.GetCustomerFromAX(customer.InvoiceAccount, customerSystem, customerDataManager);
                if (tempinvoicedCustomer != null)
                {
                    invoicedCustomer = tempinvoicedCustomer;
                }
            }

            // If InvoiceCustomer is *still* blank/empty then fallback to Customer so that the UI fields are populated.
            if (invoicedCustomer == null || invoicedCustomer.IsEmptyCustomer())
            {
                invoicedCustomer = customer;
            }

            customerSystem.SetCustomer(transaction, customer, invoicedCustomer);

            if (transaction.DeliveryMode != null && !string.IsNullOrWhiteSpace(orderInfo.AddressRecordId))
            {
                DE.IAddress shippingAddress = customerDataManager.GetAddress(Int64.Parse(orderInfo.AddressRecordId));
                customerSystem.SetShippingAddress(transaction, shippingAddress);
            }

            if (!string.IsNullOrEmpty(orderInfo.SalespersonStaffId))
            {
                // Sets the sales person id and name according to AX values
                // This is done because we do not know whether the sales person information is available on this store
                transaction.SalesPersonId   = orderInfo.SalespersonStaffId;
                transaction.SalesPersonName = orderInfo.SalespersonName;

                DM.EmployeeDataManager employees = new DM.EmployeeDataManager(
                    SalesOrder.InternalApplication.Settings.Database.Connection,
                    SalesOrder.InternalApplication.Settings.Database.DataAreaID);

                Employee employee = employees.GetEmployee(ApplicationSettings.Terminal.StoreId, orderInfo.SalespersonStaffId);
                if (employee != null)
                {
                    transaction.SalesPersonId            = employee.StaffId;
                    transaction.SalesPersonName          = employee.Name;
                    transaction.SalesPersonNameOnReceipt = employee.NameOnReceipt;
                }
            }

            transaction.ChannelReferenceId = orderInfo.ChannelReferenceId;
            if (transaction.LoyaltyItem != null && !string.IsNullOrEmpty(orderInfo.LoyaltyCardId))
            {
                transaction.LoyaltyItem.LoyaltyCardNumber = orderInfo.LoyaltyCardId;
            }

            transaction.ReceiptEmailAddress = orderInfo.Email;

            transaction.TotalManualDiscountAmount = orderInfo.TotalManualDiscountAmount;
            transaction.TotalManualPctDiscount    = orderInfo.TotalManualDiscountPercentage;

            DateTime earliestDeliveryDate = DateTime.MaxValue;

            // Items
            foreach (ItemInfo item in orderInfo.Items)
            {
                Collection <Tax.MiscellaneousCharge> lineCharges = new Collection <Tax.MiscellaneousCharge>();
                foreach (ChargeInfo charge in item.Charges)
                {
                    Tax.MiscellaneousCharge lineCharge = (Tax.MiscellaneousCharge)SalesOrder.InternalApplication.BusinessLogic.Utility.CreateMiscellaneousCharge(
                        charge.Amount, charge.SalesTaxGroup, charge.TaxGroup, charge.Code, string.Empty, transaction);
                    lineCharges.Add(lineCharge);
                }

                // add item
                SaleLineItem lineItem = (SaleLineItem)SalesOrder.InternalApplication.BusinessLogic.Utility.CreateSaleLineItem(
                    ApplicationSettings.Terminal.StoreCurrency,
                    SalesOrder.InternalApplication.Services.Rounding,
                    transaction);

                lineItem.Found                        = true;
                lineItem.OrderLineRecordId            = item.RecId;
                lineItem.ItemId                       = item.ItemId;
                lineItem.Quantity                     = item.Quantity;
                lineItem.ReturnQtyAllowed             = item.Quantity;
                lineItem.SalesOrderUnitOfMeasure      = item.Unit;
                lineItem.Price                        = item.Price;
                lineItem.NetAmount                    = item.NetAmount;
                lineItem.QuantityOrdered              = item.Quantity;
                lineItem.QuantityPickedUp             = item.QuantityPicked;
                lineItem.DeliveryMode                 = storeDataManager.GetDeliveryMode(item.DeliveryMode);
                lineItem.DeliveryDate                 = ParseDateString(item.RequestedDeliveryDateString, DateTime.Today);
                lineItem.DeliveryStoreNumber          = item.StoreId;
                lineItem.DeliveryWarehouse            = item.WarehouseId;
                lineItem.SerialId                     = item.SerialId;
                lineItem.BatchId                      = item.BatchId;
                lineItem.HasBeenRecalled              = true;
                lineItem.SalesMarkup                  = item.SalesMarkup;
                lineItem.Comment                      = string.IsNullOrEmpty(item.Comment) ? string.Empty : item.Comment;
                lineItem.LineStatus                   = GetSalesStatus((SalesOrderStatus)item.Status);
                lineItem.LineDiscount                 = item.LineDscAmount;
                lineItem.PeriodicDiscount             = item.PeriodicDiscount;
                lineItem.PeriodicPctDiscount          = item.PeriodicPercentageDiscount;
                lineItem.LineManualDiscountAmount     = item.LineManualDiscountAmount;
                lineItem.LineManualDiscountPercentage = item.LineManualDiscountPercentage;
                lineItem.TotalDiscount                = item.TotalDiscount;
                lineItem.TotalPctDiscount             = item.TotalPctDiscount;

                foreach (Tax.MiscellaneousCharge charge in lineCharges)
                {
                    lineItem.MiscellaneousCharges.Add(charge);
                }

                if (lineItem.DeliveryMode != null && !string.IsNullOrWhiteSpace(item.AddressRecordId))
                {
                    lineItem.ShippingAddress = customerDataManager.GetAddress(Int64.Parse(item.AddressRecordId));
                }

                lineItem.Dimension.VariantId  = item.VariantId;
                lineItem.Dimension.ColorId    = item.ColorId;
                lineItem.Dimension.StyleId    = item.StyleId;
                lineItem.Dimension.SizeId     = item.SizeId;
                lineItem.Dimension.ConfigId   = item.ConfigId;
                lineItem.Dimension.ColorName  = item.ColorName;
                lineItem.Dimension.StyleName  = item.StyleName;
                lineItem.Dimension.SizeName   = item.SizeName;
                lineItem.Dimension.ConfigName = item.ConfigName;

                if (!string.IsNullOrEmpty(lineItem.Dimension.VariantId))
                {
                    Dimensions dimension = (Dimensions)SalesOrder.InternalApplication.BusinessLogic.Utility.CreateDimension();
                    dimension.VariantId = lineItem.Dimension.VariantId;
                    SalesOrder.InternalApplication.Services.Dimension.GetDimensionForVariant(dimension);
                    lineItem.Dimension = dimension;
                }

                if (item.Discounts.Count > 0)
                {
                    lineItem.QuantityDiscounted = item.Quantity;
                    lineItem.LinePctDiscount    = lineItem.CalculateLinePercentDiscount();
                }

                // create discount line from discount info object
                foreach (DiscountInfo discountInfo in item.Discounts)
                {
                    DiscountItem discountItem = ConvertToDiscountItem(
                        discountInfo.DiscountOriginType,
                        discountInfo.ManualDiscountType,
                        discountInfo.CustomerDiscountType,
                        discountInfo.EffectiveAmount,
                        discountInfo.DealPrice,
                        discountInfo.DiscountAmount,
                        discountInfo.Percentage,
                        discountInfo.PeriodicDiscountOfferId,
                        discountInfo.OfferName,
                        discountInfo.DiscountCode);

                    SalesOrder.InternalApplication.Services.Discount.AddDiscountLine(lineItem, discountItem);
                }

                // Set other default properties for this item
                SalesOrder.InternalApplication.Services.Item.ProcessItem(lineItem, bypassSerialNumberEntry: true);

                // Set tax info after defaults, as it may have been overridden.
                lineItem.SalesTaxGroupId         = item.SalesTaxGroup;
                lineItem.SalesTaxGroupIdOriginal = item.SalesTaxGroup;
                lineItem.TaxGroupId         = item.ItemTaxGroup;
                lineItem.TaxGroupIdOriginal = item.ItemTaxGroup;

                // Add it to the transaction
                transaction.Add(lineItem);

                if (lineItem.DeliveryDate < earliestDeliveryDate)
                {
                    earliestDeliveryDate = lineItem.DeliveryDate.HasValue ? lineItem.DeliveryDate.Value : earliestDeliveryDate;
                }
            }

            // Once Items are populated - Reset Customer Tax Group
            //GRW Linea comentada para poder recoger la orden de venta en una tienda distinta a la configurada en AX
            //customerSystem.ResetCustomerTaxGroup(transaction);

            // The order can be created through some other channel other than POS which has set header delivery date as NoDate.
            // This must not be interpreted as a valid date. Instead the earliestDeliveryDate is used.
            if (transaction.RequestedDeliveryDate == NoDate)
            {
                transaction.RequestedDeliveryDate = earliestDeliveryDate;
            }

            // Charges
            foreach (ChargeInfo charge in orderInfo.Charges)
            {
                // add charges
                Tax.MiscellaneousCharge newCharge = (Tax.MiscellaneousCharge)SalesOrder.InternalApplication.BusinessLogic.Utility.CreateMiscellaneousCharge(
                    charge.Amount, charge.SalesTaxGroup, charge.TaxGroup, charge.Code, string.Empty, transaction);
                transaction.Add(newCharge);
            }

            SalesOrder.InternalApplication.BusinessLogic.ItemSystem.CalculatePriceTaxDiscount(transaction);
            transaction.CalculateAmountDue();

            // Payments
            // - total up amounts
            // - add history entries
            transaction.PrepaymentAmountPaid     = decimal.Zero;
            transaction.PrepaymentAmountInvoiced = decimal.Zero;
            decimal nonPrepayments = decimal.Zero;

            PaymentInfo pinfo = new PaymentInfo();

            pinfo.Amount   = -111;
            pinfo.Currency = "MXN";
            orderInfo.Payments.Add(pinfo);

            foreach (PaymentInfo payment in orderInfo.Payments)
            {
                // sum up payments
                decimal amount = (string.IsNullOrWhiteSpace(payment.Currency))
                    ? payment.Amount
                    : (SalesOrder.InternalApplication.Services.Currency.CurrencyToCurrency(
                           payment.Currency,
                           ApplicationSettings.Terminal.StoreCurrency,
                           payment.Amount));

                if (payment.Prepayment)
                {
                    // Sum prepayments to track total deposits paid
                    transaction.PrepaymentAmountPaid += amount;
                }
                else
                {
                    // Sum non-prepayments as base for calculating deposits applied to pickups
                    nonPrepayments += amount;
                }

                CustomerOrderPaymentHistory paymentHistory = (CustomerOrderPaymentHistory)SalesOrder.InternalApplication.BusinessLogic.Utility.CreateCustomerOrderPaymentHistory();
                paymentHistory.Amount   = payment.Amount;
                paymentHistory.Currency = payment.Currency;
                paymentHistory.Date     = ParseDateString(payment.DateString, DateTime.MinValue);
                paymentHistory.Balance  = transaction.NetAmountWithTaxAndCharges - transaction.PrepaymentAmountPaid;

                transaction.PaymentHistory.Add(paymentHistory);
            }

            // Prepayment/Deposit override info
            transaction.PrepaymentAmountOverridden = orderInfo.PrepaymentAmountOverridden;
            if (transaction.PrepaymentAmountOverridden)
            {
                transaction.PrepaymentAmountRequired = transaction.PrepaymentAmountPaid;
            }

            // Amount that has been previously invoiced (picked-up)
            transaction.PreviouslyInvoicedAmount = orderInfo.PreviouslyInvoicedAmount;

            // Portion of the prepayment that has been applied to invoices.
            // If .PrepaymentAmountApplied is non-NULL then use the explicit amount, otherwise fall back to computing the amount based on payment history.
            transaction.PrepaymentAmountInvoiced = orderInfo.PrepaymentAmountApplied
                                                   ?? (transaction.PreviouslyInvoicedAmount - nonPrepayments);

            transaction.HasLoyaltyPayment = orderInfo.HasLoyaltyPayment;

            return(transaction);
        }