0

Apache Tomcat(v6.0)で実行される標準のSpring Framework(v3.1.2)java(v1.6)データベースに裏打ちされた(postgres v9.1)Webアプリケーションがあります。Hibernate 3.6.10.Final and Spring DataJPA1.2.0.RELEASEを使用していることに注意してください。

2つのデータベースエンティティクラス(ChapterとChapterText)があり、それらの間には1対1の関係があります...

@Entity @Table(name="chapter")
public class Chapter implements Comparator<Chapter> {

    @Id
    @GeneratedValue(strategy=GenerationType.SEQUENCE, generator="CHAPTER_SEQ")
    @SequenceGenerator(name="CHAPTER_SEQ", sequenceName="chapter_seq", allocationSize=1)
    @Column(name="id")
    private Long id;

    @OneToOne(cascade=CascadeType.ALL, optional=false, fetch=FetchType.LAZY, orphanRemoval=true) @PrimaryKeyJoinColumn
    private ChapterText chapterText;

    // other properties plus setters and getters
}

@Entity @Table(name="chapterText")
public class ChapterText {

    @Id
    @GeneratedValue(generator="foreign")
    @GenericGenerator(name="foreign", strategy="foreign", parameters={ @Parameter(name="property", value="parent") })
    @Column(name="id")
    private Long id;

    @OneToOne(mappedBy="chapterText", optional=false)
    private Chapter parent;

    @Column(name="body") @Lob
    private String body;

    // setters and getters
}

ここで、ChapterTextには大量のテキストを保持できる可能性のある@Lobプロパティが含まれているため、ChapterクラスでchapterTextプロパティをマークして、遅延ロードされるようにしました。

OpenEntityManagerInViewFilterをセットアップして構成したので、モデルにチャプターエンティティ(「chapter」という名前)を追加できます。その後、JSPXファイルでこれを実行できるはずです...

${chapter.chapterText.body}

これにより、ChapterTextエンティティが遅延ロードされ、呼び出し元のブラウザ用に生成されたXHTMLページにbodyプロパティの値が含まれるはずです。

これは、私が何年も使用しているデータベースからの情報を表示するための非常に標準的な方法です。ただし、Postgresで@Lobプロパティを使用する必要があったのはこれが初めてです。これを行うと、次のスタックトレースが表示されます...

org.apache.jasper.JasperException: javax.servlet.ServletException: javax.servlet.jsp.JspException: javax.servlet.jsp.JspException: javax.el.ELException: Error reading 'body' on type project.vo.db.ChapterText_$$_javassist_5
.
.
.
javax.servlet.ServletException: javax.servlet.jsp.JspException: javax.servlet.jsp.JspException: javax.el.ELException: Error reading 'body' on type project.vo.db.ChapterText_$$_javassist_5
.
.
.
javax.servlet.jsp.JspException: javax.el.ELException: Error reading 'body' on type project.vo.db.ChapterText_$$_javassist_5
.
.
.
javax.el.ELException: Error reading 'body' on type project.vo.db.ChapterText_$$_javassist_5
.
.
.
org.hibernate.exception.GenericJDBCException: could not load an entity: [project.vo.db.ChapterText#1]
.
.
.
org.postgresql.util.PSQLException: Large Objects may not be used in auto-commit mode.

私が見つけたものから、Posgresは、自動コミットがfalseに設定されたトランザクションを介してアクセスされるラージオブジェクトにアクセスする必要があります。

厄介なことに、これを回避するために私が考えることができた唯一のアプローチは、@ Lobプロパティをフェッチし、@ Transactionalでマークし、表示目的で特別に作成されたBeanに値をロードするリポジトリメソッドを作成することです。それは機能しますが、少しエレガントではないようです。

誰かが別のアプローチのアイデアを持っていますか?

4

1 に答える 1