Динамическое добавление и удаление элементов в одном представлении с помощью Entity Framework и MVC - PullRequest
3 голосов
/ 01 марта 2011

Я уже некоторое время рассматриваю этот же вопрос в разных формах (см., Например, Entity Framework и MVC 3. Отношение не может быть изменено, поскольку одно или несколько свойств внешнего ключа не допускают обнуление), и это все еще беспокоит меня, поэтому я подумал, что я бы сказал немного более обобщенно:

Я чувствую, что это не может быть очень необычной проблемой:

У вас естьобъект сущности (используя Entity Framework), скажем, User.У пользователя есть несколько простых свойств, таких как FirstName, LastName и т. Д. Но у него также есть некоторые списки свойств объекта, например, рассылаемые по электронной почте примеры электронной почты.Электронная почта часто представляет собой список объектов, так что вы можете добавить к этому объекту свойства, такие как Адрес и Тип (Дом, Работа и т. Д.).Я использую это в качестве примера, чтобы сохранить его универсальным, но это может быть что угодно, дело в том, что вы хотите, чтобы пользователь мог добавлять произвольное количество этих элементов.Вы также должны иметь возможность удалять элементы (старый адрес или любой другой).

Теперь на обычной веб-странице вы ожидаете, что сможете добавить эти элементы в том же представлении.Но MVC в том виде, в котором он кажется разработанным, облегчает это, если вы вызываете совершенно новый View только для добавления адреса.(В шаблоне для индексного представления вы получаете ссылку «Создать новый», например).

Я встречал пару примеров, которые делают что-то близкое к тому, что я имею в виду:

http://haacked.com/archive/2008/10/23/model-binding-to-a-list.aspx

и

http://blog.stevensanderson.com/2010/01/28/editing-a-variable-length-list-aspnet-mvc-2-style/

Проблема в том, что примеры проектов на этих сайтах работают нормально, с объектами фиктивной модели и просто списками (необъект с дочерним списком), это совсем другое дело, если вы действительно хотите что-то сделать с опубликованной информацией - в моем случае сохраните в базу данных через модель Entity Framework.Чтобы приспособить эти случаи к этому, я внезапно оказался в лабиринте запутанного и определенно не СУХОГО кода ... Жонглирование объектов с помощью AutoMapper и еще много чего, и Entity Framework не позволит вам сохранять и так далее (см. Выше).ссылка, если вы заинтересованы в деталях).

Что я хочу получить, это действительно ли возможно, что это такая необычная вещь, чтобы хотеть сделать?Обновить дочернюю коллекцию в том же представлении, что и родительский объект (например, адреса электронной почты в данном случае)?Мне кажется, что это не может быть необычным для всех, и должен быть стандартный способ обработки такого сценария, и я просто скучаю по нему (и никто здесь до сих пор не смог указать мне на прямойрешение, возможно, потому что я сделал его слишком абстрактным с моими собственными примерами приложений).

Так что, если есть простое решение того, что, на мой взгляд, должно быть простой проблемой (так как дизайн очень распространен), пожалуйста, сообщитея.

1 Ответ

0 голосов
/ 01 марта 2011

Вы пытались обновить проект по ссылке на блог Стивена Андерсона, чтобы привязать его к сложному объекту? Создайте класс в моделях с именем Sack, присвойте ему одно свойство и посмотрите, сможете ли вы заставить его работать.

public class Sack
{
    public IEnumberable<Gift> Gifts { get; set; } 
}

Мне понадобилось всего минуту, чтобы настроить его и запустить, как я думаю, вы собираетесь. Следующее улучшение, которое я сделал бы, это добавление расширения HtmlHelper, которое по существу совпадает с Html.EditorFor(m => m.SomeProperty), только назовите его чем-то более значимым и сделайте его интерфейсом с расширениями области префикса, предоставленными в проекте.

public static class HtmlExtensions
{
    public static IHtmlString CollectionEditorFor<TModel, TValue>(this HtmlHelper html, Expression<Func<TModel, TValue>> expression)
    {
        if (/* type of expression value is not a collection */) throw new FailureToFollowTheRulesException("id10t");

        // your implementation
    }
}
...