Связывание модели с массивом json, содержащим объекты различных типов, в Asp.Net MVC - PullRequest
1 голос
/ 22 июня 2011

У меня есть массив json, содержащий целые числа и объекты.

[1,2,3,{Name:"russia",Value:6},{Name:"usa",Value:"8"}]

У меня также есть следующий класс на стороне сервера

class country {
  string Name;
  int Value;
}

Как мне связать массив json с параметром на стороне сервера? Я попытался использовать List<object> на сервере. Он отлично связывает целые числа, но экземпляры стран не создаются. Вместо этого примитивные объекты создаются и добавляются в список.

Спасибо.

Ответы [ 2 ]

1 голос
/ 28 июня 2011

Хорошо, я наконец решил это. Для этого я создал пользовательский механизм связывания моделей, полученный из стандартного механизма связывания моделей. Вот код.

public ActionResult Home(NonHomogeneousList input)

[ModelBinder(typeof(CustomModelBinder))]
class NonHomogeneousList : List<object>

public class CustomModelBinder : DefaultModelBinder
{
    public override object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
        {
            NonHomogeneousList model = (NonHomogeneousList)base.BindModel(controllerContext, bindingContext);
            if (model.Members != null)
            {
                IModelBinder countryBinder = Binders.GetBinder(typeof(Country));

            // find out if the value provider has the required prefix
            bool hasPrefix = bindingContext.ValueProvider.ContainsPrefix(bindingContext.ModelName);
            string prefix = (hasPrefix) ? bindingContext.ModelName + "." : "";

            for (var i = 0; i < model.Count; i++)
            {
                var member = model.Members[i];
                if (member.GetType().Equals(typeof(object)))
                {
                    var subKey =  CreateSubIndexName( prefix , i);
                    ModelBindingContext innerContext = new ModelBindingContext()
                    {
                        ModelMetadata = ModelMetadataProviders.Current.GetMetadataForType(null, typeof(Country)),
                        ModelName = subKey,
                        ModelState = bindingContext.ModelState,
                        PropertyFilter = bindingContext.PropertyFilter,
                        ValueProvider = bindingContext.ValueProvider,
                    };
                    var country = countryBinder.BindModel(controllerContext, innerContext);
                    model.Members[i] =  country;
                }
            }
        }
        return model;
    }
}
}
1 голос
/ 22 июня 2011

Вы можете попробовать что-то вроде этого:

Отформатируйте действие контроллера, чтобы принять List<int> для ваших целочисленных значений и List<Country> для объектов вашей страны.

public ActionResult Index(List<int> intValues, List<Country> countryValues)

Затем создайте свой JSON-файл так, чтобы он содержал и массив целых чисел, и массив объектов страны:

var postData = {
    intValues: [1, 2, 3],
    countryValues: [
        { Name: 'USA', Value: 6 },
        { Name: 'Russia', Value: 8 }
    ]
};

и выполнить простой вызов AJAX для отправки данных

$(function() {
    $.ajax({
        type: 'POST',
        url: "@Url.Action("Create")",
        contentType: "application/json",
        data: JSON.stringify(postData)
    });
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...