简体   繁体   中英

Is navigation through composite-id's key-many-to-one possible?

Is it possible to navigate through the key-many-to-one associations of a composite-id in Nhibernate?

I have a few (legacy) tables that I mapped with the following settings:

<class name="StructureUser">
    <composite-id>
        <key-many-to-one name="Structure" class="Structure" column="STRUKTUR_ID" />
        <key-many-to-one name="User" class="User" column="USERID" />
    </composite-id>
    ...
</class>

<class name="Structure">
    <id name="Id" column="id" type="Int32" >
        <generator class="native"/>
    </id>
    <property name="Low" column="low" type="Int32" />
    ...
</class>

I want to access the "Low" property of Structure through the StructureUser class in a query. I tried every usage of the Criteria API I could think of but always an error. Here are two of the queries I tried:

ICriteria crit1 = Session.CreateCriteria(typeof(StructureUser))
    .CreateAlias("Structure", "struc")
    .Add(Restrictions.Le("struc.Low", 123));

ICriteria crit2 = Session.CreateCriteria(typeof(StructureUser))
    .Add(Restrictions.Le("Structure.Low", 123));

The error in crit1 comes from the database and says, that "struc_1.Low is not valid in this context", because NHibernate doesn't generate the join needed for the restriction in the sql command. The error in crit2 comes from NHibernate, telling me that it can't access the "Structure.Low" property on StructureUser.

I got around this problem by declaring the composite-id with key-property elements and declaring the relationships with normal many-to-one elements.

Is there another solution to this problem?

have you tried

ICriteria crit1 = Session.CreateCriteria(typeof(StructureUser))
    .CreateCriteria("Structure", "struc")
    .Add(Restrictions.Le("struc.Low", 123));

I had a similar problem.

As the original poster said, you need to add a many-to-one relationship on the element from the composite key you want to alias and you need to set the properties "insert" and "update" to "false" .

Then you can keep it in the composite-id, you don't need to change it into a key-property element.

<class name="StructureUser">
<composite-id>
    <key-many-to-one name="Structure" class="Structure" column="STRUKTUR_ID" />
    <key-many-to-one name="User" class="User" column="USERID" />
</composite-id>

<many-to-one name="Structure" class="Structure" column="STRUKTUR_ID" insert="false" update="false" />

...

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM