EnumOrdinalUserType.java

  1. package org.itracker.persistence.dao;

  2. import org.hibernate.HibernateException;

  3. import java.sql.PreparedStatement;
  4. import java.sql.ResultSet;
  5. import java.sql.SQLException;
  6. import java.sql.Types;
  7. import java.util.Properties;

  8. /**
  9.  * Custom Hibernate UserType to persist a Java 5 enum constant as an INTEGER
  10.  * using its ordinal position.
  11.  * <p/>
  12.  * <p>Beware that the enum.ordinal() returns a is zero based that changes
  13.  * if the position of the enum members change! </p>
  14.  *
  15.  * @author johnny
  16.  */
  17. public final class EnumOrdinalUserType extends AbstractEnumUserType {

  18.     private static final int[] SQL_TYPES = {Types.SMALLINT};

  19.     /**
  20.      * Enum members, in the order they where declared.
  21.      */
  22.     @SuppressWarnings("unchecked")
  23.     private Enum[] enumValues;

  24.     /**
  25.      * Default constructor, required by Hibernate.
  26.      */
  27.     public EnumOrdinalUserType() {
  28.     }

  29.     public void setParameterValues(Properties parameters) {
  30.         super.setParameterValues(parameters);
  31.         this.enumValues = this.enumClass.getEnumConstants();
  32.     }

  33.     public Object nullSafeGet(ResultSet rs, String[] names,
  34.                               Object owner) throws HibernateException, SQLException {
  35.         final int ordinal = rs.getInt(names[0]);

  36.         return rs.wasNull() ? null : this.enumValues[ordinal];
  37.     }

  38.     public void nullSafeSet(PreparedStatement stmt, Object value,
  39.                             int index) throws HibernateException, SQLException {
  40.         if (value == null) {
  41.             stmt.setNull(index, Types.INTEGER);
  42.         } else {
  43.             stmt.setInt(index, ((Enum<?>) value).ordinal());
  44.         }
  45.     }

  46.     public int[] sqlTypes() {
  47.         return SQL_TYPES;
  48.     }

  49.     public String objectToSQLString(Object value) {
  50.         return Integer.toString(((Enum<?>) value).ordinal());
  51.     }

  52.     public String toXMLString(Object value) {
  53.         return objectToSQLString(value);
  54.     }

  55.     public Object fromXMLString(String xmlValue) {
  56.         final int ordinal;

  57.         try {
  58.             ordinal = Integer.parseInt(xmlValue);
  59.         } catch (NumberFormatException ex) {
  60.             throw new HibernateException(ex);
  61.         }
  62.         return this.enumValues[ordinal];
  63.     }

  64. }