#nhibernate #fluent-nhibernate #nhibernate-mapping #lazy-loading
#nhibernate #свободно-nhibernate #nhibernate-сопоставление #отложенная загрузка
Вопрос:
У меня есть несколько объектов больших данных, хранящихся в свойстве CompressedData, поэтому я не хочу загружать эти данные каждый раз, когда я выполняю какой-либо запрос. Поэтому я попытался пометить это свойство как LazyLoad() в классе сопоставления. Нет доступа к CompressedData вне класса объектов, потому что у меня есть свойство UncompressedData, которое предоставляет мне функциональность сжатия / распаковки данных. Поэтому я вызываю CompressedData только внутри класса TestEntity. Но у меня проблема. NHibernate 3.2.0.4000 (или FluentNHibernate 1.3.0.717) не хотел загружать свойство LazyLoad, если нет запросов к этому свойству из класса объектов. Если попытаться запустить тест, я получу пустую строку.
public class TestEntity {
public TestEntity(){}
public TestEntity(string otherData, string dataForCompress){
OtherData = otherData;
UncompressedData = dataForCompress;
}
public virtual string OtherData {get;set;}
public virtual byte[] CompressedData {get;set;}
public virtual string UncompressedData {
get {
return SomeLongFunctionForDecompress(CompressedData);
}
set {
CompressedData = SomeLongFunctionForCompress(value);
}
}
}
public class TestEntityMapping : ClassMap<TestEntity> {
public TestEntityMapping(){
Map(OtherData);
Map(CompressedData).LazyLoad();
}
}
[Test]
public void can_readLazyLoadedProperty(){
TestEntity obj1 = new TestEntity("test","long data here");
using (nHibernateHelper.CreateNewSession(){
Session.Save(obj1);
}
using (nHibernateHelper.CreateNewSession(){
TestEntity obj2 = Session.Get(obj1.Id);
//byte[] data1 = obj2.CompressedData;
string data2 = obj2.UncompressedData;
Assert.AreEqual("long data here",data2);
}
}
Но если раскомментировать byte[] data1 = obj2.CompressedData;
строку, все работает нормально. Может быть, мне нужно добавить какой-то атрибут к свойству CompressedData или добавить некоторые свойства к отображению?
Ответ №1:
Я полагаю, что .NET предоставляет аналогичный механизм, что и Java, и из вашего описания кажется, что это так:
Hibernate изменяет классы объектов, обертывая их в свои собственные объекты, которые изменяют методы получения, чтобы LazyLoad работал
Вызывая методы получения изнутри, вы вызываете неизмененную версию методов получения, которые не обрабатывают LazyLoad.
Итак, это то, что вы получаете, является особенностью, а не ошибкой. Решением может быть перемещение логики за пределы объекта, у которого должны быть только поля и средства доступа.