Используя MVC 3 Entity Framework Code-First, как вы создаете новый объект many в отношении «один ко многим»?

Я уверен, что это очень прямолинейно, однако, прошерстив сеть, я не могу найти ничего, что могло бы меня исправить.

Я использую ASP.NET MVC 3 с моделированием Entity Framework Code-first.

У меня есть простая связь «один ко многим» между календарем и событием (для каждого календаря может быть 0 или более событий).

Проще говоря, я не понимаю, как создать/вставить новое событие, связанное с календарем.

Мои определения домена объекта:

public class Calendar
{
    [Key]
    public long id { get; set; }
    public string title { get; set; }
    public string description { get; set; }
    public virtual ICollection<Event> events { get; set; }
} //class

public class Event
{
    [Key]
    public long id { get; set; }          
    public string title { get; set; }
    public string description { get; set; }
    public DateTime startdate { get; set; }
    public DateTime enddate { get; set; }
    public int importance { get; set; }
} //class

Я создал страницу со ссылкой «Создать новое событие», которая передает идентификатор календаря действию CalendarController с именем «Создать» (/localhost:xxxxx/Calendar/Create/1).

Я застрял на этом этапе, как и в случае с кодом, у меня нет calendar_id (или чего-то подобного) в качестве указанного члена класса Event, чтобы связать событие с календарем. Он существует в базе данных, поскольку столбец был сгенерирован механизмом code-first.

Я попытался создать ViewModel, сочетающий идентификатор календаря и объект Event, однако, когда я возвращаюсь из Create.cshtml, идентификатор календаря сбрасывается с 1 на 0, хотя информация о событии была действительной.

В заключение, в отношениях «один ко многим» (как указано выше), как вы создаете новое событие (многие стороны) с календарем (одна сторона)? Я уверен, что это довольно просто, и я что-то упускаю, но любая помощь будет оценена по достоинству.

/****************/

Вот немного больше деталей, которые, я надеюсь, добавят ясности в мою проблему.

  1. Пользователь выбирает Календарь (calendar_id, скажем, 1).
  2. На странице сведений для этого конкретного календаря есть ссылка на контроллер/действие (CalendarController/CreateEvent) для создания нового события, связанного с этим конкретным календарем. Созданный маршрут — Calendar/CreateEvent/1 (создайте новое событие для календаря с идентификатором == 1).
  3. В действии CreateEvent теперь у меня есть идентификатор экземпляра календаря для нового события.

Вот тут я запутался...

Объект Event не имеет члена данных calendar_id, так как он создается движком code-first, поэтому мне нечего назначать calendar_id, полученный в данных маршрута.

Я знаю, что это стандартная ситуация, но я что-то упускаю. Мне нужно сохранить calendar_id до [HttpPost]CreateEvent. Оттуда я могу просто найти нужный календарь (используя calendar_id), взять информацию из формы нового события (в CreateEvent.cshtml), чтобы создать новое событие, и просто вызвать Calendar.Add(newEvent).

Как мне сохранить calendar_id (или календарь, если на то пошло) на протяжении всего цикла GET/form/POST?

Еще раз спасибо за любую помощь.

/****************/ Я повторно попробовал возможное решение, упомянутое ниже, чтобы добавить виртуальный календарь и CalendarId в класс Event. Я изменил параметр действия, принятый для объекта Event, для функций HttpGet и HttpPost. В функции HttpGet я устанавливаю CalendarId в значение календаря, в который будет добавлено новое событие (как указано выше, идентификатор == 1). Все работало нормально в представлении CreateEvent, однако при возврате к действию HttpPost CreateEvent CalendarId был сброшен до 0.

Я все еще что-то упускаю... но спасибо за помощь, и я все еще ищу эту искру.


person Billbris    schedule 09.08.2011    source источник


Ответы (2)


Потратив некоторое время на то, чтобы переосмыслить свою проблему и провести дополнительные исследования, я нашел следующую информацию и решение.

Во-первых, очень хорошее руководство (немного длинное, но много подробностей) доступно по адресу: http://www.asp.net/entity-framework/tutorials/creating-an-entity-framework-модельданных-для-an-asp-net-mvc-приложения

Этот учебник не углубляется и не использует Ioc, однако концепции, касающиеся структуры сущностей и первых идей кода, очень полезны.

Что касается моего решения, я сделал две вещи: 1. В соответствии с приведенным выше руководством я добавил два поля в свой класс Event. Я добавил свойства «long timeline_id» и «календарь виртуального календаря». Это дает мне место для хранения timeline_id, переданного в действие контроллера CreateEvent. И свойство виртуального календаря предоставляет свойство навигации обратно к таблице календаря. 2. Я решил использовать скрытое поле в форме CreateCalendar cshtml для создания нового события. Это позволяет сохранить timeline_id в форме, а затем вернуть его в экземпляр HttpPost действия CreateEvent.

Это решает мою проблему, однако, если у кого-то есть более элегантное решение, дайте мне знать.

person Billbris    schedule 10.08.2011

Что я обычно делаю, поскольку я гораздо лучше знаком с тем, как обычно должна выглядеть структура таблицы базы данных, чем с синтаксисом EF Code First, так это настраиваю свои таблицы, а затем использую EF Power Tools, чтобы преобразовать таблицы в POCO и сопоставления.

Reverse
(источник: msdn.com)

Что касается ваших сущностей, почему бы просто не добавить свойство Calendar в ваш класс Event

public class Event
{
    [Key]
    public long id { get; set; }          
    public string title { get; set; }
    public string description { get; set; }
    public DateTime startdate { get; set; }
    public DateTime enddate { get; set; }
    public int importance { get; set; }

    public virtual Calendar Calendar { get; set; }
    public int CalendarId { get; set; }
} //class
person kenwarner    schedule 09.08.2011
comment
Спасибо. Я буду иметь это в виду в следующий раз (это на самом деле звучит довольно интересно), однако у меня все на месте, и я знаю, что просто упустил что-то глупое, и я хотел бы узнать, что это такое. - person Billbris; 10.08.2011
comment
Что касается вашего последнего вопроса (почему бы не добавить календарь...). Движок code-first пожаловался, что у меня было два CalendarId, когда я это делал. Конфликт возник из-за того, что я вручную ввел CalendarId и CalendarId, сгенерированный движком code-first. - person Billbris; 10.08.2011