1

Please go easy on me as I'm very new to MVC and web development in general.

I've inherited an ASP website which currently only has an 'OK' and 'Cancel' button. I need to break out 'OK' into two separate actions ('Add' and 'Remove'). 'Cancel' should still redirect the user back to the site homepage.

Here is the cshtml:

<script type="text/javascript">
    var dict = {};
    function Cancel() {
        window.location = "/Home/Index/";
    }

</script>

@using (Html.BeginForm("SaveServiceWindow", "Approve", FormMethod.Post, new { name = "SaveServiceWindow" }))
{
 <!--
  Other form controls
 -->


        <tr><td>Desired Action:</td></tr>
        <tr>
            <td align="left" width="300">
                <input type="submit" value="Add Group" name="Add" id="submit" />
            </td>
            <td align="left" width="300">
                <input type="submit" value="Remove Group" name="Remove" id="submit" />
            </td>
            <td align="left" width="300">
                <input type="button" value="Cancel" onclick="Cancel();" />
            </td>
        </tr>
    </table>
}

And here is how the Controller method is declared (I'm not including the method contents as it's not relevant to the question):

[HttpPost]
public ActionResult SaveServiceWindow(FormCollection collection, TemporalApprovalModel approvalInfo)
    {
    }

I see that a FormCollection object is being passed to this method. I found this answer which looks really promising, however, I'm a bit confused regarding how to retrofit the existing code:

  • in the cshtml I have, I'm passing a method name in Html.BeginForm. Is there a permutation of BeginForm where the submit button method doesn't need to be hard-coded?
  • Also, would I still be able to pass in a FormCollection object to the controller methods (as opposed to a MessageModel object as indicated in the linked answer)?
Mike Bruno
  • 600
  • 2
  • 9
  • 26

1 Answers1

1

The post you linked to is pretty old. You can now use html attributes to do all of the work, assuming your target environment supports them. By using this method, you can keep your existing parameters without any trouble.

First, you'll want an action on your controller for each button.

So, split SaveServiceWindow into two actions, such as AddGroup and RemoveGroup.

[HttpPost]
public ActionResult AddGroup(FormCollection collection, TemporalApprovalModel approvalInfo)
{
}

[HttpPost]
public ActionResult RemoveGroup(FormCollection collection, TemporalApprovalModel approvalInfo)
{
}

Second, on your buttons, you can use the attributes formaction and formmethod to specify one of your new actions.

<td align="left" width="300">
    <input type="submit" formmethod="post" formaction="@Url.Action("AddGroup", "{ControllerName}")" value="Add Group" name="Add" id="submit" />
</td>
<td align="left" width="300">
    <input type="submit" formmethod="post" formaction="@Url.Action("RemoveGroup", "{ControllerName}")" value="Remove Group" name="Remove" id="submit" />
</td>

where {ControllerName} is the name of your controller. You may need to modify the @Url.Action function to fit your application.

When you click your submit button, it will call the correct action.

Please refer to the MDN Web Doc for the input element to see if this is compatible with your environment. Do a search for formaction and you'll see the compatibility table. You can also see more information on formaction and formmethod there.

EDIT: Some additional tips.

When generating your form, make sure to remove the current posting information while testing:

@using (Html.BeginForm("SaveServiceWindow", "Approve", FormMethod.Post, new { name = "SaveServiceWindow" }))
{
}

to

@using ()
{
}

Since the formaction and formmethod are specified on the input, you don't need them on the form.

To make sure the correct link is being generated, right click on the input and click Inspect. See what the input attributes are and make sure they're right.

Since you're not very experienced with web development (in your own words, not being rude), I suggest you read over some basic information on HTML forms. Whenever you're generating a POST request, and not using AJAX, you'll need a form to submit your data with. Then, take a look at how this can be done in MVC using the Razor engine.

Jack
  • 1,453
  • 1
  • 15
  • 35
  • Thanks! So, in the @Url.Action function, the first parameter would be the name of the method in the Controller, and the second one would be the name of the Controller class? – Mike Bruno Nov 01 '18 at 18:06
  • Yes. You may want to go [read](https://learn.microsoft.com/en-us/dotnet/api/system.web.mvc.urlhelper.action?view=aspnet-mvc-5.2) on @Url.Action to get an understanding of how it works. If my answer helped you, please consider marking it as best answer and giving it an upvote. Thanks! Feel free to comment if you have any issues, too. – Jack Nov 01 '18 at 18:11
  • To expand on that, @Url.Action isn't necessary. You can, technically, hardcode the url for `formaction`. But that is bad practice. @Url.Action will generate the correct url for you. – Jack Nov 01 '18 at 18:11
  • Thanks again! So, I implemented the individual actions and applied the edits to the cshtml per your instructions. The buttons all render, however, nothing happens when I click on them (besides Cancel which I did not change). We are on IE 11 and Chrome 66, so it doesn't look like compatibility with the input element is the issue here. I imagine that there could be many issues going on here, but any guesses? If I, say, had a typo or syntax error in the Controller or Action name, is ASP smart enough to detect that they do not exist & prevent the button from doing anything? – Mike Bruno Nov 01 '18 at 18:36
  • One other thing I should mention is that I removed the @using container as I figured that was only applicable when there was a single submit button that was bound to a single Controller action – Mike Bruno Nov 01 '18 at 18:41
  • I added some additional explanation for a few things I could think of. If you have a syntax error, the compiler should catch it at the very least, if not your IDE. You definitely still need to generate the form, so add that back in as described in my edited answer. – Jack Nov 01 '18 at 18:42
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/182960/discussion-between-mike-bruno-and-jack). – Mike Bruno Nov 01 '18 at 18:50