2009-06-10 2 views
0

내가 스튜어트 찰스와 제임스 그레고리 말을 들었다으로 업데이트유창함 - NHibernate에 : 차별 개체가 hierrachy를로드하려면 제대로

글쎄, 내 모델로 시작 충분히 이상한. 서로 다른 종류의 관계를 구별하면서 클래스 간의 양방향 참조가 분명히 이루어지지 않았으며 분명히 아주 좋은 이유가 있습니다.

모델을 뒤집어서 사용자와 Fiches간에 HasManyToMany를 사용하여 다른 모델로 변경 한 다음 몇 가지 코딩 유효성 검사를 추가하여 사용자가 둘 이상의 Fiche에 연결할 수 없도록했습니다.

그래서 내가 경고의 종류는 이런 종류의 문제에 대한 답변을 추측 : "하지 마")

대답 할 시간을내어 주셔서 모두 감사합니다!


안녕하세요 모두

유창함 NHibernate에의 올바른 사용에 대한 경로는 하드 하나이며, 난 정말 난처한 상황에 빠진 느낌이 들기 시작 이후, 나는 그것이 도움을 요청 해치지 않을 것이라고 생각. 여기에 문제가 있습니다.

범인

나는 다음과 같은 두 개의 클래스, 피시와 사용자가. Fiche에는 사용자 소유자가 있어야하며 많은 사용자 추종자가있을 수 있습니다. 반면에 사용자는 선택적으로 하나의 Fiche에만 연결될 수 있습니다.

Public Class Fiche 
    Inherits EntityUpdateTrace(Of Fiche) 

    Private m_Owner As User 
    Public Property Owner() As User 
     ' snip 

    Private m_Followers As IList(Of User) 
    Public Property Followers() As IList(Of User) 
     ' snip 

End Class 

Public Class User 
    Inherits EntityUpdateTrace(Of User) 

    Private m_Fiche As Fiche 
    Public Property Fiche() As Fiche 
     ' snip 

End Class 

나는 다음 매핑

Public Class FicheMapping 
Inherits ClassMap(Of Fiche) 
Public Sub New() 
    [Not].LazyLoad() 
    Id(Function(f As Fiche) f.Id).GeneratedBy.GuidComb() 
    References(Of User)(Function(f As Fiche) f.Owner).Not.Nullable() 
    HasMany(Of User)(Function(f As Fiche) f.Followers).Inverse() 
End Sub 
End Class 

Public Class UserMapping 
    Inherits ClassMap(Of User) 
    Public Sub New() 
     [Not].LazyLoad() 
     Id(Function(a As User) a.Id).GeneratedBy.GuidComb() 
     References(Of Fiche)(Function(a As User) a.Fiche).Nullable() 
    End Sub 
End Class 

질문을합니다 (EntityUpdateTrace 기본 클래스는 프리 세이브/PreUpdate 사용/수정 시간을하는 GUID ID를 포함 만들기)

무엇 내가 잘못하고있는거야? :) 나는 믿을 수 없을만큼 간단한 것처럼 보이지만이 모델을 작동시키는 것처럼 보이지 않습니다.

  • 피처는 모든 사용자를 관련 항목으로로드합니다. 논리적 인 소리, 그리고 내가 특정 매개 변수를 차별해야한다고 생각하지만, 전적으로 데이터베이스와 관련이 있기 때문에 (나는 도메인 위생의 연습 문제로 클래스를 계속 깨끗하게 유지하려고 노력하고있다) 정말 좋아하지 않는다. 그래서 Fiche가 매우 중요하다면 Fiche는 Alice에 의해 만들어지고 Bob이 따라옵니다. 추종자를 다시로드 할 때 Alice와 Bob을 찾습니다. 두 가지 유형의 사용자를 차별하는 방법이 있습니까?

  • 나는 즉시 내가 (피시) f.Followers으로 함수 f()

    hasMany의 (사용자의)에 매핑 변경으로 주문 추종자를 유지하기 위해 데이터베이스의 목록을 사용하려면,하지만 것 .AsList().역()

다음과 같은 오류가 나옵니다 :

null index column for collection: Followers

이 오류에 대한 정보의 양이 정말 압도적 아니라, 저를지도하는 난이 모델에 길을 잘못 복용하고있어 가정 할 , 나는 주먹 문제로 나를 인도한다. .. 내가 도대체 ​​뭘 잘못하고 있니?

읽어 주셔서 감사 드리며 이에 대한 통찰력을 얻으십시오!

답변

1

