Developer forum

Forum » Dynamicweb 9.0 Upgrade issues » Value cannot be null. Parameter name: key in CreateCartViewModel

Value cannot be null. Parameter name: key in CreateCartViewModel

Andrew Rushworth
Reply

HI,

After upgrading the site from 9.9.5 to 9.15.3 we started to get the following error with users and their carts (attachment ValueCannotBeNull):

[ArgumentNullException: Value cannot be null.
Parameter name: key]
   System.ThrowHelper.ThrowArgumentNullException(ExceptionArgument argument) +52
   System.Collections.Generic.Dictionary`2.FindEntry(TKey key) +14578763
   System.Collections.Generic.Dictionary`2.TryGetValue(TKey key, TValue& value) +21
   Dynamicweb.Ecommerce.ProductCatalog.ViewModelFactory.CreateCartViewModel(Order cart, Nullable`1 areaId) +2387
   Dynamicweb.Ecommerce.Frontend.EcomPageOnOutputSubscriber.CreateInstance(Order cart, Nullable`1 areaId) +102
   Dynamicweb.Ecommerce.Frontend.EcomPageOnOutputSubscriber.OnNotify(String notification, NotificationArgs args) +375
   Dynamicweb.Extensibility.Notifications.NotificationManager.Notify(String notification, NotificationArgs eventArgs) +875
   Dynamicweb.Frontend.PageView.Output() +1513
   Dynamicweb.AspNet.DynamicwebHttpHandler.ProcessRequest(HttpContext context) +71
   System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +542
   System.Web.<>c__DisplayClass285_0.<ExecuteStepImpl>b__0() +38
   System.Web.HttpApplication.ExecuteStepImpl(IExecutionStep step) +11857797
   System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +93


We found that deleting the cart, the user was able to access the site again and log in.
We then started getting the following:

Recursive call: The Context.GetCart() is not a cart and cannot be updated.                             
   Order.AutoId = 118825, SessionCartKey = EcomCart) 
   (OrderID:CART109305 (IsCart:True, Complete:False) Total:410, orderline total:R410,00; Orderlines:1 - Products:1, Discounts:0, Taxes:0, BOM:0, 
   (IP:10.212.134.207, Url:/), Thread:6, HashCode:8353582.)
 
The Recursive error is addressed in the latest update, so we updated the site from 9.15.3 to 9.15.13.
The Recursive error is resolved, but now we are still stuck with the initial error of the NULL value.

The problem seems to be either in Dynamicweb.Ecommerce.ProductCatalog.ViewModelFactory.CreateCartViewModel or in the data where there is a NULL value that shouldn't be there.
 
To Reproduce the error we do the following:
1. Log into front end and add an item to the cart - cart is fine and no issues
2. Open an ingognito window and log in with the same user - Error occurs
ValueCannotBeNull.png

Replies

 
Nicolai Pedersen Dynamicweb Employee
Nicolai Pedersen
Reply

Hi Andrew

I can do that on https://swiftdemo.dynamicweb-cms.com/ - you can try with DemoUser/DemoUser123 and check it out.'

So you might have a cart related setting or something custom.

This is the code that seems to fail:

Seems like you have orderlines with no product ids or something like that.

It could be nice to see the EcomOrderlines for the cart that is causing the issues.

We can of course skip this code if there are orderlines with missing product ids or what is causing this.

 
Andrew Rushworth
Reply

Thanks Nicolai.  I also suspected that as this piece of code changed from between version 9.15.3 and 9.5.13 when I compared the dlls.
However I was pointed in the right direction to resolve the issue.
 

I think what I missed in the stack trace was the Notification Manager - I think this would indicate that the CreateCartViewModel was being called from a notification subscribe (but maybe I'm wrong) 

[ArgumentNullException: Value cannot be null.
Parameter name: key]
   System.ThrowHelper.ThrowArgumentNullException(ExceptionArgument argument) +52
   System.Collections.Generic.Dictionary`2.FindEntry(TKey key) +14578763
   System.Collections.Generic.Dictionary`2.TryGetValue(TKey key, TValue& value) +21
   Dynamicweb.Ecommerce.ProductCatalog.ViewModelFactory.CreateCartViewModel(Order cart, Nullable`1 areaId) +2387
   Dynamicweb.Ecommerce.Frontend.EcomPageOnOutputSubscriber.CreateInstance(Order cart, Nullable`1 areaId) +102
   Dynamicweb.Ecommerce.Frontend.EcomPageOnOutputSubscriber.OnNotify(String notification, NotificationArgs args) +375
   Dynamicweb.Extensibility.Notifications.NotificationManager.Notify(String notification, NotificationArgs eventArgs) +875
   Dynamicweb.Frontend.PageView.Output() +1513
   Dynamicweb.AspNet.DynamicwebHttpHandler.ProcessRequest(HttpContext context) +71
   System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +542
   System.Web.<>c__DisplayClass285_0.<ExecuteStepImpl>b__0() +38
   System.Web.HttpApplication.ExecuteStepImpl(IExecutionStep step) +11857797
   System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +93

Anyway, the issue was I had a custom notification subscriber that I created for future use -  in order to clear custom order fields when a user does a re-order, I need to clear payment information as this is duplicated with the order).
This was passing a NULL Cart object to CreateCartViewModel.  Although this didn't seem to give an issue in 9.9.5 but does in 9.15.3.

