2

スタック オーバーフローの専門家の皆様、こんにちは。あなたの専門知識が必要です。

既存の DB で Hibernate を使用しようとしています。現在、 User オブジェクトと、それに付随する UserData オブジェクトのリストを読み込もうとしています。

DBでは(簡略化された)レイアウトは

|    User      |      |          UserData               |
----------------      -----------------------------------
uid | username |      | uid | parentuid | field | value | 

したがって、各 User オブジェクトは、UserData.parentuid = User.uid であるすべての UserData オブジェクトに一致します。

My User クラス マッピング ファイル

    <class name="com.agetor.commons.security.User" table="ac_users">
    <id name="uid" column="uid" type="long" >
        <!--<generator class="native"/>-->
    </id>
    <property name="username" column="username" />   

    <list name="fieldData" cascade="all">
        <key column="parentuid" not-null="true" />
        <index column="parentuid" />
        <one-to-many class="com.agetor.commons.fields.FieldData"/>
    </list>

</class> 

Mu UserData マッピング ファイル

    <class name="com.agetor.commons.fields.FieldData" table="ac_userdef_data">
    <id name="uid" column="uid" type="long" >
    <!--<generator class="native"/> -->
    </id>
    <!--<property name="parentuid" column="parentuid" />   -->
    <property name="fieldname" column="fieldname" />
    <property name="value" column="value" />
</class>

これまでに多くの異なる構成を試しましたが、それらのすべてにさまざまな程度の失敗がありました。ここに貼り付けたコードは機能しません。

  • そうしないと、Hibernate が「マッピングで列が繰り返されました」というエラーを出すため、parentuid プロパティはコメントアウトされています。
  • 現在、uidフィールドにはまだ「マッピングの繰り返し列」があります。<list-index />
  • UserData.parentuid が外部キーであり、リストが User.uid をキーとして使用する必要があることを指定する場所がわかりません。

誰かが助けてくれることを願っています。


1 対多と多対 1 の両方を定義すると、双方向になりませんか? 現在の作業モデルは単方向であり、UserData には User への参照がありません。Hibernate が UserData で User の get メソッドまたは set メソッドを見つけられなかったため、提案は失敗しました。

このコードは User.uid をキーとして使用し、これを UserData.parentuid 列と照合することを暗示していますか? それとも、この事実は別の場所で指定されていますか?

  <list name="fieldData" inverse="true">
    <key column="parentuid" not-null="true" />
    <one-to-many class="com.agetor.commons.fields.FieldData"/>
  </list>

私はまだHibernateを学んでおり、見つけたドキュメントと例を通して自分の道を進んでいます。

4

4 に答える 4

0

-->

<list name="fieldData" cascade="all">
    <key column="uid" not-null="true" />
    <index column="parentuid" />
    <one-to-many class="com.agetor.commons.fields.FieldData"/>
</list>

これを試してみてください。キー列をparentuidからuidに変更しました(そして、hibernateマッピングでsetを使用することをお勧めします)

乾杯、ナゲンドラ・プラサド..

于 2009-05-04T06:34:35.647 に答える
0

あなたは近いと思いますが、 List はおそらく新しい User クラスで必要なデータ構造ではありません。リストは、テーブルにはないように見える子要素の順序付けを意味します。リストのようなインデックス付きのコレクションがある場合、データにはインデックスを提供する別の列が必要なため、「マッピングで列が繰り返される」問題が発生します。

私が使用する経験則は次のとおりです。各マッピングには、マッピングするクラスの各メンバーのエントリが含まれている必要があります。たとえば、User クラスには FieldData のコレクションのエントリが必要ですが、FieldData マッピングには parentuid のエントリは必要ありません。これは、その列が FieldData クラスの要素にマップされないためです。FieldData を配置するためにのみ使用されます。親オブジェクトのコレクション内。

User オブジェクトに FieldData の順序付きコレクションが実際に含まれている場合は、代わりにセットを使用します。一方、「フィールド」名をインデックスとして使用して、代わりに FieldData のマップが必要になる可能性が高いと思います。次に、FieldData クラスは「フィールド」列をマップする必要がなく、それをメンバーとして持たず、値 (およびこのテーブルの他のフィールド - もちろん、実際に列が 1 つしかない場合) を持つだけです。マップするままにすると、文字列から文字列へのマップになってしまう可能性があります。

于 2009-02-06T00:48:20.197 に答える
0

これを試してください(ドライコード):

<class name="com.agetor.commons.security.User" table="ac_users">
  <id name="uid" column="uid" type="long" >
    <!--<generator class="native"/>-->
  </id>
  <property name="username" column="username" />   

  <list name="fieldData" inverse="true">
    <key column="parentuid" not-null="true" />
    <one-to-many class="com.agetor.commons.fields.FieldData"/>
  </list>
</class>

<class name="com.agetor.commons.fields.FieldData" table="ac_userdef_data">
  <id name="uid" column="uid" type="long" >
    <!--<generator class="native"/> -->
  </id>
  <many-to-one name="user" class="com.agetor.commons.security.User" fetch="join">
     <column name="parentuid" not-null="true"/>
  </many-to-one>
  <property name="fieldname" column="fieldname" />
  <property name="value" column="value" />
</class>

それが機能する場合は、省略したインデックスとカスケードのものを追加してみてください。

乾杯、
ミッチ

于 2009-02-03T15:51:27.960 に答える