2011-05-17 20 views
5

我喜歡在我的一個項目中使用PostgreSQL contrib中的ltree,我喜歡在數據庫頂部使用某種ORM層(Hibernate,EclipseLink)。我沒有發現有關使用此類持久性的任何有用信息。我想我必須用新的類型和相應的操作符來擴展當前的PostgreSQL方言。然而,我不知道從哪裏開始,以及做這件事的正確方法是什麼。 ltree非常像一個字符串,所以我猜應該從字符串表示開始。使用帶有Java ORM層的PostgreSQL ltree類型

有人能給我建議和/或鏈接到正在做類似事情的例子嗎?我還找不到完整的教程。

回答

3

這裏有一些指針可以幫助你。這不是一個完整的答案,但對評論來說太過分了。

Hibernate和EclipseLink都實現了JPA標準,但也有一些自己的擴展並允許自定義行爲。

我還沒有做特定的ltree的任何工作,但我認爲你可以使用java的String類,並添加一個註解到列來取代正常的列類型(這可以在標準的JPA中完成)。

@Column(columnDefinition="ltree") 
private String myLtreeValue; 

如果一個字符串的Java方面是不夠的,你可以創建自己的類,併爲它寫一個轉換器類。你可以在this question中看到一個例子。這將是持久性提供者的依賴。

當使用涉及ltree值的條件執行查詢時,您可能最好使用JPA @NamedNativeQuery註釋來定義涉及特殊運算符的查詢。舉一個例子see here

+0

謝謝,看起來很有希望。可悲的是,我們決定放棄ORM,因爲時間不夠,所以我可以稍後再嘗試。我給了它一個。 – NagyI 2011-05-18 08:39:59

+0

我們在我們的解決方案中使用了Spring的SQL行映射器。它實際上並不是一個ORM層,但我們只有幾張表,所以它仍然非常可維護。 因爲我沒有時間去測試它,而你的是這裏唯一相關的答案,我接受它。 – NagyI 2011-06-14 10:14:03

8

這樣的:

@Column(name = "dir", nullable = false, columnDefinition = "ltree") 
@Type(type = "ru.zen0n.hibernate.types.LTreeType") 
private String path; 

這:

package ru.zen0n.hibernate.types; 

import java.io.Serializable; 
import java.sql.PreparedStatement; 
import java.sql.ResultSet; 
import java.sql.SQLException; 
import java.sql.Types; 

import org.hibernate.HibernateException; 
import org.hibernate.usertype.UserType; 

public class LTreeType implements UserType { 

    @Override 
    public int[] sqlTypes() { 
     return new int[] {Types.OTHER}; 
    } 

    @SuppressWarnings("rawtypes") 
    @Override 
    public Class returnedClass() { 
     return String.class; 
    } 

    @Override 
    public boolean equals(Object x, Object y) throws HibernateException { 
     return x.equals(y); 
    } 

    @Override 
    public int hashCode(Object x) throws HibernateException { 
     return x.hashCode(); 
    } 

    @Override 
    public Object nullSafeGet(ResultSet rs, String[] names, Object owner) 
      throws HibernateException, SQLException { 
     return rs.getString(names[0]); 
    } 

    @Override 
    public void nullSafeSet(PreparedStatement st, Object value, int index) 
      throws HibernateException, SQLException { 
     st.setObject(index, value, Types.OTHER); 
    } 

    @Override 
    public Object deepCopy(Object value) throws HibernateException { 
     return new String((String)value); 
    } 

    @Override 
    public boolean isMutable() { 
     return false; 
    } 

    @Override 
    public Serializable disassemble(Object value) throws HibernateException { 
     return (Serializable)value; 
    } 

    @Override 
    public Object assemble(Serializable cached, Object owner) 
      throws HibernateException { 
     return cached; 
    } 

    @Override 
    public Object replace(Object original, Object target, Object owner) 
      throws HibernateException { 
     // TODO Auto-generated method stub 
     return deepCopy(original); 
    } 

} 
相關問題