예제 #1
0
        public QuantityOperationViewModel(QuantityOperationDTO quantityOperationDto)
        {
            Id            = quantityOperationDto.Id;
            Type          = (QuantityOperationType)quantityOperationDto.Type;
            OrderId       = quantityOperationDto.OrderId;
            Market        = quantityOperationDto.Market;
            MarketplaceId = quantityOperationDto.MarketplaceId;
            Comment       = quantityOperationDto.Comment;
            CreateDate    = quantityOperationDto.CreateDate;
            CreatedBy     = quantityOperationDto.CreatedBy;
            CreatedByName = quantityOperationDto.CreatedByName;

            QuantityChanges = quantityOperationDto.QuantityChanges
                              .Select(q => new QuantityChangeViewModel()
            {
                Id          = q.Id,
                Quantity    = q.Quantity,
                Size        = q.Size,
                StyleItemId = q.StyleItemId,
                StyleId     = q.StyleId,
                StyleString = q.StyleString,
                InActive    = q.InActive
            })
                              .OrderBy(q => q.Quantity)
                              .ToList();
        }
예제 #2
0
        public static void AddQuantityOperation(ILogService log,
                                                IUnitOfWork db,
                                                IQuantityManager quantityManager,
                                                string orderId,
                                                IList <DTOOrderItem> items,
                                                ITime time,
                                                long?by)
        {
            var operationDto = new QuantityOperationDTO();

            operationDto.Type            = (int)QuantityOperationType.FromMailPage;
            operationDto.OrderId         = orderId;
            operationDto.Comment         = String.Empty;
            operationDto.QuantityChanges = new List <QuantityChangeDTO>();

            if (items != null)
            {
                foreach (var item in items)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = item.StyleEntityId ?? 0,
                        StyleItemId = item.StyleItemId ?? 0,
                        Quantity    = item.Quantity,
                    });
                }
            }

            quantityManager.AddQuantityOperation(db,
                                                 operationDto,
                                                 time.GetAppNowTime(),
                                                 by);
        }