List 목록의 의미로 인해 오류가 발생했습니다. 가방은 기본적으로 IList에 매핑되기 때문에 까다로운 일이지만, 이는 .NET 프레임 워크에 "bag"의미가있는 컬렉션 유형이 없기 때문입니다. 개념적으로 "가방"은 물건이 단지 가방에 던져지고 어떤 순서로든 제거되고 가방 내부를 쉽게 이동할 수 있기 때문에 순서가 없습니다. 그러나 목록은 본질적으로 정렬되고 인덱싱됩니다 (추가 의미론이있는 배열로 생각하므로 각 요소에 고유 한 인덱스 값이 있습니다). 당신이 얻는 에러 메시지는 NHibernate가 각각의 엘리먼트에 대한 인덱스 값을 저장하는 컬럼을 원한다는 것을 나타냅니다. (유일해야하고 IList, 앤티 정수 값이기 때문에 유일해야합니다). 인덱스 열이 없으므로 쿼리에 ORDER BY 절을 추가하여 다른 방법으로 정렬해야합니다.

첫 번째 문제는 어떻게 작업하고 있는지 다시 생각해 볼 필요가 있습니다. 사실, 당신은 NHibernate filters을 활용할 수 있을지 모르지만 어떻게 작동할지 말할 수있는 경험이 없습니다. 귀하의 Followers 컬렉션은 실제로 Fiche (모두 User, 참조 번호 Fiche)과 관련된 모든 사용자이므로 RelatedUsers과 같습니다. 리포지토리 패턴을 사용하면 UserOwner과 같지 않은 RelatedUsers을 쿼리하는 FindFollowers(Fiche fiche)과 같은 메서드를 사용할 수 있습니다. 이 패턴은 User을 주문하려고했기 때문에 추가로 도움이 될 수 있습니다. 같은 뭔가 (C#을 기준 쿼리) :

session.CreateCriteria(typeof(Fiche)) 
    .CreateCriteria("RelatedUsers", JoinType.InnerJoin) 
     .Add(Restrictions.Not(Restrictions.Eq("Id", fiche.Owner.Id))) 
     .AddOrder(Order.Asc("PropertyNameToOrderBy")) 
     .List<User>(); 
+0

첫 번째 문제에 대해 목록의 색인 된 열이 매핑 된 poco 클래스의 책임이되어야하는 이유는 무엇인지 모르겠지만 이상하게 느껴집니다. 나는 완전히 이해하고 있는지 잘 모르겠습니다. 내가 서있는 곳에서 당신이 제안하는 것은 Fiche 매핑에서 Followers 관계를 가져와 Repository 쿼리에 대한 호출로 대체해야한다는 것입니다. 그러나 예제로 제공 한 쿼리는 매핑 된 관계 (귀하의 경우에는 RelatedUsers라고 함)를 사용합니다. 내가 쿼리를 시도하고 그것은 재산에 대해 불평했다 ... – samy

+0

그것은 어떤 부동산에 대해 불평 했습니까? 오류 메시지는 무엇입니까? –

+0

Fiche 클래스와 Fiche 매핑을 변경하여 Followers 속성을 제거했습니다. 내가 쿼리를 시도하면 다음과 같은 오류가 발생합니다 : 속성을 해결할 수 없습니다 : 추종자 : DALAGScan.Fiche 나는 어느 시점에서 내가 오해한다고 생각합니다. 왜냐하면 한 손으로는 내가 isn 속성에 대해 쿼리 할 수 ​​없다는 것을 이해합니다. 맵핑되지 않았지만 다른 한편으로 맵핑하면 Nhibernate에서 원하는 동작을 얻지 못합니다 ... – samy

1

그것은 당신이 필요 같은 소리 다 대다 대신 일대의. 이렇게하면 여러 사용자가 단일 사용자를 참조 할 수 있습니다.

컬렉션의 순서는 테이블에 인덱스 열이 없으면 AsList이 작동하지 않습니다. 이것은 갭이없는 각 레코드의 숫자 값을 포함하는 열입니다. 이 동작을 원하지 않으면 order-by 속성을 사용해야합니다.

+0

마침내 당신의 방식대로하려고했다. UniqueIntId라는 매핑 된 열을 각 사용자마다 틈이없는 다른 정수로 초기화했습니다. 그런 다음 매핑을 변경하고 AsList() 메서드에 UniqueIntId를 인덱스로 사용하고 싶다고 말했습니다. 아아, 행운이 없으므로 같은 방식으로 행동해야한다고 주장했습니다. 온라인에서이 기능의 예가 있습니까? – samy

관련 문제