2

私は次のモデルを持っています:

ReportReportSectionおよび ReportSectionProperty

レポートには0から多数のReportSectionsがあり、ReportSectionには0から多数のReportSectionPropert -iesがあります。これは、3レベルの深さのオブジェクトグラフとしての資格があります。

新しいレポートを作成し、それにいくつかのセクションを追加してから、いくつかのプロパティを追加します。レポートを永続化しようとすると、次のエラーが発生します。

Caused by: org.apache.openjpa.lib.jdbc.ReportingSQLException: ERROR: insert or update on table "report_section" violates foreign key constraint "fk_report_section_report"
  Detail: Key (id_node)=(186) is not present in table "report". {prepstmnt 20859482 INSERT INTO core.report_section (index_section, name, report_section_type, id_node) VALUES (?, ?, ?, ?) [params=?, ?, ?, ?]} [code=0, state=23503]

つまり、OpenJPAはオブジェクトグラフを永続化していますが、どういうわけかそれは途中から始まりました。id_node 186は確かにレポートテーブルの次のIDですが、明らかに、ReportSectionが保存されているときにそのオブジェクトは保存されません。

セクションまたはプロパティを追加する各操作の間にem.persist(report)、次にem.flush()を配置すると、すべてが機能します。これは行く方法ですか?

セクションにプロパティを追加しない場合、em.flush()がなくても、レポートの永続化は機能します。

私はJPAプロバイダーとしてOpenJPA2.0.3を使用しています。


たぶん、コードのいくつかの関連部分:

Report.java

public class Report{

    @OneToMany(targetEntity = ReportSection.class, cascade = CascadeType.ALL, mappedBy="report")
    private List reportSections;

    public void addReportSection(ReportSection section){
        synchronized (this) {
            if (getReportSections() == null)
                reportSections = new ArrayList();
            reportSections.add(section);
            section.setReport(this);
        }
    }
}

ReportSection.java

パブリッククラスReportSection{

    @ManyToOne
    @JoinColumn(name = "id_node")
    プライベートレポートレポート;

    @OneToMany(targetEntity = ReportSectionProperty.class、cascade = CascadeType.ALL、mappedBy = "reportSection")
    プライベートリストreportSectionProperties;

    public void setReport(レポートレポート){
        this.report=レポート;
    }

    public void addReportSectionProperty(ReportSectionProperty reportSectionProperty){
        同期(これ){
            if(getReportSectionProperties()== null)
                reportSectionProperties = new ArrayList();
            reportSectionProperties.add(reportSectionProperty);
            reportSectionProperty.setReportSection(this);
        }
    }
}

ReportSectionProperty

パブリッククラスReportSectionProperty{

    @ManyToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "id_report_section")
    プライベートReportSectionreportSection;

    public void setReportSection(ReportSection reportSection){
        this.reportSection = reportSection;
    }
}
4

3 に答える 3

1

これはデッド スレッドかもしれませんが、同様の問題に直面したので、今後の参考のために、どのように解決したかを示したいと思います (失われた魂が OpenJPA に対処しなければならない場合に備えて)

OpenJPA が sql ステートメントを正しい順序で再配置できるように、このプロパティーを persistence.xml に設定してみてください。

プロパティ名="openjpa.jdbc.SchemaFactory" 値="native(ForeignKeys=true)"

http://openjpa.apache.org/faq.html#FAQ-CanOpenJPAreorderSQLstatementstosatisfydatabaseforeignkeyconstraints%253F

于 2011-03-04T15:51:36.823 に答える
0

ReportSection から Report への @ManyToOne 関係に cascade=ALL を追加してみましたか?

親 Report オブジェクトにも @Id プロパティを投稿すると役立つ場合があります。

于 2011-11-19T20:40:10.877 に答える
0

セクションまたはプロパティを追加する各操作の間に em.persist(report) と em.flush() を配置すると、すべてが機能します。これは行く方法ですか?

これは、適切なカスケード設定が定義され、双方向の関連付けが適切に構築されていれば必要ありません (もちろん、JPA プロバイダーのバグは除きます)。最初の部分は問題ないようです。しかし、私はあなたが最後の部分をどのように行うかを見たい.

于 2010-09-15T17:22:05.447 に答える