简体   繁体   中英

asp.net mvc4 won't properly deserialize and bind Dictionary<string,List<CustomType>> from json

JSON.NET deserializes it fine, but whatever mvc uses for controller parameter binding barfs hard. Can I do anything else to make this work?

The bits:

  public partial class Question
  {
    public Dictionary<string, List<QuestionExtendedProp>> TemporaryExtendedProperties { get; set; }
  }

And the controller method

[HttpPost]
public JsonResult SaveQuestions(Question[] questions)
{
  var z =
    JsonConvert.DeserializeObject(
      "{'Options':[{'PropKey':'asdfasd','PropVal':'asdfalkj'},{'PropKey':'fdsafdsafasdfas','PropVal':'fdsafdas'}]}",
      typeof (Dictionary<string, List<QuestionExtendedProp>>)) as Dictionary<string, List<QuestionExtendedProp>>;
  //this deserializes perfectly. z is exactly what I want it to be
  //BUT, questions is all wrong. See pic below

  //lots of code snipped for clarity, I only care about the incoming questions object
  return Utility.Save(questions);
}

Here's what MVC gives me for this exact string (Pulled from fiddler, extras snipped for your reading pleasure)

    "TemporaryExtendedProperties":{"Options": 
        [{"PropKey":"NE","PropVal":"NEBRASKA"}, 
         {"PropKey":"CORN","PropVal":"CHILDREN OF"}, 
         {"PropKey":"COW","PropVal":"MOO"}]}

“局部”面板中的奇怪反序列化值

Why does MVC mangle the binding from this perfectly fine json string and how can I get it to not do so? I have complete control over the json structure and creation.

Edit
I tried changing the type of Question.TemporaryExtendedProperties to List<KeyValuePair<string, List<QuestionExtendedProp>>> , but that didn't work either. Here's the new json (which matches exactly what System.Web.Script.Serialization.JavaScriptSerializer serializes an object to!)

{
   TemporaryExtendedProperties: [
      {
         Key: 'Options',
         Value: [
            {
               PropKey: 'NEBRASKA',
               PropVal: 'NE'
            },
            {
               PropKey: 'DOG',
               PropVal: 'CORN'
            },
            {
               PropKey: 'MEOW???',
               PropVal: 'COW'
            }
         ]
      }
   ]
}

That didn't work either. It's deserialized by the controller to a List<blah,blah> properly, with a count of 1 (as expected), but the Key and Value are both null . Json.NET again handles it perfectly.

Ugh.

I ended up just removing the need for a dictionary. The new code looks like this:

//Other half is autogenerated by EF in models folder
public partial class Question
{
    public List<QuestionExtendedProp> TemporaryExtendedProperties { get; set; }
}

//Other half is autogenerated by EF in models folder
public partial class QuestionExtendedProp
{
    public string DictionaryKeyValue { get; set; }
}

mvc handles this just fine. My controller now looks like this

[HttpPost]
public JsonResult SaveQuestions(Question[] questions)
{

  foreach (var q in questions)
  {
    //do regular question processing stuff
    //20 lines later
    IEnumerable<IGrouping<string, QuestionExtendedProp>> ExtendedPropGroups = q.TemporaryExtendedProperties.GroupBy(x => x.DictionaryKeyValue);
    foreach (IGrouping<string, QuestionExtendedProp> group in ExtendedPropGroups)
    {
      string groupKey = group.Key;
      foreach (var qexp in group)
      {
        //do things here
      }
    }
  }
  //rest of the stuff now that I've processed my extended properties...properly
  return Utility.SaveQuestions(questions);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM