我有一个标准的 Spring Framework (v3.1.2) java (v1.6) 数据库支持 (postgres v9.1) Web 应用程序,它在 Apache Tomcat (v6.0) 上运行。请注意,我使用的是 Hibernate 3.6.10.Final 和 Spring Data JPA 1.2.0.RELEASE。
我有两个数据库实体类——Chapter 和 ChapterText——它们之间是一对一的关系......
@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,所以我可以向模型添加一个章节实体(名称为“章节”),然后在我的 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 中。虽然这确实有效,但似乎有点不雅。
有没有人对替代方法有任何想法?