今天在开发过程中遇见很奇怪的问题,hibernate在使用getSession().createSQLQuery(sql).setResultTransformer(Criteria.ALIAS_TO_ENTITY_MAP);
方式查询时,返回一个map对象。在对象中取得数据库为Char类型的数据,能得到的只有该字段的第一位,其余的均会被右截断:如 字段名APPENDCODE 值00000026 那么 map.get('APPENDCODE ')为 '0'
另:我的数据库是DB2。
一阵google过后,看到一篇博客的回复写的有些道理
“
真正的原因在于Hibernate使用的dialect里面
将JDBC的CHAR映射到了Character而不是String”
究竟是不是这样呢?
查证了hibernate-3.2.0.ga.zip中的源代码。其中src\org\hibernate\dialect\DB2Dialect.java文件中发现了如下代码
public DB2Dialect() { super(); registerColumnType( Types.BIT, "smallint" ); registerColumnType( Types.BIGINT, "bigint" ); registerColumnType( Types.SMALLINT, "smallint" ); registerColumnType( Types.TINYINT, "smallint" ); registerColumnType( Types.INTEGER, "integer" ); /********以下为重点**************/ registerColumnType( Types.CHAR, "char(1)" ); /********以上为重点**************/ registerColumnType( Types.VARCHAR, "varchar($l)" ); registerColumnType( Types.FLOAT, "float" ); registerColumnType( Types.DOUBLE, "double" ); registerColumnType( Types.DATE, "date" ); registerColumnType( Types.TIME, "time" ); registerColumnType( Types.TIMESTAMP, "timestamp" ); registerColumnType( Types.VARBINARY, "varchar($l) for bit data" ); registerColumnType( Types.NUMERIC, "numeric($p,$s)" ); registerColumnType( Types.BLOB, "blob($l)" ); registerColumnType( Types.CLOB, "clob($l)" ); }
如上,非常神奇的是hibernate将Char类型的注册对应类型数据库端写为了char(1)。确实让人不好理解。那么解决方案:
1 用addScalar(String arg,Type type)方法定义要返回的字段类型
2 修改相关dialect类,如
import java.sql.Types; import org.hibernate.Hibernate; import org.hibernate.dialect.DB2Dialect; public class PmDb2Dialect extends DB2Dialect { public PmDb2Dialect() { super(); registerHibernateType(Types.CHAR, "char"); } }
然后改变hibernate配置
hibernate.dialect org.hibernate.dialect.DB2Dialect 将红字改为自己的类