#nhibernate #collections #paging
#nhibernate #Коллекции #подкачка
Вопрос:
У меня есть объект с коллекцией пакетов, и я хочу просмотреть весь набор данных. В коллекции есть предложение order-by. Когда я пытаюсь загрузить коллекцию, NHibernate генерирует SQL, который работает очень медленно, потому что это заставляет SQL Server сортировать по очень неуникальному свойству, а в таблице содержится большой объем данных.
Код:
var session = NHibernateSessionManager.Instance.GetSession();
session.CreateCriteria<Album>()
.SetFetchMode("Track", FetchMode.Eager)
.SetMaxResults(1000)
.SetFirstResult(1)
.AddOrder(new Order("Id", true))
.List();
Сопоставление пакета (обратите внимание на атрибут order-by):
<bag name="Track" inverse="true" lazy="true" batch-size="1000" cascade="none"
order-by="TrackNumber ASC">
Соответствующий SQL сгенерированный:
OVER(ORDER BY track2_.TrackNumber, this_.Id) as __hibernate_sort_row
Если я удалю order-by из сопоставления, SQL изменится на это (намного лучше):
OVER(ORDER BY this_.Id) as __hibernate_sort_row
Итак, вопрос: есть ли способ переопределить или удалить сопоставленное предложение order-by?
Комментарии:
1. У вас нет способа изменить сопоставления hbm после создания фабрики сеансов. Почему бы вам просто не удалить order-by в сопоставлении hbm напрямую? Вы всегда можете добавить 2 заказа во время запроса.
2. как сказал Тилак Натен, вы не можете переопределить после создания фабрики, но вы можете в объекте конфигурации и создать другую фабрику с этой настройкой. я иногда использовал его, когда мне нужны небольшие корректировки, не знаю, возможно ли это в вашей ситуации
Ответ №1:
После комментариев Тилака Натена и Фиро похоже, что короткий ответ на вопрос: «Нет, вы не можете этого сделать». Длинный ответ заключается в удалении атрибута order-by из сопоставления и добавлении его по мере необходимости. Причина, по которой это было, заключается в том, что это всегда необходимо, за исключением этой необычной ситуации. Фиро предложил переопределить заводскую конфигурацию, которая, я думаю, будет работать, потому что это для отчетности. Для всех, кто хочет знать, как это сделать, вот код для удаления order-by из сопоставления xml программно:
Configuration cfg = new Configuration().Configure();
var albumMapping = cfg.ClassMappings.Where(x => x.DiscriminatorValue == "Foo.Album").First();
var trackProperty = albumMapping.GetProperty("Track");
var bagMapping = ((NHibernate.Mapping.Bag)trackProperty.Value);
bagMapping.OrderBy = "";
sessionFactory = cfg.BuildSessionFactory();