1

I have a AJAX call from my webpage sending the following data to my MVC3 action method.

{
  "name":"Test",
  "newitems":[
    {"id":15,"amount":100,"unit":"gram"},
    {"id":1,"amount":75,"unit":"gram"},
    {"id":46,"amount":25,"unit":"gram"}
  ]
}

In my controller I have the following classes:

public class NewDataItem
{
  public string name { get; set; }
  public List<NewDataItemDetails> newitems { get; set; }
}

public class NewDataItemDetails
{
  public int id { get; set; }
  public int amount { get; set; }
  public string unit { get; set; }
}

And the Action method that received the request have a NewDataItem as a parameter. This works perfect, however the amount property of NewDataItemDetails might not always contain an int. It might for example be 50.45. So because of that I changed the line public int amount { get; set; } to public decimal amount { get; set; }.

After this change amount is always shown as 0, and not the proper value that it did when it was an int.

Why does MVC fail to bind the value to the property when it is a decimal, when it worked just fine as an int?

Øyvind Bråthen
  • 59,338
  • 27
  • 124
  • 151

5 Answers5

1

I found the problem.

If I change the line "amount":100, to "amount":"100", it works fine. It seems that the MVC ModelBinder can manage the string to decimal conversion, but not the int to decimal.

Øyvind Bråthen
  • 59,338
  • 27
  • 124
  • 151
1

See the answer here Default ASP.NET MVC 3 model binder doesn't bind decimal properties from ryudice about creating a DecimalModelBinder. It works and it also keeps all the model validation working, (some other solutions use deserialization which can stop validation from working.

Community
  • 1
  • 1
Jafin
  • 4,153
  • 1
  • 40
  • 52
0

If you don't want to change model binder then you can create json object and convert amount to string.It will work fine for me.

var test={"amount":""};
var test1={"amount":100}
test.amount=test1.amount.toString();
Thakur Rock
  • 515
  • 5
  • 7
0

Your type (class) NewDataItemDetails property amount is of type int.

You are making things difficult to manage. If you are expecting to have amount as a decimal eventually, it simplifies to actually use amount's type as decimal.

This will avoid having you to extend the default model binder and cater for your behaviour.

I think, it is wiser and it simplies to send the amount as decimal in the ajax call. it provides consistency.

Neelesh
  • 475
  • 3
  • 16
  • How do I send it as decimal in the ajax call? JavaScript makes no distinction between ints and decimals. It's just numbers to JavaScript. – Øyvind Bråthen Aug 26 '11 at 07:49
  • And the point is that I want to have the property as a decimal in my class, but it's currently not working. That's why it's currently an int. But the good news is... I got it solved :) See my answer for details. – Øyvind Bråthen Aug 26 '11 at 07:50
  • Yes, it will work given that you changed amount to decimal. :) – Neelesh Aug 26 '11 at 07:55
  • Nope, it worked because I added "" around the actual amount in the JSON data. I tried setting the data type to decimal in my data object before posting the question of course. – Øyvind Bråthen Aug 26 '11 at 10:20
0

I know I am a bit late with this but there is another solution which works without changing anything until MVC fixes it (I believe it is at their end).

In my javascript I add 0.00001 to my value if it is supposed to be a decimal but is a round number. For those I know should be currency values I know this has no effect and will round down. For those that I do not know their value and this could affect it I remove the 0.00001 from the value after binding in mvc. The binding works correctly as this is no longer an int in the eyes of mvc