[Subscribe(Dynamicweb.Ecommerce.Notifications.Ecommerce.Cart.Created)]

public class CartCreatedNotification : NotificationSubscriber
{
public override void OnNotify(string notification, NotificationArgs args)
{
            if (args == null || !(args is Dynamicweb.Ecommerce.Notifications.Ecommerce.Cart.CreatedArgs))
                        return;
 
            Dynamicweb.Ecommerce.Notifications.Ecommerce.Cart.CreatedArgs cArgs = (Dynamicweb.Ecommerce.Notifications.Ecommerce.Cart.CreatedArgs)args;
  }
 
At least the problem is solved now though.
Thank you, much appreciated.
 
Nicolai Pedersen Dynamicweb Employee
Nicolai Pedersen
Reply

Good find. And one of the wonders of changing any code over the lifespan of a product :-)

 
Andrew Rushworth
Reply

I'm still investigating this - I thought it was resolved, but it seems to only occur if there are discount lines on the order - and it may be even be occuring due to LS OMNI live integration with regards to discounts as it clears and uses discount calculated by LS.

If you create an order on the front end and just use that session then its fine.  But if I log out and then log back in I get the NULL parameter problem.

If there is no discount then the problem doesn't occur.

Difficult to debug

 
Nicolai Pedersen Dynamicweb Employee
Nicolai Pedersen
Reply

Could indicate a wrong orderlinetype of the discounts coming from omni - or a missing orderlineid. That has to be set manually.

 

 
Andrew Rushworth
Reply

Hi Nicolai,

It was never an issue when we were on 9.9.2 because CreateCartViewModel didn't exist in Ecommerce.dll at that stage as far as I could tell.
The problem also only occurs when you log out and log back in.
So if you add item to cart and omni calculates discount line and adds to order then everything is fine - the discount appears in the OrderLine table (to note the product number is NULL anlong with variant id = NULL, but everythign works fine).

The issue only occurs if you log out and back in or create another session via an incognito window.

This is the XML from live integration when it gets it back from omni - notice that for discount lines there is no itemid or product id.
Could this maybe where the product code in CreateCartViewModel is failing?

 <OrderDiscountLines>
    <OrderDiscountLine>
      <ExtensionData />
      <Id />
      <Description>10% Off Treat</Description>
      <DiscountAmount>164.00</DiscountAmount>
      <DiscountPercent>10.00</DiscountPercent>
      <DiscountType>TotalDiscount</DiscountType>
      <LineNumber>1</LineNumber>
      <No>1</No>
      <OfferNumber>5000PDISC0000387</OfferNumber>
      <OrderId />
      <PeriodicDiscGroup />
      <PeriodicDiscType>Unknown</PeriodicDiscType>
    </OrderDiscountLine>
  </OrderDiscountLines>
  <OrderLines>
    <OrderLine>
      <ExtensionData />
      <Id />
      <Amount>1476.00</Amount>
      <DiscountAmount>164.00</DiscountAmount>
      <DiscountPercent>10.00</DiscountPercent>
      <ItemDescription>Dipbrow Pomade</ItemDescription>
      <ItemId>113163</ItemId>
      <ItemImageId />
      <LineNumber>1</LineNumber>
      <LineType>Item</LineType>
      <NetAmount>1283.48</NetAmount>
      <NetPrice>356.52</NetPrice>
      <OrderId />
      <Price>410.00</Price>
      <Quantity>4.00</Quantity>
      <QuantityOutstanding>0</QuantityOutstanding>
      <QuantityToInvoice>4.00</QuantityToInvoice>
      <QuantityToShip>0</QuantityToShip>
      <TaxAmount>192.52</TaxAmount>
      <UomId />
      <VariantDescription>AUBURN</VariantDescription>
      <VariantId>AUBURN</VariantId>
    </OrderLine>

 
Andrew Rushworth
Reply

This is how the discount initially appears on teh OrderLines table - and you can checkout and add more items, etc.
However as soon as I log out and back in, I get an error and the Discount line has been removed fromteh table by live integration - so I assume the process is that live integration removes all discount lines and re-adds them.

 
Nicolai Pedersen Dynamicweb Employee
Nicolai Pedersen
Reply

Hi Andrew

There is a setting to tell if carts should be recalculated on login - not sure it will impact this though. See below.

From the response I can see that the orderlines have no ID - that is what is causing this I guess. I made a pull request to make it less volatile to that - code looks like this:

 
Andrew Rushworth
Reply

Yeah, that setting didn't make a difference.

How do I get hold of the change, Is this in a repository somewhere and do I need access?

 
Andrew Rushworth
Reply

In order to solve this from the live integration side, I changed the discount line to force it to have an ID when adding to the Order object.
As there is one discount per line I just made it the related productLine ID and concatenated _1 onto the end: discountOrderLine.Id = productOrderLine.Id + "_1";

It resolves the issue, but not sure its the most elegant way.

 

You must be logged in to post in the forum