В моих приложениях я всегда разделял вещи, используя разные модели для базы данных (Entity Framework) и MVC. Я также разделил их на разные проекты:
- Example.Entities - содержит мои сущности для EF и контекст БД для доступа к ним.
- Example.Models - содержит модели MVC.
- Example.Web - веб-приложение. Зависит от обоих Example.Domain и Example.Models.
Вместо хранения ссылок на другие объекты, как это делают сущности домена, модели MVC содержат идентификаторы как целые числа.
Когда поступает запрос GET для страницы, контроллер MVC выполняет запрос к базе данных, который возвращает объект. Я написал методы "Converter", которые берут предметную сущность и преобразуют ее в модель MVC. Существуют и другие методы, которые делают обратное (от модели MVC до сущности домена). Затем модель передается в представление и, следовательно, клиенту.
Когда приходит запрос POST, контроллер MVC получает модель MVC. Метод конвертера преобразует это в объектную сущность. Этот метод также выполняет любые проверки, которые не могут быть выражены как атрибуты, и гарантирует, что, если сущность домена уже существует, мы обновляем ее, а не получаем новую. Методы обычно выглядят примерно так:
public class PersonConverter
{
public MyDatabaseContext _db;
public PersonEntity Convert(PersonModel source)
{
PersonEntity destination = _db.People.Find(source.ID);
if(destination == null)
destination = new PersonEntity();
destination.Name = source.Name;
destination.Organisation = _db.Organisations.Find(source.OrganisationID);
//etc
return destination;
}
public PersonModel Convert(PersonEntity source)
{
PersonModel destination = new PersonModel()
{
Name = source.Name,
OrganisationID = source.Organisation.ID,
//etc
};
return destination;
}
}
Используя эти методы, я убираю дублирование, которое в противном случае происходило бы в каждом контроллере. Использование генериков может дедуплицировать вещи еще дальше.
Выполнение этих действий дает множество преимуществ:
- Вы можете настроить модель для конкретного вида или действия. Скажем, у вас есть форма регистрации для человека, которая при отправке создает много разных объектов (человек, организация, адрес). Без отдельных моделей MVC это будет очень сложно.
- Если мне нужно передать в представление больше информации, чем было бы доступно в сущности, или объединить две сущности в одну модель, то мои драгоценные модели баз данных никогда не будут затронуты.
- Если вы когда-либо сериализуете модель MVC как JSON или XML, вы получаете сериализованную только непосредственную модель, а не любую другую сущность, связанную с этой.