NHibernate子集合到DTO的投影

NHibernate子集合到DTO的投影,nhibernate,nhibernate-criteria,queryover,Nhibernate,Nhibernate Criteria,Queryover,我已经仔细研究了一下这个问题的答案,有几个问题表明这是不可能的 所以我想知道什么是一个很好的解决方案来向我的DTO投影一个儿童收藏。 我是否需要运行两个单独的投影并手动将子项添加到父项 我使用的是NH3.3.1,我有以下DTO数据结构 public class ProviderDto { public int Id { get; set; } public string Name { get; set; } public IList<EmployerDTO&

我已经仔细研究了一下这个问题的答案,有几个问题表明这是不可能的

所以我想知道什么是一个很好的解决方案来向我的DTO投影一个儿童收藏。 我是否需要运行两个单独的投影并手动将子项添加到父项

我使用的是NH3.3.1,我有以下DTO数据结构

 public class ProviderDto
{
    public int Id { get; set; }
    public string Name { get; set; }
    public IList<EmployerDTO> Employers { get; set; }
}


 public class EmployerDTO
{
    public int Id { get; set; }
    public string Name { get; set; }

}
公共类提供程序到
{
公共int Id{get;set;}
公共字符串名称{get;set;}
公共IList{get;set;}
}
公营雇员
{
公共int Id{get;set;}
公共字符串名称{get;set;}
}
我想将我的提供商和雇主域实体映射到此结构,并进行投影。(在这个简单的场景中,我的域实体与我的dto非常相似)

Employer-EmployerIAS=null;
提供者providerAlias=null;
ProviderDto ProviderDto=null;
var dto=session.QueryOver(()=>providerAlias)
.JoinAlias(x=>x.雇主,()=>EmployeerAlias)
.Where(()=>providerAlias.Id==1)
.Select(Projections.ProjectionList())
.Add(Projections.Property(()=>providerAlias.Id).WithAlias(()=>providerDto.Id))
.Add(Projections.Property(()=>providerAlias.Name).WithAlias(()=>providerDto.Name))
//这是我无法投影我的儿童雇主集合的地方
.TransformUsing(Transformers.AliasToBean()).List();
我如何绘制整个儿童收藏的地图?
非常感谢。

您应该使用futures批量查询并自己构建关系

Employer employerAlias = null;
Provider providerAlias = null;
ProviderDto providerDto = null;
EmployerDto employerDto = null;

var providers = session.QueryOver<Provider>(() => providerAlias)
        .JoinAlias(x => x.Employers, () => employerAlias)
        .Where(()=> providerAlias.Id == 1)
        .Select(Projections.ProjectionList()
        .Add(Projections.Property(() => providerAlias.Id).WithAlias(() =>    providerDto.Id))
        .Add(Projections.Property(() => providerAlias.Name).WithAlias(() => providerDto.Name))
        .TransformUsing(Transformers.AliasToBean<ProviderDto>()).Future<ProviderDto>();

var employers = session.QueryOver<Employer>(() => employerAlias)
//Etc 
.TransformUsing(Transformers.AliasToBean<EmployerDto>()).Future<EmployerDto>();
Employer-EmployerIAS=null;
提供者providerAlias=null;
ProviderDto ProviderDto=null;
EmployerTo EmployerTo=null;
var providers=session.QueryOver(()=>providerAlias)
.JoinAlias(x=>x.雇主,()=>EmployeerAlias)
.Where(()=>providerAlias.Id==1)
.Select(Projections.ProjectionList())
.Add(Projections.Property(()=>providerAlias.Id).WithAlias(()=>providerDto.Id))
.Add(Projections.Property(()=>providerAlias.Name).WithAlias(()=>providerDto.Name))
.TransformUsing(Transformers.AliasToBean()).Future();
var employers=session.QueryOver(()=>employerIAS)
//等
.TransformUsing(Transformers.AliasToBean()).Future();
然后是将正确的雇主映射到提供者的问题。您可能需要DTO中的更多信息,但使用未来的查询,您将只进行一次数据库往返以获取所有信息

编辑:

以便让哪些雇主与哪些供应商进行映射

session.QueryOver(() => provider)
       .JoinAlias(() => provider.Employers, () => employer)
       .SelectList(list => list.Select(() => provider.Id).WithAlias(() =>     peDTO.ProviderId)
                               .Select(() => employer.Id).WithAlias(() =>     peDTO.EmployerId))
       .TransformUsing(Transformers.AliasToBean<ProviderEmployerMapDTO>()).Future<ProviderEmployerMapDTO>();
session.QueryOver(()=>provider)
.JoinAlias(()=>provider.Employers,()=>employer)
.SelectList(list=>list.Select(()=>provider.Id)。带别名(()=>peDTO.ProviderId)
.Select(()=>employer.Id).WithAlias(()=>peDTO.EmployerId))
.TransformUsing(Transformers.AliasToBean()).Future();

太好了。我要试试这个。马上回来。我可以问一下吗。在第二个(雇主)预测中,什么是接近“何处”的最佳方式子句。显然,我需要检索与我刚刚批处理的提供商相关联的所有雇主。但是提供商与雇主之间只有单向关系。谢谢。这就是我说DTO可能需要修改的原因。你可以将ProviderId放在雇主身上吗?还是多对多?如果是多对多,你可以写一个投影将ProviderId:EmployerId列表作为第三个未来查询(添加另一个名为ProviderEmployerTo的DTO)。请记住,您希望对所有查询使用相同的限制。即:ProviderId==1。这是一对多。理想情况下,我不希望向雇主添加提供商参考。在我仍处于第一次投影的上下文中时,有没有办法进行投影?谢谢,在第一次投影后选择一个子选项?或者一些类似的事情(不确定这是否可能!)
session.QueryOver(() => provider)
       .JoinAlias(() => provider.Employers, () => employer)
       .SelectList(list => list.Select(() => provider.Id).WithAlias(() =>     peDTO.ProviderId)
                               .Select(() => employer.Id).WithAlias(() =>     peDTO.EmployerId))
       .TransformUsing(Transformers.AliasToBean<ProviderEmployerMapDTO>()).Future<ProviderEmployerMapDTO>();