2011-08-30 29 views
8

Tôi đã một enum trong postgresql được xác định như sau:Clojure/postgresql: Làm cách nào để truy cập các giá trị enum từ các kết quả Jdbc4Array?

create type color as enum ('yellow', 'purple', 'white', 'black'); 

Và tôi có thể đến được Jdbc4Array như vậy:

(def colors 
    ((first (sql/with-connection db/db 
    (sql/with-query-results res 
     ["select enum_range(null::color)"] 
     (doall res)))) :enum_range)) 

Điều này cho thấy một đối tượng như thế này:

#<Jdbc4Array {yellow,purple,white,black}> 

Nhưng hãy thử những điều bình thường ném một ngoại lệ:

(.getArray colors) => stream closed 

Vì vậy, tôi hình dung tôi cần phải truy cập vào mảng trước khi kết nối được đóng:

(def colors 
    ((sql/with-connection db/db 
    (sql/with-query-results res 
     ["select enum_range(null::color)"] 
     (.getArray ((first (doall res)) :enum_range)))))) 

Nhưng trong trường hợp này tôi có được ngoại lệ này:

Method org.postgresql.jdbc4.Jdbc4Array.getArrayImpl(long,int,Map) 
is not yet implemented. 

Sinister. Tôi có thể làm gì ở đây?

Trả lời

1

Có điều gì đó rất lạ xảy ra với việc triển khai thực hiện Jdbc4Array.getArray() của Postgresql, tôi không thể làm cho nó hoạt động. Nhưng, tôi có một số thành công với .getResultSet():

user=> (with-connection db (with-query-results rs ["select enum_range(null::color)"]  
      (.getResultSet (get (first(doall rs)) :enum_range)))) 
#<Jdbc4ResultSet [email protected]> 

Bây giờ, nội dung của mảng có thể được truy cập thông qua giao diện ResultSet chuẩn. Tôi đã sao chép một số mã từ clojure.contrib.sql để làm điều đó:

(defn resultset-seq 
    [^java.sql.ResultSet rs] 
    (let [rsmeta (. rs (getMetaData)) 
    idxs (range 1 (inc (. rsmeta (getColumnCount)))) 
    keys (map (fn [i] (. rsmeta (getColumnLabel i))) idxs) 
    check-keys (or (apply distinct? keys) 
       (throw (Exception. "ResultSet must have unique column labels"))) 
    row-struct (apply create-struct keys) 
    row-values (fn [] (map (fn [^Integer i] (. rs (getObject i))) idxs)) 
    rows (fn thisfn [] 
      (when (. rs (next)) 
     (cons (apply struct row-struct (row-values)) (lazy-seq (thisfn)))))] 
    (rows))) 

mang đến cho (xin lỗi cho mã phong cách nhanh hack)

user=> (with-connection db 
     (with-query-results rs ["select enum_range(null::color)"] 
          (get (first (resultset-seq 
              (.getResultSet (get (first(doall rs)) 
                   :enum_range)))) 
           "VALUE"))) 
#<PGobject yellow> 
Các vấn đề liên quan