0

私は Hibernate が初めて@OneToOneで、コードで機能することができません。
多くの読書の後、私は分離株の例を作成し、コミュニティの助けを求めることを考えました.

3 つのクラスがあるとします。1 つの抽象 (Class_A) と、それを継承する 2 つのクラス (Class_B / Class_C)。Class_C には、Class_B への一方向ポインタがあります。
(図を用意しましたが、サイトに掲載できません:-/)。

ノート:

  1. Pure Java + Hibernate 3.6.0 Final + Oracle 11g。
  2. 継承戦略 = Table per Concrete Class
  3. で開発hibernate.hbm2ddl.auto=update
  4. 私たちのコードでは、 Class_B は独自のテーブルを必要とするため、 no @Embeddable.
  5. 私たちのコードでは、 Class_C も抽象的であり、単純化された例で示されているものではありません。

コード

クラス_A

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public abstract class Class_A {
    @Id
    public long myId = 0;
}

Class_B

@Entity
@Table(name = "Class_B")
public class Class_B extends Class_A {
    private String myString = "Hellos - I'm Class_B!";
}

Class_C

@Entity
@Table(name = "Class_C")
public class Class_C extends Class_A {
    private String myString = "Hellos - I'm Class_C!";

    @OneToOne(cascade=CascadeType.ALL, fetch=FetchType.EAGER)
    @NotNull
    private Class_B classB;

    public void setClassB(Class_B classB) {
        this.classB = classB;
    }
}

休止状態のコード

StatelessSession statelessSession = sessionFactory.openStatelessSession();
Class_C classC = new Class_C();
classC.myId = 92;
Class_B classB = new Class_B();
classB.myId = 8000;
classC.setClassB(classB);

statelessSession.beginTransaction();
statelessSession.insert(classC);
statelessSession.getTransaction().commit();
statelessSession.close();

問題

  1. Hibernateではinsert(classC)、Class_C を挿入する SQL のみを発行します。Class_B を挿入する SQL はありません。Oracle で Class_C の詳細が表示されますが、Class_B のテーブルは空です。
    SQLは次のとおりです。

    Hibernate: Class_C (classB_myId、myString、myId) 値 (?、?、?) に挿入します。

  2. getTransaction().commit()爆発する

これ:

java.sql.BatchUpdateException: ORA-02291: integrity constraint (NDP.FK9619CF1CAD47EF0F) violated - parent key not found
at oracle.jdbc.driver.OraclePreparedStatement.executeBatch(OraclePreparedStatement.java:17660)
at oracle.jdbc.driver.OracleStatementWrapper.executeBatch(OracleStatementWrapper.java:771)
at com.mchange.v2.c3p0.impl.NewProxyPreparedStatement.executeBatch(NewProxyPreparedStatement.java:1723)
at org.hibernate.jdbc.BatchingBatcher.doExecuteBatch(BatchingBatcher.java:70)
at org.hibernate.jdbc.AbstractBatcher.executeBatch(AbstractBatcher.java:268)
at org.hibernate.impl.StatelessSessionImpl.managedFlush(StatelessSessionImpl.java:333)
at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:133)
...

質問してください

  1. なぜこれが機能しないのですか...何が間違っていますか?
  2. レガシー コードでは、アプリケーションは一意の ID 番号を割り当て、生成された ID を使用するつもりはありません。したがって@GenerateValue、私たちの@Id場合は考慮されません。これが失敗する理由ですか?
  3. と+の違いは何@OneToOne(cascade = CascadeType.ALL)ですか?@OneToOne@Cascade({CascadeType.ALL})

どうもありがとう!

  • テン・オブ・ア・カインド
4

2 に答える 2

0

Hibernate のドキュメントを確認してください。そこに述べられているように:

ステートレス セッションを使用して実行される操作は、関連付けられたインスタンスにカスケードされることはありません。 http://docs.jboss.org/hibernate/core/3.3/reference/en-US/html/batch.html#batch-statelesssession

org.hibernate.StatelessSessionを使用すると、オブジェクトを挿入するときにオブジェクトの相互依存関係を処理できます。org.hibernate.Sessionを使用している場合はそうではありません。

この場合、classC オブジェクトの前にclassB オブジェクトを永続化して機能させる必要があります。永続的な順序は重要です。永続化の順序を変更すると、org.hibernate.exception.ConstraintViolationExceptionが発生します。永続コンテキストがないため、ステートレス セッションを使用する場合は慎重に選択してください。

statelessSession.beginTransaction();

statelessSession.insert(classB); // <- Persisting classB

statelessSession.insert(classC);
statelessSession.getTransaction().commit();
statelessSession.close();

Hibernate 3.6.0 Final + MySQL 5.0.51a-24 でテスト済み

于 2011-02-15T17:26:07.513 に答える
0

原因はきっと

StatelessSession statelessSession = sessionFactory.openStatelessSession(); 

Session代わりに法線を使用してみてください:

Session session = sessionFactory.openSession(); 

StatelessSession特別な状況でのみ使用する特別な目的のツールです。通常の操作では、常に を使用する必要がありますSession。休止状態のドキュメントから:

あるいは、Hibernate は、切り離されたオブジェクトの形式でデータベースとの間でデータをストリーミングするために使用できるコマンド指向の API を提供します。StatelessSession には永続コンテキストが関連付けられておらず、高レベルのライフサイクル セマンティクスの多くは提供されません。特に、ステートレス セッションは、第 1 レベルのキャッシュを実装せず、第 2 レベルまたはクエリ キャッシュとも対話しません。トランザクションのライトビハインドまたは自動ダーティ チェックは実装されていません。ステートレス セッションを使用して実行される操作は、関連付けられたインスタンスにカスケードされることはありません。

于 2011-02-15T16:01:16.413 に答える