/// <summary>
            /// Get the tender type configuration by identifier.
            /// </summary>
            /// <param name="context">The request context.</param>
            /// <param name="tenderTypeId">The id of tender type.</param>
            /// <returns>The matching tender type.</returns>
            private static TenderType GetTenderType(RequestContext context, string tenderTypeId)
            {
                var dataServiceRequest = new GetChannelTenderTypesDataRequest(context.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                var response           = context.Execute <EntityDataServiceResponse <TenderType> >(dataServiceRequest);

                return(response.PagedEntityCollection.Results.SingleOrDefault(channelTenderType => string.Equals(channelTenderType.TenderTypeId, tenderTypeId, StringComparison.OrdinalIgnoreCase)));
            }
Exemple #2
0
            /// <summary>
            /// Retrieves the tender removal tender type identifier.
            /// </summary>
            /// <param name="context">Request context.</param>
            /// <returns>The tender type identifier for tender removal type.</returns>
            private string GetTenderRemovalTypeIdentifier(RequestContext context)
            {
                string tenderRemovalTypeId = "-1";  // initialize tender removal type id to -1 as EPOS does
                int    function            = 4;     // initialize function to 4 as EPOS does

                var getChannelTenderTypesDataRequest = new GetChannelTenderTypesDataRequest(context.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                var tenderTypes = context.Runtime.Execute <EntityDataServiceResponse <TenderType> >(getChannelTenderTypesDataRequest, context).PagedEntityCollection;

                if (tenderTypes != null)
                {
                    tenderRemovalTypeId = tenderTypes.Results.Where(tenderType => tenderType.Function == function).Select(tenderType => tenderType.TenderTypeId).FirstOrDefault();
                }

                return(tenderRemovalTypeId);
            }
Exemple #3
0
            /// <summary>
            /// Round for channel payment method.
            /// </summary>
            /// <param name="request">Service request.</param>
            /// <returns>Rounded value.</returns>
            private GetRoundedValueServiceResponse GetPaymentRoundedValue(GetPaymentRoundedValueServiceRequest request)
            {
                GetChannelTenderTypesDataRequest       dataServiceRequest = new GetChannelTenderTypesDataRequest(request.RequestContext.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                EntityDataServiceResponse <TenderType> response           = request.RequestContext.Execute <EntityDataServiceResponse <TenderType> >(dataServiceRequest);

                TenderType tenderType = response.PagedEntityCollection.Results.SingleOrDefault(channelTenderType => string.Equals(channelTenderType.TenderTypeId, request.TenderTypeId, StringComparison.OrdinalIgnoreCase));

                RoundingMethod roundingMethod = tenderType.RoundingMethod;

                if (roundingMethod == RoundingMethod.None)
                {
                    return(new GetRoundedValueServiceResponse(request.Value));
                }

                decimal currencyUnit = tenderType.RoundOff;

                if (currencyUnit == decimal.Zero)
                {
                    currencyUnit = Rounding.DefaultRoundingValue;
                }

                decimal roundedValue;

                if (request.IsChange)
                {
                    // For change rounding up/down should be applied in opposite direction.
                    if (roundingMethod == RoundingMethod.Down)
                    {
                        roundingMethod = RoundingMethod.Up;
                    }
                    else if (roundingMethod == RoundingMethod.Up)
                    {
                        roundingMethod = RoundingMethod.Down;
                    }
                }

                // Using absolute value so payment and refund is rounded same way when rounding up or down.
                decimal absoluteAmount = Math.Abs(request.Value);

                roundedValue = Rounding.RoundToUnit(absoluteAmount, currencyUnit, roundingMethod);
                if (request.Value < 0)
                {
                    // Revert sign back to original.
                    roundedValue = decimal.Negate(roundedValue);
                }

                return(new GetRoundedValueServiceResponse(roundedValue));
            }
            /// <summary>
            /// Retrieves the cash tender type identifier.
            /// </summary>
            /// <param name="context">The request context.</param>
            /// <returns>The tender type identifier for cash tender type.</returns>
            private static string GetCashTenderTypeIdentifier(RequestContext context)
            {
                string cashTenderTypeId   = null;
                int    payCashOperationId = (int)RetailOperation.PayCash;

                var dataServiceRequest = new GetChannelTenderTypesDataRequest(context.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                EntityDataServiceResponse <TenderType> dataServiceResponse = context.Execute <EntityDataServiceResponse <TenderType> >(dataServiceRequest);
                ReadOnlyCollection <TenderType>        tenderTypes         = dataServiceResponse.PagedEntityCollection.Results;

                if (tenderTypes != null)
                {
                    cashTenderTypeId = tenderTypes.Where(t => t.OperationId == payCashOperationId).Select(t => t.TenderTypeId).FirstOrDefault();
                }

                return(cashTenderTypeId != null ? cashTenderTypeId : "-1"); // Defaulting to -1, same as EPOS
            }
Exemple #5
0
            /// <summary>
            /// Customer account deposit transactions cannot be tendered with the 'On Account' payment method.
            /// </summary>
            /// <param name="context">The context.</param>
            /// <param name="transaction">The transaction.</param>
            /// <param name="tenderLineBase">The tender line.</param>
            public static void ValidateCustomerAccountDepositPaymentRestrictions(RequestContext context, SalesTransaction transaction, TenderLineBase tenderLineBase)
            {
                if (transaction.CartType != CartType.AccountDeposit)
                {
                    return;
                }

                var        getChannelTenderTypesDataRequest = new GetChannelTenderTypesDataRequest(context.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                var        tenderTypes = context.Runtime.Execute <EntityDataServiceResponse <TenderType> >(getChannelTenderTypesDataRequest, context).PagedEntityCollection.Results;
                TenderType tenderType  = tenderTypes.Single(t => t.TenderTypeId.Equals(tenderLineBase.TenderTypeId));

                // It should not be allowed to pay with and deposit to the same customer account.
                if (tenderType.OperationType == RetailOperation.PayCustomerAccount &&
                    tenderLineBase.CustomerId.Equals(transaction.CustomerId))
                {
                    throw new DataValidationException(DataValidationErrors.Microsoft_Dynamics_Commerce_Runtime_CannotPayForCustomerAccountDepositWithCustomerAccountPaymentMethod, "Customer account deposit transactions cannot be tendered with the 'On Account' payment method.");
                }
            }
            /// <summary>
            /// Gets the tender types for the channel.
            /// </summary>
            /// <param name="context">The request context.</param>
            /// <returns>The dictionary of tender types where key is tender type identifier, and value is tender type object.</returns>
            private static Dictionary <string, TenderType> GetChannelTenderTypes(RequestContext context)
            {
                long channelId          = context.GetPrincipal().ChannelId;
                var  dataServiceRequest = new GetChannelTenderTypesDataRequest(channelId, QueryResultSettings.AllRecords);
                EntityDataServiceResponse <TenderType> dataServiceResponse = context.Runtime.Execute <EntityDataServiceResponse <TenderType> >(dataServiceRequest, context);
                ReadOnlyCollection <TenderType>        tenderTypes         = dataServiceResponse.PagedEntityCollection.Results;

                if (tenderTypes == null)
                {
                    throw new DataValidationException(
                              DataValidationErrors.Microsoft_Dynamics_Commerce_Runtime_ObjectNotFound,
                              string.Format("The tender types of channel {0} was not found.", channelId));
                }

                var tenderTypeDict = tenderTypes.ToDictionary(t => t.TenderTypeId, t => t);

                return(tenderTypeDict);
            }
            private static Dictionary <RetailOperation, List <TenderLine> > MapRetailOperationToTenderLine(RequestContext context, Collection <TenderLine> tenderLines)
            {
                var getChannelTenderTypesDataRequest = new GetChannelTenderTypesDataRequest(context.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                var channelTenderTypes = context.Runtime.Execute <EntityDataServiceResponse <TenderType> >(getChannelTenderTypesDataRequest, context).PagedEntityCollection.Results;

                ThrowIf.Null(channelTenderTypes, "channelTenderTypes");

                Dictionary <RetailOperation, List <TenderLine> > results = new Dictionary <RetailOperation, List <TenderLine> >();

                if (tenderLines == null)
                {
                    return(results);
                }

                foreach (TenderLine tenderLine in tenderLines)
                {
                    if (tenderLine.Status == TenderLineStatus.Committed)
                    {
                        foreach (TenderType tenderType in channelTenderTypes)
                        {
                            if (tenderLine.TenderTypeId == tenderType.TenderTypeId)
                            {
                                if (results.ContainsKey(tenderType.OperationType))
                                {
                                    results[tenderType.OperationType].Add(tenderLine);
                                }
                                else
                                {
                                    var list = new List <TenderLine>();
                                    list.Add(tenderLine);
                                    results[tenderType.OperationType] = list;
                                }
                            }
                        }
                    }
                }

                return(results);
            }
            private static void OnAuthorizePaymentExecuting(AuthorizePaymentServiceRequest request)
            {
                // Call to get tender types (cached).
                var        dataServiceRequest = new GetChannelTenderTypesDataRequest(request.RequestContext.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                var        response           = request.RequestContext.Execute <EntityDataServiceResponse <TenderType> >(dataServiceRequest);
                TenderType tenderType         = response.PagedEntityCollection.Results.Single(t => string.Equals(t.TenderTypeId, request.TenderLine.TenderTypeId, StringComparison.OrdinalIgnoreCase));

                switch (tenderType.OperationType)
                {
                case RetailOperation.PayCreditMemo:
                    if (request.TenderLine.Amount < 0)
                    {
                        request.RequestContext.Execute <NullResponse>(new CheckAccessServiceRequest(RetailOperation.IssueCreditMemo));
                    }

                    break;

                default:
                    request.RequestContext.Execute <NullResponse>(new CheckAccessServiceRequest(tenderType.OperationType));
                    break;
                }
            }
Exemple #9
0
            /// <summary>
            /// Calculate specific reason codes on a tender line and add them to the incoming collection.
            /// </summary>
            /// <param name="request">The request object.</param>
            /// <param name="requiredReasonCodes">The collection to which required reason codes are added.</param>
            /// <param name="reasonCodeRequirements">The required specific reason codes map.</param>
            /// <param name="tenderLine">The tenderLine on which to calculate required reason codes.</param>
            private static void CalculateRequiredSpecificReasonCodesOnTenderLine(
                CalculateRequiredReasonCodesServiceRequest request,
                IDictionary <string, ReasonCode> requiredReasonCodes,
                HashSet <ReasonCodeRequirement> reasonCodeRequirements,
                TenderLine tenderLine)
            {
                if (tenderLine.Status == TenderLineStatus.Historical)
                {
                    return;
                }

                // if tenderline is a card, refrelation3 becomes tenderline.cardtypeid and tablerefid is creditcard
                var getChannelTenderTypesDataRequest = new GetChannelTenderTypesDataRequest(request.RequestContext.GetPrincipal().ChannelId, QueryResultSettings.AllRecords);
                var tenderTypes = request.RequestContext.Runtime.Execute <EntityDataServiceResponse <TenderType> >(getChannelTenderTypesDataRequest, request.RequestContext).PagedEntityCollection.Results;

                ReasonCodeTableRefType tableRef = ReasonCodeTableRefType.Tender;
                string refRelation3             = string.Empty;

                TenderType tenderType = tenderTypes.Where(type => type.TenderTypeId == tenderLine.TenderTypeId).SingleOrDefault();

                if (tenderType.OperationId == (int)RetailOperation.PayCard)
                {
                    refRelation3 = tenderLine.CardTypeId;
                    tableRef     = ReasonCodeTableRefType.CreditCard;
                }

                CalculateReasonCodesSpecificToEntity(
                    request,
                    tenderLine.TenderTypeId,
                    tableRef,
                    request.SalesTransaction.StoreId,
                    tenderLine.TenderTypeId,
                    refRelation3,
                    requiredReasonCodes,
                    reasonCodeRequirements,
                    tenderLine.ReasonCodeLines,
                    null);
            }