예제 #3
0
        public long AddQuantityOperation(IUnitOfWork db,
                                         QuantityOperationDTO quantityOperation,
                                         DateTime when,
                                         long?by)
        {
            var operation = new QuantityOperation();

            operation.Type    = (int)quantityOperation.Type;
            operation.OrderId = quantityOperation.OrderId;
            operation.Comment = quantityOperation.Comment;

            operation.CreateDate = when;
            operation.CreatedBy  = by;

            db.QuantityOperations.Add(operation);
            db.Commit();

            foreach (var change in quantityOperation.QuantityChanges)
            {
                var dbChange = new QuantityChange();
                dbChange.QuantityOperationId = operation.Id;

                dbChange.StyleId     = change.StyleId;
                dbChange.StyleItemId = change.StyleItemId;
                dbChange.Quantity    = change.Quantity;

                dbChange.InActive  = change.InActive;
                dbChange.ExpiredOn = change.ExpiredOn;
                dbChange.Tag       = StringHelper.Substring(change.Tag, 50);

                dbChange.CreateDate = when;
                dbChange.CreatedBy  = by;

                db.QuantityChanges.Add(dbChange);

                LogStyleItemQuantity(db,
                                     change.StyleItemId,
                                     change.Quantity,
                                     null,
                                     QuantityChangeSourceType.AddSpecialCase,
                                     operation.Type.ToString(),
                                     dbChange.Id,
                                     StringHelper.Substring(StringHelper.GetFirstNotEmpty(operation.OrderId), 50),
                                     when,
                                     by);
            }
            db.Commit();

            return(operation.Id);
        }
        public void SendEmail(IUnitOfWork db,
                              ILogService log,
                              IEmailService emailService,
                              IQuantityManager quantityManager,
                              DateTime when,
                              long?by)
        {
            CallResult <Exception> result;

            if (AppSettings.IsDemo)
            {
                result = CallResult <Exception> .Success(null);
            }
            else
            {
                result = emailService.SendEmail(this, CallSource.UI, by);
            }

            CallHelper.ThrowIfFail(result);

            Order order = null;

            switch (this.EmailType)
            {
            case EmailTypes.RequestFeedback:
                db.Orders.UpdateRequestedFeedback(this.OrderNumber);
                break;

            case EmailTypes.AddressVerify:
                db.Orders.UpdateRequestedAddressVerify(this.OrderNumber);
                break;

            case EmailTypes.LostPackage:
                break;

            case EmailTypes.LostPackage2:
                break;

            case EmailTypes.UndeliverableAsAddressed:
                break;

            case EmailTypes.ExchangeInstructions:
                if (ExchangeItems != null)
                {
                    var exchangeToItems = ExchangeItems.Where(i => i.InputQuantity > 0).ToList();
                    if (exchangeToItems.Any())
                    {
                        var model = new QuantityOperationDTO()
                        {
                            Type            = (int)QuantityOperationType.ExchangeOnHold,
                            OrderId         = this.OrderNumber,
                            Comment         = "Sent Exchange Instruction",
                            QuantityChanges = exchangeToItems.Select(i => new QuantityChangeDTO()
                            {
                                Quantity    = i.InputQuantity,
                                StyleId     = i.ExchangeStyleId ?? 0,
                                StyleItemId = i.ExchangeStyleItemId ?? 0,
                                StyleString = i.ExchangeStyleString,
                                ExpiredOn   = when.AddDays(14),
                                Tag         = "Exchanged from: " + i.StyleString + ", styleItemId: " + i.StyleItemId,
                            }).ToList(),
                        };
                        quantityManager.AddQuantityOperation(db, model, when, by);
                    }

                    foreach (var item in ExchangeItems)
                    {
                        log.Info("Exchange item, from styleId=" + item.StyleId + " styleItemId=" + item.StyleItemId +
                                 " --- to styleId=" + item.ExchangeStyleId + ", styleItemId=" +
                                 item.ExchangeStyleItemId + ", quantity=" + item.InputQuantity);
                        //TODO: save into DB
                    }
                }
                break;
            }

            if (!String.IsNullOrEmpty(NewComment))
            {
                AddOrderComment(db,
                                OrderNumber,
                                NewComment,
                                when,
                                by);
            }

            var emailNotifyType = EmailNotifyHelper.GetEmailNotifyFrom(this.EmailType);

            db.OrderEmailNotifies.Add(new OrderEmailNotify()
            {
                OrderNumber = this.OrderNumber,
                Reason      = "User emailed, webpage",
                Type        = (int)emailNotifyType,
                CreateDate  = when,
                CreatedBy   = by
            });
            db.Commit();

            if (ReplyToEmailId.HasValue)
            {
                var email = db.Emails.Get(ReplyToEmailId.Value);
                if (email != null)
                {
                    email.ResponseStatus = (int)EmailResponseStatusEnum.Sent;
                    db.Commit();
                    log.Info("Mark as responsed (as reply), emailId=" + email.Id);
                }
            }

            if (!String.IsNullOrEmpty(this.OrderNumber))
            {
                var orderEmails = db.Emails.GetAllByOrderId(this.OrderNumber)
                                  .Where(e => e.FolderType == (int)EmailFolders.Inbox &&
                                         ((String.IsNullOrEmpty(e.AnswerMessageID) &&
                                           e.ResponseStatus == (int)EmailResponseStatusEnum.None) ||
                                          e.ResponseStatus == (int)EmailResponseStatusEnum.ResponsePromised))
                                  .ToList();
                foreach (var email in orderEmails)
                {
                    var dbEmail = db.Emails.Get(email.Id);
                    dbEmail.ResponseStatus = (int)EmailResponseStatusEnum.Sent;
                    log.Info("Mark as responsed (by orderNumber), emailId=" + email.Id);
                }
                db.Commit();
            }
        }
