开发者

Error with ViewResult and ActionResult containing same parameters

In my controller, I have an Edit GET method to display the view, and an Edit POST method to save the c开发者_JAVA百科hanges:

public ViewResult Edit(int id)
{
    //
}

[HttpPost]
public ActionResult Edit(int id)
{
    //
}

But I'm getting an error saying:

Type 'Controllers.MyController' already defines a member called 'Edit' with the same parameter types

How do I get around this?


You could implement view models so you have EditViewModel containing all of the fields you wish the user to be able to edit and return this in your Edit GET method and have a strongly typed view to the view model. Then that means that in your POST method you would pass the EditViewModel as a parameter, a bit like this:

[HttpGet]
public ViewResult Edit(int id)
{
    //build and populate view model
    var viewModel = new EditViewModel();
    viewModel.Id = id;
    viewModel.Name = //go off to populate fields

    return View("", viewModel)
}

[HttpPost]
public ActionResult Edit(EditViewModel viewModel)
{
    //use data from viewModel and save in database
}

And so your GET and POST methods would have different signatures. Hope this helps.


You have to read this(3.6 Signatures and overloading) about function overloading.

Function overloading

In this approach you can have two or more functions with same name.But each function must have different signature (i.e. different types of parameter, sequence of parameters or number of parameters).

Note: return type is not a signature of parameter

In your code you have implemented both functions with same name and signatures as well.


For another, less elegant solution, imagine a site with a "Wizard-like" structure of pages (Views), where you want to pass the ViewModel from Page 1 to Page 2, from Page 2 to Page 3 etc.

The problem is that the "GET" version of Page 2 needs to receive the model from Page 1, but also needs to pass the model to Page 3 when doing a postback. Therefore both the GET and POST versions of any 'middle' pages need signature which contains the model.

A workaround is to simply add a "junk parameter" to the signature, making sure that it is nullable by using the ?.

    [HttpGet]
    public ActionResult Page2(MyModel myModel)
    {
    }

    [HttpPost]
    public ActionResult Page2(MyModel myModel, int? i)
    {
    }


Its because you are passing same parameter to both the functions which is not allowed although you specify HttpPost on one. You can change the name of the Edit Post function and specify it in Html.BeginForm() or change the parameter to FormCollection instead of int


I think the easiest way to do this is add an additional optional parameter to the global.asax.cs file:

new { controller = "Home", action = "Index", id = UrlParameter.Optional, id2 = UrlParameter.Optional } // Parameter defaults

and change your second function from

[HttpPost]
public ActionResult Edit(int id)

to

[HttpPost]
public ActionResult Edit(int id, int id2)

This way you don't have to change any of your logic. As the second parameter is optional. It wont complain if you don't provide the value.


If you are using a View Model on your POST controller method, make sure your model has an empty constructor. This was driving me nuts.

namespace app.Models
{
    public class UserEdit
    {
        public User User { get; set; }

        public UserEdit() { }
    }
}


You can try this instead.

    public ActionResult Edit()
    {
        return View();
    }

    [HttpPost]
    [ActionName("Edit")]
    public ActionResult EditPosted()
    {
        return View();
    }
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