简体   繁体   中英

c# MVC5 RedirectToAction not working - “Sequence contains no matching element”

I have a controller action that does the following:

  • Takes a list of Product models from a form.
  • Cycles through and adds selected products (IsSelected == true) to an Account model.
  • Saves the changes and Redirects to another action, passing the AccountID.
  • ID is received correctly, finds the correct account and passes it to the View.
  • The view then parses the account and shows the list of products that were added to the account above.

However, MVC keeps throwing an error "Sequence contains no matching element" and I'm struggling to figure out why.

Account Controller that takes a list of Products and adds it to the user's account:

    [HttpPost]
    [ValidateAntiForgeryToken]
    public async Task<ActionResult> AddProduct(List<Product> products)
    {
        //var acc = FetchCurrentUserAccount();
        if (db.Accounts != null)
        {
            var acc = db.Accounts.Find(UserManager.FindByIdAsync(User.Identity.GetUserId()).Result.Account.AccountID);
            foreach (var product in products)
            {
                if (product.IsSelected)
                {
                    product.PaymentStatus = enPaymentStatus.Pending
                    acc.ProductsPurchased.Add(product);
                }
            }
            await db.SaveChangesAsync();

            return RedirectToAction("Pay", "Products", new {id = acc.AccountID} );
        }
        return HttpNotFound();
    }

Product Controller that takes an AccountID, finds the account and passes it to the View as a model:

    [HttpGet]
    public ActionResult Pay(int? id)
    {
        var acc = db.Accounts.Find(id);
        return View(acc);
    }

The View itself:

@using PPPv2.Models
@model Account
@{ var subtotal = 0.0d;}
<h2>Payment:</h2>

@if (Model != null)
{
<h4>Thank you @Model.Salutation @Model.LastName</h4>
<h4>Please check that the product(s) and amounts below are correct before completing your purchase.</h4>


    foreach (var item in Model.ProductsPurchased)
    {

        <div>
            @Html.DisplayFor(modelItem => item.Name)
            <div>
                @Html.DisplayFor(modelItem => item.Price)
                @{ subtotal += item.Price; }
            </div>
        </div>
    }

    <div>
        Total to pay:
        <div>
            @Html.Display(String.Format("£{0:#,###0.00}", subtotal))
        </div>
    </div>

    @Html.ActionLink("Pay", "Process", "Products", new {id = Model.ProductsPurchased.First(x => x.PaymentStatus == enPaymentStatus.Sold)}, new {@class = "btn btn-warning"})
}
else
{
    <div>
        No products were found in your cart... Odd...
        <div>
            @Html.ActionLink("Select a product", "AddProduct", "Account", null, new {@class = "btn btn-warning"})
        </div>
    </div>
}

Points to note:

  • During the foreach(var product in Products) loop in the Account Controller; product is populated correctly. Yet when added to the account, the Count of the list increases correctly and the PaymentStatus is correct, but the remaining fields are null.
  • Creating a new Product() and pushing each individual property from product into it gives the same result.

Any ideas?

on this line:

@Html.ActionLink("Pay", "Process", "Products", 
new {id = Model.ProductsPurchased.First(x => x.PaymentStatus == enPaymentStatus.Sold)},
 new {@class = "btn btn-warning"})

You'll need to first add a condition checking whether there are any items in the ProductsPurchased collection that have a status of Sold. You may also want to make sure you wish to display a product with status of Sold , or rather as your controller code suggests, one with a status of Pending .

So, basically

if(Model.ProductsPurchased.Any(x => x.PaymentStatus == enPaymentStatus.Sold/*or Pending?*/)){
@Html.ActionLink("Pay", "Process", "Products", 
    new {id = Model.ProductsPurchased.First(x => x.PaymentStatus == enPaymentStatus.Sold/*or Pending?*/)},
     new {@class = "btn btn-warning"})
}

I'm not certain of the fix, but I believe it is that you are not waiting for the acc to return back, well more accurately for this to return back.

UserManager.FindByIdAsync(User.Identity.GetUserId()).Result.Account.AccountID

Because you are using async, I would have expected you to use await before trying to use the result. Have you tried mak

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM