Andrew Mallonee
Andrew Mallonee

Reputation: 374

How to omit/prevent data from being sent to the POST method in the Controller in MVC

I have a view that is using a model and I am using that information to create a form. I have three steps of the form that are optional or may not be shown.

The problem is that these hidden sections get posted along with the form data and break the business logic. (I have no control over the business logic)

So is there a way to tell the framework not to pass certain sections or fields? Perhaps VIA a class or something?

I know I could use AJAX to send certain sections as they are needed, but the site spec is to have them hidden and displayed as needed.

Upvotes: 4

Views: 1818

Answers (2)

Erik Philips
Erik Philips

Reputation: 54628

Although you could do this client-side, it won't stop malicious over-posting/mass assignment.

I suggest reading 6 Ways To Avoid Mass Assignment in ASP.NET MVC.

Excerpts:

Specify Included Properties only:

[HttpPost]
public ViewResult Edit([Bind(Include = "FirstName")] User user)
{
  // ...
}

Specify Excluded Properties only:

[HttpPost]
public ViewResult Edit([Bind(Exclude = "IsAdmin")] User user)
{
  // ...
}

Use TryUpdateModel()

[HttpPost]
public ViewResult Edit()
{
  var user = new User();
  TryUpdateModel(user, includeProperties: new[] { "FirstName" });
  // ...
}

Using an Interface

public interface IUserInputModel
{
  string FirstName { get; set; }
}

public class User : IUserInputModel
{
  public string FirstName { get; set; }
  public bool IsAdmin { get; set; }
}

[HttpPost]
public ViewResult Edit()
{
  var user = new User();
  TryUpdateModel<IUserInputModel>(user);
  // ...
}

Use the ReadOnlyAttribute

public class User 
{
  public string FirstName { get; set; }

  [ReadOnly(true)]
  public bool IsAdmin { get; set; }
}

Lastly, and the most recommended approach is to use a real ViewModel, instead a domain Model:

public class UserInputViewModel
{
  public string FirstName { get; set; }
}

Upvotes: 2

EternalWulf
EternalWulf

Reputation: 773

Show/Hide will not allow/disallow the value from being sent to the Controller.

Elements that are Disabled or just not editable will (99% of the time) be returned as null / minVal.

You can set the elements in the View as Disabled by using JQuery in the script:

$('#elementID').attr("disabled", true);

OR you could use a DOM command:

document.getElementById('elementID').disabled = "true";

So you can set the fields as both Disabled AND Hidden, so that it is neither displayed, nor populated. Then in your Controller you can just base the Business Logic on whether or not certain fields (preferable Mandatory fields, if you have any) are null.


You can check this in C# like this: For a string:

if (string.IsNullOrWhiteSpace(Model.stringField))
{
    ModelState.AddModelError("stringField", "This is an error.");
}

For a DateTime:

if (Model.dateTimeField == DateTime.MinValue)
{
    ModelState.AddModelError("dateTimeField ", "This is an error.");
}

Just for interest sake, here is how you can Hide/Show elements on the View using JQuery:

$('#elementID').hide();
$('#elementID').show();

Upvotes: 1

Related Questions