Текущая система, над которой я работаю, использует Castle Activerecord для обеспечения ORM (Object Relational Mapping) между объектами Domain и базой данных. Это все хорошо, и в большинстве случаев на самом деле хорошо работает!
Проблема возникает с поддержкой Castle Activerecords для асинхронного выполнения, а точнее, SessionScope, который управляет сеансом, к которому принадлежат объекты. Короче говоря, случается плохое!
Поэтому мы ищем способ легко преобразовать (мыслить автоматически) из объектов Домена (которые знают, что БД существует и заботится) в объект DTO (которые ничего не знают о БД и не заботятся о сессиях, отображая атрибуты или все это ORM).
Есть ли у кого-нибудь предложения по этому поводу? Для начала я ищу базовое сопоставление объекта «один к одному». Объект домена Person будет отображен, чтобы сказать PersonDTO . Я не хочу делать это вручную, так как это пустая трата времени.
Очевидно, что на ум приходит размышление, но я надеюсь, что некоторые лучшие ИТ-знания, распространяющиеся вокруг этого сайта, предложат "круче" .
О, я работаю в C #, объекты ORM, как было сказано ранее, сопоставлены с Castle ActiveRecord.
Пример кода:
По запросу @ ajmastrean я связал с примером, который я (плохо) высмеял вместе. В этом примере есть форма захвата , форма захвата контроллер , домен объекты, activerecord репозиторий и async помощник , Это немного большой (3 МБ), потому что я включил ActiveRecored DLL, необходимые для его запуска. Вам нужно будет создать базу данных с именем ActiveRecordAsync на локальном компьютере или просто изменить файл .config.
Основные детали примера:
Форма захвата
Форма захвата имеет ссылку на контроллер
private CompanyCaptureController MyController { get; set; }
При инициализации формы она вызывает MyController.Load ()
закрытое void InitForm ()
{
MyController = новый CompanyCaptureController (это);
MyController.Load ();
}
Это вернется к методу LoadComplete ()
public void LoadCompleted (Company loadCompany)
{
_context.Post(delegate
{
CurrentItem = loadCompany;
bindingSource.DataSource = CurrentItem;
bindingSource.ResetCurrentItem();
//TOTO: This line will thow the exception since the session scope used to fetch loadCompany is now gone.
grdEmployees.DataSource = loadCompany.Employees;
}, null);
}
}
это то место, где "плохие вещи" встречаются, так как мы используем дочерний список Company, который установлен как Ленивая загрузка.
Контроллер
Контроллер имеет метод Load, который был вызван из формы, затем он вызывает помощник Asyc для асинхронного вызова метода LoadCompany, а затем возвращается к методу LoadComplete формы Capture.
public void Load ()
{
new AsyncListLoad<Company>().BeginLoad(LoadCompany, Form.LoadCompleted);
}
Метод LoadCompany () просто использует Репозиторий, чтобы найти известную компанию.
public Company LoadCompany()
{
return ActiveRecordRepository<Company>.Find(Setup.company.Identifier);
}
Оставшаяся часть примера является довольно общей, в ней есть два класса домена, которые наследуются от базового класса, установочный файл для вставки некоторых данных и хранилище для обеспечения возможностей ActiveRecordMediator .