关于hibernate3中enum类型的数据持久化问题

对需要解决的问题的描述: 
把一个enum类型的字段持久化到数据库中,写入到数据库中的值为Integer类型,且有特定的含义: 
 
我们知道,如果我们某一个pojo对象的某个属性为enum类型的话,在持久化的时候可能会出现如下两种情况: 
1、数据库中enum_col的类型为(oracle:number或者sql server:numeric) 
   @Column(name="enum_col") 
   public MyEnum getCol(){ 
      return this.col; 
   } 
此种情况下,存到数据库中的数据时col.ordinal()所返回的int数值 
2、数据库中enum_col的类型为(oracle:varchar2,或者sql server:varchar) 
   @Column(name="enum_col") 
   public MyEnum getCol(){ 
      return this.col; 
   } 
此种情况下,存储到数据库中的值为定义此enum是所使用的名字如: 
   public enum MyEnum{ 
       DATA1, 
       DATA2; 
   } 
则,如果this.col代表DATA1则写DATA1到数据库中去。
那么我们通过什么样的手段来改变这些呢?如果使用的是hibernate的话可以借助于UserType来实现: 
首先、定义一个enum MyEnumData,(在持久化的时候把其code写到数据库中去) 
package ec.snow.hib.pojos; 
public enum MyEnumData{ 
   DATA1("data1",100), 
   DATA2("data2",200), 
   DATA3("data3",300);
   private String name; 
   private int code; 
    
   public int getCode(){ 
      return this.code; 
   } 
   public String getName(){ 
      return this.name; 
   } 
   MyEnumData(String name,int code){ 
      this.name = name; 
      this.code = code; 
   } 
//辅助方法,主要在UserType的实现中通过相应的code得到MyEnumData 
 
public static MyEnumData formCode(int code){ 
 
       for(MyEnumData u:MyEnumData.values()){ 
          if(u.getCode()==code)return u; 
       } 
       return null; 
   } 
}
//******************************* 
接下来、定义相应的UserType的实现: 
package com.snow.hib.pojos;
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;
/** 
 *@author anwxAn Weixiao 
 *@version $Id$ 
 */ 
public class MyEnumDataType implements UserType { 
    
    public int[] sqlTypes() {    
        int[] types = {Types.INTEGER};          
        return types;    
    }    
   
    public Class returnedClass(){ 
        return UserTitle.class;    
    }    
   
    public boolean equals(Object x, Object y) throws HibernateException {    
        return x == y;    
    }    
   
    public int hashCode(Object x) throws HibernateException {    
        return x.hashCode();    
    }    
   
    public Object nullSafeGet(ResultSet rs, String[] names, Object owner) 
throws HibernateException, SQLException {    
        int code = rs.getInt(names[0]);    
        return rs.wasNull() ? null : MyEnumData.formCode(code);//notice code to use     
    }    
   
    public void nullSafeSet(PreparedStatement st, Object value, int index)  
throws HibernateException, SQLException {    
        if (value == null) {    
            st.setNull(index, Types.INTEGER);    
        } else {    
            st.setInt(index, ((MyEnumData) value).getCode());    
        }    
    }    
   
    public Object deepCopy(Object value) throws HibernateException {    
        return value;    
    }    
   
    public boolean isMutable() {    
        return false;    
    }    
   
    public Serializable disassemble(Object value) throws HibernateException {    
        return (Serializable) deepCopy(value);    
    }    
   
    public Object assemble(Serializable cached, Object owner) throws HibernateException {    
        return deepCopy(cached);    
    }    
   
    public Object replace(Object original, Object target, Object owner)  
throws HibernateException {    
        return deepCopy(original);    
    }      
} 
//********************************** 
最后、通过自定义的UserType来实现对enum的有效持久化 
package com.snow.hib.pojos;
import Java.io.Serializable;
import Javax.persistence.Column; 
import Javax.persistence.Entity; 
import Javax.persistence.Id; 
import Javax.persistence.Table;
import org.hibernate.annotations.Type;
/** 
 *@author anwxAn Weixiao 
 *@version 
 */ 
@Entity 
@Table(name="my_def_type") 
public class UseMyEnumData implements Serializable{    
    
    private static final long serialVersionUID = 6905822670746966787L; 
    private String id; 
    private String username;      
    private MyEnumData enumData;    
     
    @Column(updatable = true,nullable = true,name="MY_TITLE") 
    @Type(type="com.snow.hib.pojos.MyEnumDataType") 
    public MyEnumData getEnumData() {    
        return enumData;    
    }    
   
    public void setEnumData(MyEnumData data) {    
        this.enumData = data;    
    } 
     
    @Column(updatable=true,nullable = true,name="USER_NAME") 
    public String getUsername() {    
        return username;    
    }   
    public void setUsername(String username) {    
        this.username = username;    
    }
 /** 
  * @return Returns the id. 
  */ 
    @Id 
 public String getId() { 
  return id; 
 }
 /** 
  * @param id The id to set. 
  */ 
 public void setId(String id) { 
  this.id = id; 
 }     
}  
下面是测试结果: 
//***************************Test result 
       UseMyEnumData data = new UseMyEnumData(); 
          data.setId("123456"); 
          data.setTitle(MyEnumData.DATA1); 
          data.setUsername("chsi:manager"); 
          manager.saveUseMyEnumData(title); 
则数据库中写入的数据为: [123456 100 chsi:manager] 
posted @ 2014-01-07 15:28  roilat  阅读(344)  评论(0)    收藏  举报