2010-08-09 2 views
4

DetachedCriteria에 대해 documentation을 읽습니다. 설명서에는 투영에 대한 별칭 설정이 선택 사항임이 명확하게 나와 있습니다. 그러나 별칭을 생략 할 때마다 내 모델 속성에 데이터가 없습니다. 다음은 두 가지 테스트 모델입니다.선택 사항 인 경우 내 영사를 별명으로 설정해야하는 이유는 무엇입니까?

[ActiveRecord("INCIDENT")] 
public class Incident : ActiveRecordBase<Incident> 
{ 
    [PrimaryKey(PrimaryKeyType.Native, "INCIDENT_ID", ColumnType = "Int32")] 
    public virtual int IncidentId { get; set; } 

    [Property("CREATION_DATETIME", ColumnType = "DateTime")] 
    public virtual DateTime? CreationDatetime { get; set; } 

    [BelongsTo("CAUSE_CD")] 
    public virtual Cause Cause { get; set; } 
} 

[ActiveRecord("CAUSE")] 
public class Cause : ActiveRecordBase<Cause> 
{ 
    [PrimaryKey(PrimaryKeyType.Native, "CAUSE_CD", ColumnType = "String")] 
    public virtual string CauseCd { get; set; } 

    [Property("CAUSE_DESC", ColumnType = "String", NotNull = true)] 
    public virtual string CauseDesc { get; set; } 
} 

다음은 데이터베이스를 쿼리하는 데 사용하는 항목입니다.

DetachedCriteria incidentCriteria = DetachedCriteria.For<Incident>("i") 
.SetProjection(Projections.ProjectionList() 
    .Add(Projections.Property("i.IncidentId")) 
    .Add(Projections.Property("i.CreationDatetime")) 
) 
.SetResultTransformer(Transformers.AliasToBean<Incident>()); 
IList<Incident> incidents = Incident.FindAll(incidentCriteria); 

별칭을 설정하지 않으면 두 투영 속성이 채워지지 않습니다. 그래서 내 질문은, 왜 별칭 선택입니까? 나는 다른 것을 놓치고 있다고 확신한다. 그러나 임의의 별칭 (예 : abc)을 입력하면 인시던트 클래스에서 속성 "abc"를 찾을 수 없다는 오류를 반환합니다. 공정하게, 나는 적절한 별칭을 추가하여 내 속성 이름과 일치시킵니다. 그리고 짜잔! 이제 내 속성에 속성이 채워집니다.

이제 조회 테이블을 쿼리 할 때 문제가 발생합니다. 내 ProjectionList에

.Add(Projections.Property("c.CauseDesc"), "CauseDesc") 

을 추가하고

.CreateCriteria("i.Cause", "c") 

를 추가하지만 지금은 내 사고 모델 "CauseDesc"를 찾을 수 없습니다 뿌려줍니다.

전체적인 시련에는 무엇이 누락 되었습니까?

업데이트 : 다음 코드

IList<Incident> results = sess.CreateCriteria<Incident>("i") 
    .SetProjection(Projections.ProjectionList() 
     .Add(Projections.Property("i.IncidentId"), "IncidentId") 
     .Add(Projections.Property("i.CreationDatetime"), "CreationDatetime") 
     .Add(Projections.Property("c.CauseDesc"), "CauseDesc") 
    ) 
    .Add(Expression.Gt("i.IncidentId", 1234567)) 
    .CreateAlias("Cause", "c") 
    .List<Incident>(); 

이 (내가 프로파일 러로 체크) 유효한 쿼리를 생성하지 않습니다하지만 내 일반적인 목록을 채우는 문제가있는 것 같다. 그것은 나에게 "\"System.Object [] \ "값이 \"oms_dal.Models.Incident \ "유형이 아니기 때문에이 일반 콜렉션에서 사용할 수 없습니다. \ r \ n 매개 변수 이름 : 값". 그러나 프로젝션을 사용하지 않으면 모든 것이 잘 작동하지만 그다음 원하지 않는 50 개 이상의 필드를 선택합니다. 이 상황에서 DTO를 사용해야한다는 것을 의미합니까?

답변

5

당신도 ... 같은

.Add(Projections.Property("i.IncidentId"), "IncidentId") 

을 투사 속성 이름을 지정하는 데 일반적으로 동일한 도메인 객체에 투영하지 않습니다 필요합니다. 당신은 몇 가지 기준 (안 DTO), 다음 예측을 설정하지 일치하는 사건을 원하는 경우에 당신은 ... 다음

public class IncidentDTO 
{ 
    public int IncidentID { get; set; } 
    public DateTime CreationDatetime { get; set; } 
} 

및 ...

.SetProjection(Projections.ProjectionList() 
    .Add(Projections.Property("i.IncidentId"), "IncidentId") 
    .Add(Projections.Property("i.CreationDatetime"), "CreationDatetime") 
) 
.SetResultTransformer(Transformers.AliasToBean<IncidentDTO>()); 

을 같은 DTO 사건을 만들어야합니다 /의 ResultTransformer . 대신이 작업을 수행하면됩니다.

IList<Incident> incidents = session.CreateCriteria<Incident>() 
    .CreateAlias("Cause", "c") //now you can access Cause properties via `c.` 
    .Add(Restrictions.Eq("c.CauseDesc", "some cause")) 
    .List<Incident>(); 

루트 기준 개체에 별칭이 필요하지 않은 방법을 확인하십시오. 도움이된다면, 나는 초기 객체를 위해서만 CreateCriteria를 사용합니다. 자식 개체를 참조해야하는 경우 CreateAlias를 사용합니다.

+0

마지막 예제에서 "값 \"System.Object [] \ "이 (가) \"oms_dal.Models.Incident \ "유형이 아니므로이 일반 콜렉션에서 사용할 수 없습니다. \ r \ n 매개 변수 이름 : 값 "을 설정합니다. 내 업데이트 된 답변을보십시오. – Mike

+0

예, 프로젝션을 설정하면 DTO를 사용해야합니다.투영은 도메인 객체의 속성로드를 제어하는 ​​데 사용되지 않습니다. 이들은 데이터를 표시 목적으로 DTO에 투영하는 데 사용됩니다. – dotjoe

+0

고마워요! 이제는 내게 더 명확 해. :) – Mike

관련 문제