예제 #5
0
        public long Add(IUnitOfWork db,
                        IQuantityManager quantityManager,
                        ICacheService cache,
                        DateTime when,
                        long?by)
        {
            IList <ListingOrderDTO> orderItems;
            StyleEntireDto          style;

            var operationDto = new QuantityOperationDTO();

            operationDto.Type            = (int)Type;
            operationDto.OrderId         = OrderId;
            operationDto.Comment         = Comment;
            operationDto.QuantityChanges = new List <QuantityChangeDTO>();
            switch (Type)
            {
            case QuantityOperationType.Exchange:
                orderItems = db.Listings.GetOrderItems(OrderId);
                var current = orderItems.FirstOrDefault(o => o.ItemOrderId == OrderItemId);
                if (current != null)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = current.StyleId ?? 0,
                        StyleItemId = current.StyleItemId ?? 0,
                        Quantity    = -(Quantity ?? 0),
                    });
                }

                style = db.Styles.GetActiveByStyleIdAsDto(StyleId);
                if (style != null)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = style.Id,
                        StyleItemId = StyleItemId ?? 0,
                        Quantity    = Quantity ?? 0
                    });
                }
                break;

            case QuantityOperationType.Return:
                orderItems = db.Listings.GetOrderItems(OrderId);
                foreach (var item in orderItems)
                {
                    if (InputOrderItems != null)
                    {
                        var inputItem = InputOrderItems.FirstOrDefault(i => i.ItemOrderId == item.ItemOrderId);
                        if (inputItem != null)
                        {
                            item.QuantityOrdered = inputItem.Quantity;
                        }
                    }

                    if (item.QuantityOrdered > 0)
                    {
                        operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                        {
                            StyleId     = item.StyleId ?? 0,
                            StyleItemId = item.StyleItemId ?? 0,
                            Quantity    = -item.QuantityOrdered,
                        });
                    }
                }
                break;

            case QuantityOperationType.ExchangeOnHold:
            case QuantityOperationType.ReturnOnHold:
                orderItems = db.Listings.GetOrderItems(OrderId);
                foreach (var item in orderItems)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = item.StyleId ?? 0,
                        StyleItemId = item.StyleItemId ?? 0,
                        Quantity    = -item.QuantityOrdered,
                        InActive    = true
                    });
                }
                break;

            case QuantityOperationType.Replacement:
                orderItems = db.Listings.GetOrderItems(OrderId);
                foreach (var item in orderItems)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = item.StyleId ?? 0,
                        StyleItemId = item.StyleItemId ?? 0,
                        Quantity    = item.QuantityOrdered,
                    });
                }
                break;

            case QuantityOperationType.Lost:
            case QuantityOperationType.SoldOutside:
            case QuantityOperationType.StoreManual:
            case QuantityOperationType.Damaged:
            case QuantityOperationType.CompensationGift:
                style = db.Styles.GetActiveByStyleIdAsDto(StyleId);
                if (style != null)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = style.Id,
                        StyleItemId = StyleItemId ?? 0,
                        Quantity    = Quantity ?? 0,
                    });
                }
                break;

            case QuantityOperationType.InvalidBox:
                style = db.Styles.GetActiveByStyleIdAsDto(StyleId);
                if (style != null)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = style.Id,
                        StyleItemId = StyleItemId ?? 0,
                        Quantity    = Quantity ?? 0,
                    });
                }
                style = db.Styles.GetActiveByStyleIdAsDto(StyleIdToRemove);
                if (style != null)
                {
                    operationDto.QuantityChanges.Add(new QuantityChangeDTO()
                    {
                        StyleId     = style.Id,
                        StyleItemId = StyleItemIdToRemove ?? 0,
                        Quantity    = QuantityToRemove ?? 0,
                    });
                }
                break;
            }

            var operationId = quantityManager.AddQuantityOperation(db,
                                                                   operationDto,
                                                                   when,
                                                                   by);

            if (StyleItemId.HasValue)
            {
                cache.RequestStyleItemIdUpdates(db, new List <long>()
                {
                    StyleItemId.Value
                }, by);
            }

            if (StyleItemIdToRemove.HasValue)
            {
                cache.RequestStyleItemIdUpdates(db, new List <long>()
                {
                    StyleItemIdToRemove.Value
                }, by);
            }

            return(operationId);
        }
