da_funk
da_funk

Reputation: 43

How to pass an "id" to controller from multiple models?

I'm trying to pass an id to my basket but I keep getting an error

The parameters dictionary contains a null entry for parameter 'id' of non-nullable type 'System.Int32' for method 'System.Web.Mvc.ActionResult AddToBasket(Int32, Int32)' in 'UberUnlock.Controllers.BasketController'. An optional parameter must be a reference type, a nullable type, or be declared as an optional parameter. Parameter name: parameters

I don't realize what is wrong, my code is working fine when I reference to only one model

@model UberUnlock.Product

on top of the view but whenever I try to add two models through ModelView

@model UberUnlock.ViewModel.MultipleModelInOneView

I keep getting an error mentioned above, thanks.

Here is my View code

@model UberUnlock.ViewModel.MultipleModelInOneView


                    <dd>
                        @using (Html.BeginForm("AddToBasket", "Basket"))
                        {
                            @Html.AntiForgeryToken()
                            @Html.HiddenFor(model => model.Products.ID)

                            @Html.DropDownList("quantity", Enumerable.Range(1, 10).Select(i => new SelectListItem { Text = i.ToString(), Value = i.ToString() }))
                            <input type="submit" class="btn btn-primary btn-default margin" value="Add to Basket">
                        }
                    </dd>

<p>

    @Html.ActionLink("Edit", "Edit", new { id = Model.Products.ID }) |
    @Html.ActionLink("Back to List", "Index")
</p>

Here is my ViewModel code

using UberUnlock.Models;


namespace UberUnlock.ViewModel
{
    public class MultipleModelInOneView
    {
        public Order Orders { get; set; }
        public Product Products { get; set; }

    }
}

My BasketController code

[HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult AddToBasket(int id, int quantity)
    {
        Basket basket = Basket.GetBasket();
        basket.AddToBasket(id, quantity);
        return RedirectToAction("Index");
    }

This is a ProductController(this is a controller for my View)

public ActionResult Details(int? id)
        {

            var model = new MultipleModelInOneView();

            if (id == null)
            {
                return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
            }
            model.Products = db.Products.Find(id);
            if (model.Products == null)
            {
                return HttpNotFound();
            }
            return View(model);
        }

Upvotes: 0

Views: 1559

Answers (1)

The_Outsider
The_Outsider

Reputation: 1925

You are not passing the parameters needed to the controller method,id and quantity. In your Html.BeginForm add the values for id and quantity.

@model UberUnlock.ViewModel.MultipleModelInOneView


                <dd>
                    @using (Html.BeginForm("AddToBasket", "Basket", new { id = Model.Products.ID,quantity = quantityvalue }))
                    {
                        @Html.AntiForgeryToken()
                        @Html.HiddenFor(model => model.Products.ID)

                        @Html.DropDownList("quantity", Enumerable.Range(1, 10).Select(i => new SelectListItem { Text = i.ToString(), Value = i.ToString() }))
                        <input type="submit" class="btn btn-primary btn-default margin" value="Add to Basket">
                    }
                </dd>

<p>

@Html.ActionLink("Edit", "Edit", new { id = Model.Products.ID }) |
@Html.ActionLink("Back to List", "Index")
</p>  

Or if you do not want to pass any values all the time you can make the parameters in your controller nullable. Or as pointed out by Rahul, you can set them to 0.

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult AddToBasket(int? id, int? quantity)
{
    Basket basket = Basket.GetBasket();
    basket.AddToBasket(id, quantity);
    return RedirectToAction("Index");
}

Or the other way is to remove the parameters id and quantity and pass the view model.

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult AddToBasket(MultipleModelInOneView model)
{
    Basket basket = Basket.GetBasket();
    basket.AddToBasket(model.Product.ID, model.Product.quantity);
    return RedirectToAction("Index");
}

Upvotes: 1

Related Questions