2013-05-14 4 views
2

Рассмотрим следующую упрощенную область:жадная загрузка дополнительный один-к-одному с NHibernate

public class Movie 
{ 
    public virtual int Id { get; set; } 
    public virtual MovieDetail MovieDetail { get; set; } 
} 

public class MovieDetail 
{ 
    public virtual int Id { get; set; } 
    public virtual Movie Movie { get; set; } 
} 

MovieDetail не может существовать без Movie, но Movie может существовать без MovieDetail (то есть у нас нет никаких подробностей о Это).

Наша база данных имеет отдельную таблицу для Movie с колоннами Id и отдельную таблицу для MovieDetail с колоннами Id и MovieId. Существует также внешний ключ от MovieDetail.MovieId до Movie.Id.

У нас есть все, что отображается в NHibernate, но при получении коллекции Movie экземпляров мы хотим, чтобы левое внешнее соединение было MovieDetail. Если нет, у нас может возникнуть проблема с N + 1 при итерации по экземплярам Movie. Это имеет место сейчас: есть отдельный запрос для каждого вызова свойства Movie.MovieDetail.

Я пробовал сопоставление one-to-one, но это похоже на случай, когда у вас есть оба экземпляра. В нашем случае у нас не всегда есть MovieDetail. Кроме того, они не используют один и тот же первичный ключ.

Я исследовал формулу, но это потребовало бы, чтобы мой MovieDetail реализовал IUserType, по сути поставив NHibernate в мой домен. Я бы хотел этого избежать.

ответ

0

Возможно, вы можете попробовать добавить отношение «много-к-одному» в карточке Movie к MovieDetail, оно будет действовать как одно к одному.

Если вы установите для параметра «не-null» значение «false», оно также равно нулю. Я не знаю, если вы ленивая загрузка или нет, когда это так, MovieDetail загружается при необходимости, а не по левому соединению.

Должны ли все свойства быть виртуальными в обоих классах?

<many-to-one name="MovieDetail" column="Id" class="MovieDetail" not-null="false" lazy="false"/> 
+0

Я не мог заставить его работать. Возможно, наш домен имеет что-то экзотическое (я его упростил). Свойства действительно должны быть виртуальными (они были). – Peter

0

Я в немного спешил, и я не знаю, если вы можете изменить ваш домен/дб схему, но вы можете попробовать и посмотреть на http://ayende.com/blog/3937/nhibernate-mapping-component.

Мне кажется, что Movie может иметь не более одного MovieDetail, которого может не быть. MovieDetail могут иметь такие свойства, как Description, ReleaseDate, Actors и т. Д. Я не совсем понимаю, почему вы разделили эти понятия. Объединив их, у вас будет 1 меньше стола и 1 меньше FK, чтобы присоединяться каждый раз, когда вы хотите перечислить фильмы.

Компонент позволяет изолировать ваши данные в отдельной сущности при сопоставлении с той же таблицей, что и Movie.

+0

Ну, это был упрощенный домен/схема. Реальная вещь имеет свою причину, поэтому, но я упростил/анонимировал ее. – Peter