예제 #6
0
        public long Apply(IUnitOfWork db,
                          ICacheService cache,
                          IQuantityManager quantityManager,
                          IStyleHistoryService styleHistory,
                          ISystemActionService actionService,
                          DateTime when,
                          long?by)
        {
            var style = db.Styles.Get(StyleId);

            style.UpdateDate = when;
            style.UpdatedBy  = by;

            style.ReSaveDate = when;
            style.ReSaveBy   = by;

            StyleViewModel.UpdateLocations(db, styleHistory, StyleId, Locations, when, by);

            var wasAnyChanges = false;

            if (Sizes != null && Sizes.Any())
            {
                var styleItems      = db.StyleItems.GetFiltered(si => si.StyleId == StyleId).ToList();
                var styleItemCaches = db.StyleItemCaches.GetFiltered(si => si.StyleId == StyleId).ToList();

                foreach (var size in Sizes)  //Update quantity (marking when/by)
                {
                    //int? oldQuantity = null;
                    //int? newQuantity = null;
                    string tag        = null;
                    bool   wasChanged = false;

                    var styleItem      = styleItems.FirstOrDefault(si => si.Id == size.StyleItemId);
                    var styleItemCache = styleItemCaches.FirstOrDefault(sic => sic.Id == size.StyleItemId);

                    if (styleItem != null)
                    {
                        if (size.UseBoxQuantity)
                        {
                            if (styleItem.Quantity != null)
                            {
                                var oldQuantity = styleItem.Quantity;
                                var newQuantity = size.BoxQuantity;
                                tag = size.BoxQuantitySetDate.ToString();

                                styleItem.Quantity        = null;
                                styleItem.QuantitySetDate = null;
                                styleItem.QuantitySetBy   = null;
                                //styleItem.RestockDate = null;
                                wasChanged = true;

                                quantityManager.LogStyleItemQuantity(db,
                                                                     styleItem.Id,
                                                                     newQuantity,
                                                                     oldQuantity,
                                                                     QuantityChangeSourceType.UseBoxQuantity,
                                                                     tag,
                                                                     null,
                                                                     null,
                                                                     when,
                                                                     by);
                            }
                        }

                        if (size.NewRestockDate.HasValue &&
                            styleItem.RestockDate != size.NewRestockDate)
                        {
                            styleHistory.AddRecord(styleItem.StyleId,
                                                   StyleHistoryHelper.RestockDateKey,
                                                   DateHelper.ToDateTimeString(styleItem.RestockDate),
                                                   StringHelper.JoinTwo("-", styleItem.Size, styleItem.Color),
                                                   DateHelper.ToDateTimeString(size.NewRestockDate),
                                                   styleItem.Id.ToString(),
                                                   by);

                            styleItem.RestockDate = size.NewRestockDate;
                            wasChanged            = true;
                        }

                        if (size.NewManuallyQuantity.HasValue)
                        {
                            var operationType = size.NewManuallyQuantity.Value < 0 ? QuantityOperationType.Lost : QuantityOperationType.AddManually;

                            var quantityOperation = new QuantityOperationDTO()
                            {
                                Type            = (int)operationType,
                                QuantityChanges = new List <QuantityChangeDTO>()
                                {
                                    new QuantityChangeDTO()
                                    {
                                        StyleId     = style.Id,
                                        StyleItemId = styleItem.Id,
                                        Quantity    = -1 * size.NewManuallyQuantity.Value,
                                        //NOTE: we need to change sign to opposite because we substract quantity operataions from inventory
                                    }
                                },
                                Comment = "From style quantity dialog",
                            };

                            quantityManager.AddQuantityOperation(db,
                                                                 quantityOperation,
                                                                 when,
                                                                 by);

                            //NOTE: Hot updating the cache (only for first few seconds to display the updates before recalculation)
                            if (styleItemCache != null)
                            {
                                styleItemCache.SpecialCaseQuantityFromDate += -1 * size.NewManuallyQuantity.Value;
                                styleItemCache.TotalSpecialCaseQuantity    += -1 * size.NewManuallyQuantity.Value;
                            }

                            wasChanged = true;
                        }

                        if (size.IsRemoveRestockDate == true)
                        {
                            styleItem.RestockDate = null;

                            wasChanged = true;
                        }

                        if (size.OnHold != styleItem.OnHold)
                        {
                            quantityManager.LogStyleItemQuantity(db,
                                                                 styleItem.Id,
                                                                 size.OnHold ? 0 : styleItem.Quantity,
                                                                 size.OnHold ? styleItem.Quantity : 0,
                                                                 QuantityChangeSourceType.OnHold,
                                                                 size.OnHold.ToString(),
                                                                 null,
                                                                 null,
                                                                 when,
                                                                 by);
                            styleItem.OnHold = size.OnHold;

                            wasChanged = true;
                        }
                    }

                    if (wasChanged)
                    {
                        db.Commit();
                        wasAnyChanges = true;
                    }
                }
            }

            //NOTE: always update cache
            cache.RequestStyleIdUpdates(db,
                                        new List <long>()
            {
                StyleId
            },
                                        UpdateCacheMode.IncludeChild,
                                        AccessManager.UserId);

            if (wasAnyChanges)
            {
                db.Commit();

                SystemActionHelper.RequestQuantityDistribution(db, actionService, StyleId, by);
            }

            return(StyleId);
        }
        public ApplyOrderResult Apply(ILogService log,
                                      IUnitOfWork db,
                                      IOrderHistoryService orderHistoryService,
                                      IQuantityManager quantityManager,
                                      DateTime when,
                                      long?by)
        {
            var dbOrder                 = db.Orders.GetById(EntityId);
            var addressChanged          = false;
            var shipmentProviderChanged = false;
            var shouldRecalcRates       = dbOrder.IsInsured != IsInsured ||
                                          dbOrder.IsSignConfirmation != IsSignConfirmation;

            var manuallyAddress = ComposeAddressDto();

            //NOTE: empty when fields was readonly
            if (!AddressHelper.IsEmptyManually(manuallyAddress))
            {
                var originalAddress = dbOrder.GetAddressDto();

                addressChanged    = AddressHelper.CompareWithManuallyAllFields(originalAddress, manuallyAddress);
                shouldRecalcRates = shouldRecalcRates || AddressHelper.CompareWithManuallyBigChanges(originalAddress, manuallyAddress);

                if (addressChanged)
                {
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyPersonNameKey, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyPersonName : dbOrder.PersonName, ManuallyPersonName, by);
                    dbOrder.ManuallyPersonName = ManuallyPersonName;
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingAddress1Key, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingAddress1 : dbOrder.ShippingAddress1, ManuallyShippingAddress1, by);
                    dbOrder.ManuallyShippingAddress1 = ManuallyShippingAddress1;
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingAddress2Key, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingAddress2 : dbOrder.ShippingAddress2, ManuallyShippingAddress2, by);
                    dbOrder.ManuallyShippingAddress2 = ManuallyShippingAddress2;
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingCityKey, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingCity : dbOrder.ShippingCity, ManuallyShippingCity, by);
                    dbOrder.ManuallyShippingCity = ManuallyShippingCity;
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingCountryKey, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingCountry : dbOrder.ShippingCountry, ManuallyShippingCountry, by);
                    dbOrder.ManuallyShippingCountry = ManuallyShippingCountry;

                    dbOrder.ManuallyShippingState = !ShippingUtils.IsInternational(dbOrder.ManuallyShippingCountry)
                                                    // == "US"
                        ? ManuallyShippingUSState
                        : ManuallyShippingState;

                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingZipKey, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingZip : dbOrder.ShippingZip, ManuallyShippingZip, by);
                    dbOrder.ManuallyShippingZip = StringHelper.TrimWhitespace(ManuallyShippingZip);
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingZipAddonKey, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingZipAddon : dbOrder.ShippingZipAddon, ManuallyShippingZipAddon, by);
                    dbOrder.ManuallyShippingZipAddon = StringHelper.TrimWhitespace(ManuallyShippingZipAddon);
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ManuallyShippingPhoneKey, dbOrder.IsManuallyUpdated ? dbOrder.ManuallyShippingPhone : dbOrder.ShippingPhone, ManuallyShippingPhone, by);
                    dbOrder.ManuallyShippingPhone = ManuallyShippingPhone;

                    dbOrder.IsManuallyUpdated = true;
                }
                else
                {
                    dbOrder.ManuallyPersonName       = String.Empty;
                    dbOrder.ManuallyShippingAddress1 = String.Empty;
                    dbOrder.ManuallyShippingAddress2 = String.Empty;
                    dbOrder.ManuallyShippingCity     = String.Empty;
                    dbOrder.ManuallyShippingCountry  = String.Empty;

                    dbOrder.ManuallyShippingState    = String.Empty;
                    dbOrder.ManuallyShippingZip      = String.Empty;
                    dbOrder.ManuallyShippingZipAddon = String.Empty;
                    dbOrder.ManuallyShippingPhone    = String.Empty;

                    dbOrder.IsManuallyUpdated = false;
                }
            }

            dbOrder.InsuredValue = InsuredValue;
            orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.IsInsuredKey, dbOrder.IsInsured, IsInsured, by);
            dbOrder.IsInsured = IsInsured;
            orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.IsSignConfirmationKey, dbOrder.IsSignConfirmation, IsSignConfirmation, by);
            dbOrder.IsSignConfirmation = IsSignConfirmation;

            if (ManuallyShipmentProviderType.HasValue)
            {
                if (dbOrder.ShipmentProviderType != ManuallyShipmentProviderType.Value)
                {
                    shipmentProviderChanged = true;
                    shouldRecalcRates       = true;
                }

                orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ShipmentProviderTypeKey, dbOrder.ShipmentProviderType, ManuallyShipmentProviderType, by);
                dbOrder.ShipmentProviderType = ManuallyShipmentProviderType.Value;
            }

            //dbOrder.OnHold = OnHold;

            dbOrder.UpdateDate = when;
            dbOrder.UpdatedBy  = by;

            if (Items.All(i => i.NewListingId > 0)) //NOTE: only when enabled items edit
            {
                var changeNotes        = "";
                var itemSizeWasChanged = false;
                var joinItems          = JoinItems(Items);
                var dbOrderItems       = db.OrderItems.GetAll().Where(i => i.OrderId == dbOrder.Id).ToList();
                var orderItemSources   = db.OrderItemSources.GetAllAsDto().Where(i => i.OrderId == dbOrder.Id).ToList();

                foreach (var item in joinItems)
                {
                    var dbOrderItem = dbOrderItems.FirstOrDefault(im => im.ItemOrderIdentifier == item.ItemOrderId);

                    //NOTE: Get source info for set proprotionally ItemPrice etc.
                    var sourceItemOrderId = item.SourceItemOrderId;
                    var sourceItemMapping = orderItemSources.FirstOrDefault(i => i.ItemOrderIdentifier == sourceItemOrderId);

                    if (dbOrderItem != null)
                    {
                        log.Info("Updated orderItemId=" + item.ItemOrderId + ", qty=" + item.Quantity);
                    }
                    else
                    {
                        log.Info("Added orderItemId=" + item.ItemOrderId + ", qty=" + item.Quantity);
                        dbOrderItem            = db.OrderItemSources.CreateItemFromSourceDto(sourceItemMapping);
                        dbOrderItem.CreateDate = when;

                        db.OrderItems.Add(dbOrderItem);
                    }

                    dbOrderItem.ItemOrderIdentifier = item.ItemOrderId;
                    dbOrderItem.QuantityOrdered     = item.Quantity;
                    dbOrderItem.ListingId           = item.NewListingId;

                    dbOrderItem.SourceListingId           = sourceItemMapping.ListingId;
                    dbOrderItem.SourceItemOrderIdentifier = sourceItemMapping.ItemOrderIdentifier;

                    var newListing = db.Listings.GetViewListingsAsDto(withUnmaskedStyles: false)
                                     .FirstOrDefault(l => l.Id == item.NewListingId);

                    var keepListingUpdateOnlyStyle = newListing.StyleItemId != dbOrderItem.StyleItemId;
                    if (dbOrderItem.Id == 0 ||
                        item.NewListingId != item.ListingId ||
                        keepListingUpdateOnlyStyle)
                    {
                        var oldListing = db.Listings.GetViewListingsAsDto(withUnmaskedStyles: false)
                                         .FirstOrDefault(l => l.Id == sourceItemMapping.ListingId);

                        if (newListing != null && oldListing != null)
                        {
                            itemSizeWasChanged = newListing.StyleItemId != oldListing.StyleItemId;
                            if (itemSizeWasChanged)
                            {
                                var isStyleChanged = newListing.StyleString != oldListing.StyleString;
                                changeNotes += (isStyleChanged ? "Order item" : "Size") + " was changed from: " +
                                               (isStyleChanged ? oldListing.StyleString + " - " : " ") +
                                               SizeHelper.ToVariation(oldListing.StyleSize, oldListing.StyleColor)
                                               + " to: " + (isStyleChanged ? newListing.StyleString + " - " : "") +
                                               SizeHelper.ToVariation(newListing.StyleSize, newListing.StyleColor);

                                dbOrderItem.ReplaceType = (int)ItemReplaceTypes.Change;
                                dbOrderItem.ReplaceDate = when;
                                orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ReplaceItemKey, dbOrderItem.StyleItemId, dbOrderItem.Id.ToString(), newListing.StyleItemId, null, by);

                                var quantityOperation = new QuantityOperationDTO()
                                {
                                    Type            = (int)QuantityOperationType.Lost,
                                    QuantityChanges = new List <QuantityChangeDTO>()
                                    {
                                        new QuantityChangeDTO()
                                        {
                                            StyleId     = oldListing.StyleId.Value,
                                            StyleItemId = oldListing.StyleItemId.Value,
                                            Quantity    = dbOrderItem.QuantityOrdered,
                                            //NOTE: W/o sign means that the qty will be substracted
                                        }
                                    },
                                    Comment = "Order edit, change style/size",
                                };

                                quantityManager.AddQuantityOperation(db,
                                                                     quantityOperation,
                                                                     when,
                                                                     by);
                            }

                            //NOTE: Actualize current style info
                            dbOrderItem.StyleId     = newListing.StyleId;
                            dbOrderItem.StyleItemId = newListing.StyleItemId;
                            dbOrderItem.StyleString = newListing.StyleString;

                            dbOrderItem.SourceStyleString = oldListing.StyleString;
                            dbOrderItem.SourceStyleItemId = oldListing.StyleItemId;
                            dbOrderItem.SourceStyleSize   = oldListing.StyleSize;
                            dbOrderItem.SourceStyleColor  = oldListing.StyleColor;
                        }
                    }

                    if (dbOrderItem.ItemOrderIdentifier != dbOrderItem.SourceItemOrderIdentifier)
                    {
                        var portionCoef = dbOrderItem.QuantityOrdered / (decimal)sourceItemMapping.QuantityOrdered;

                        dbOrderItem.ItemPrice             = sourceItemMapping.ItemPrice * portionCoef;
                        dbOrderItem.ItemPriceInUSD        = sourceItemMapping.ItemPriceInUSD * portionCoef;
                        dbOrderItem.ShippingPrice         = sourceItemMapping.ShippingPrice * portionCoef;
                        dbOrderItem.ShippingPriceInUSD    = sourceItemMapping.ShippingPriceInUSD * portionCoef;
                        dbOrderItem.ShippingDiscount      = sourceItemMapping.ShippingDiscount * portionCoef;
                        dbOrderItem.ShippingDiscountInUSD = sourceItemMapping.ShippingDiscountInUSD * portionCoef;
                    }
                    else //NOTE: m.b. no needed, for now no cases, but can be found in future
                    {
                        dbOrderItem.ItemPrice             = sourceItemMapping.ItemPrice;
                        dbOrderItem.ItemPriceInUSD        = sourceItemMapping.ItemPriceInUSD;
                        dbOrderItem.ShippingPrice         = sourceItemMapping.ShippingPrice;
                        dbOrderItem.ShippingPriceInUSD    = sourceItemMapping.ShippingPriceInUSD;
                        dbOrderItem.ShippingDiscount      = sourceItemMapping.ShippingDiscount;
                        dbOrderItem.ShippingDiscountInUSD = sourceItemMapping.ShippingDiscountInUSD;
                    }
                }
                db.Commit();

                var toRemoveOrderItems = dbOrderItems.Where(oi => joinItems.All(i => i.ItemOrderId != oi.ItemOrderIdentifier) &&
                                                            oi.QuantityOrdered > 0).ToList(); //Keeping cancelled items with qty = 0
                foreach (var toRemove in toRemoveOrderItems)
                {
                    log.Info("Remove orderItem, ordrItemId=" + toRemove.ItemOrderIdentifier
                             + ", qty=" + toRemove.QuantityOrdered);
                    db.OrderItems.Remove(toRemove);

                    itemSizeWasChanged = true;
                }
                db.Commit();

                if (itemSizeWasChanged)
                {
                    shouldRecalcRates = true;

                    Comments.Add(new CommentViewModel()
                    {
                        Comment = changeNotes,
                        Type    = (int)CommentType.ReturnExchange
                    });
                }
            }


            if (!string.IsNullOrEmpty(ManuallyShippingGroupId))
            {
                var groupId   = int.Parse(ManuallyShippingGroupId);
                var shippings = db.OrderShippingInfos.GetByOrderId(EntityId).ToList();
                var previousIsActiveMethodIds = String.Join(";", shippings.Where(sh => sh.IsActive).Select(sh => sh.ShippingMethodId).ToList());
                var hasDropdown = shippings.Where(sh => sh.IsVisible).GroupBy(sh => sh.ShippingMethodId).Count() > 1;
                if (shippings.Any(sh => sh.ShippingGroupId == groupId))
                {
                    foreach (var shipping in shippings)
                    {
                        shipping.IsActive = shipping.ShippingGroupId == groupId;
                        if (hasDropdown) //Keep is visible
                        {
                            shipping.IsVisible = shipping.IsVisible || shipping.ShippingGroupId == groupId;
                        }
                        else
                        {
                            shipping.IsVisible = shipping.ShippingGroupId == groupId;
                        }
                    }
                    var newIsActiveMethodIds = String.Join(";", shippings.Where(sh => sh.IsActive).Select(sh => sh.ShippingMethodId).ToList());
                    orderHistoryService.AddRecord(dbOrder.Id, OrderHistoryHelper.ShippingMethodKey, previousIsActiveMethodIds, newIsActiveMethodIds, by);
                }
                else
                {
                    //Can't change active shipping to not exists
                }
            }
            db.Commit();

            //Update Package Sizes
            var activeShippings = db.OrderShippingInfos.GetByOrderId(EntityId)
                                  .Where(sh => sh.IsActive)
                                  .OrderBy(sh => sh.Id)
                                  .ToList();

            for (var i = 0; i < activeShippings.Count; i++)
            {
                if (Packages != null && i < Packages.Count)
                {
                    if (activeShippings[i].PackageLength != Packages[i].PackageLength)
                    {
                        log.Info("Changed length: " + activeShippings[i].PackageLength + "=>" + Packages[i].PackageLength);
                        activeShippings[i].PackageLength = Packages[i].PackageLength;

                        shouldRecalcRates = true;
                    }
                    if (activeShippings[i].PackageWidth != Packages[i].PackageWidth)
                    {
                        log.Info("Changed width: " + activeShippings[i].PackageWidth + "=>" + Packages[i].PackageWidth);
                        activeShippings[i].PackageWidth = Packages[i].PackageWidth;

                        shouldRecalcRates = true;
                    }
                    if (activeShippings[i].PackageHeight != Packages[i].PackageHeight)
                    {
                        log.Info("Changed height: " + activeShippings[i].PackageHeight + "=>" + Packages[i].PackageHeight);
                        activeShippings[i].PackageHeight = Packages[i].PackageHeight;

                        shouldRecalcRates = true;
                    }
                }
            }
            db.Commit();



            foreach (var comment in Comments)
            {
                if (comment.Id == 0)
                {
                    log.Info("New comment: " + comment.Comment);
                }
            }

            db.OrderComments.AddComments(
                Comments.Select(c => new CommentDTO()
            {
                Id      = c.Id,
                Message = c.Comment,
                Type    = c.Type,
            }).ToList(),
                EntityId,
                when,
                by);

            return(new ApplyOrderResult()
            {
                RateRecalcRequested = shouldRecalcRates,
                AddressValidationRequested = addressChanged ||
                                             dbOrder.AddressValidationStatus == (int)Core.Models.AddressValidationStatus.ExceptionCommunication ||
                                             dbOrder.AddressValidationStatus == (int)Core.Models.AddressValidationStatus.Exception,
                ShipmentProviderChanged = shipmentProviderChanged
            });
        }