Mybatis类型转换

Mybatis类型转换

1.1     目录

1.2     建立TypeHandler

1.2.1    TypeHandler接口

1.2.2    BaseTypeHandler抽象类

1.3     注册TypeHandler

1.4     Mybatis自动获取TypeHandler

1.5     Mybatis中自动注册的TypeHandler

 

 

1.2     建立TypeHandler

我们知道java有java的数据类型,数据库有数据库的数据类型,那么我们在往数据库中插入数据的时候是如何把java类型当做数据库类型插入数据库,在从数据库读取数据的时候又是如何把数据库类型当做java类型来处理呢?这中间必然要经过一个类型转换。在Mybatis中我们可以定义一个叫做TypeHandler类型处理器的东西,通过它可以实现Java类型跟数据库类型的相互转换。下面将就如何建立自己的TypeHandler做一个简要介绍。

1.2.1  TypeHandler接口

       在Mybatis中要实现自己的TypeHandler就需要实现Mybatis为我们提供的TypeHandler接口。在TypeHandler中定义了四个方法:

Java代码  收藏代码
  1. public interface TypeHandler<T> {  
  2.    
  3.     /** 
  4.      * 用于定义在Mybatis设置参数时该如何把Java类型的参数转换为对应的数据库类型 
  5.      * @param ps 当前的PreparedStatement对象 
  6.      * @param i 当前参数的位置 
  7.      * @param parameter 当前参数的Java对象 
  8.      * @param jdbcType 当前参数的数据库类型 
  9.      * @throws SQLException 
  10.      */  
  11.     void setParameter(PreparedStatement ps, int i, T parameter,  
  12.            JdbcType jdbcType) throws SQLException;  
  13.    
  14.     /** 
  15.      * 用于在Mybatis获取数据结果集时如何把数据库类型转换为对应的Java类型 
  16.      * @param rs 当前的结果集 
  17.      * @param columnName 当前的字段名称 
  18.      * @return 转换后的Java对象 
  19.      * @throws SQLException 
  20.      */  
  21.     T getResult(ResultSet rs, String columnName) throws SQLException;  
  22.    
  23.     /** 
  24.      * 用于在Mybatis通过字段位置获取字段数据时把数据库类型转换为对应的Java类型 
  25.      * @param rs 当前的结果集 
  26.      * @param columnIndex 当前字段的位置 
  27.      * @return 转换后的Java对象 
  28.      * @throws SQLException 
  29.      */  
  30.     T getResult(ResultSet rs, int columnIndex) throws SQLException;  
  31.    
  32.     /** 
  33.      * 用于Mybatis在调用存储过程后把数据库类型的数据转换为对应的Java类型 
  34.      * @param cs 当前的CallableStatement执行后的CallableStatement 
  35.      * @param columnIndex 当前输出参数的位置 
  36.      * @return 
  37.      * @throws SQLException 
  38.      */  
  39.     T getResult(CallableStatement cs, int columnIndex) throws SQLException;  
  40.    
  41. }  

 

       现在假设我们有一个实体对象User,其中有一个属性interests是String数组类型,如下所示:

Java代码  收藏代码
  1. public class User {  
  2.    
  3.     private int id;  
  4.     private String name;  
  5.     private int age;  
  6.     private String[] interests;  
  7.    
  8.     public int getId() {  
  9.        return id;  
  10.     }  
  11.    
  12.     public void setId(int id) {  
  13.        this.id = id;  
  14.     }  
  15.    
  16.     public String getName() {  
  17.        return name;  
  18.     }  
  19.    
  20.     public void setName(String name) {  
  21.        this.name = name;  
  22.     }  
  23.    
  24.     public int getAge() {  
  25.        return age;  
  26.     }  
  27.    
  28.     public void setAge(int age) {  
  29.        this.age = age;  
  30.     }  
  31.    
  32.     public String[] getInterests() {  
  33.        return interests;  
  34.     }  
  35.    
  36.     public void setInterests(String[] interests) {  
  37.        this.interests = interests;  
  38.     }  
  39.    
  40.     @Override  
  41.     public String toString() {  
  42.        return "User [age=" + age + ", id=" + id + ", interests="  
  43.               + Arrays.toString(interests) + ", name=" + name + "]";  
  44.     }  
  45.      
  46. }  

 

我们需要把它以拼接字符串的形式存到数据库中,然后在取出来的时候又把它还原为一个String数组。这个时候我们就可以给它定义一个TypeHandler专门来处理String数组类型和数据库VARCHAR类型的相互转换。在这里我们建立一个名叫StringArrayTypeHandler的TypeHandler,代码如下所示:

Java代码  收藏代码
  1. package com.tiantian.mybatis.handler;  
  2.    
  3. import java.sql.CallableStatement;  
  4. import java.sql.PreparedStatement;  
  5. import java.sql.ResultSet;  
  6. import java.sql.SQLException;  
  7. import java.sql.Types;  
  8.    
  9. import org.apache.ibatis.type.JdbcType;  
  10. import org.apache.ibatis.type.TypeHandler;  
  11.    
  12. public class StringArrayTypeHandler implements TypeHandler<String[]> {  
  13.    
  14.        public String[] getResult(ResultSet rs, String columnName)  
  15.                      throws SQLException {  
  16.               String columnValue = rs.getString(columnName);  
  17.               return this.getStringArray(columnValue);  
  18.        }  
  19.    
  20.        public String[] getResult(ResultSet rs, int columnIndex)  
  21.                      throws SQLException {  
  22.               String columnValue = rs.getString(columnIndex);  
  23.               return this.getStringArray(columnValue);  
  24.        }  
  25.    
  26.        public String[] getResult(CallableStatement cs, int columnIndex)  
  27.                      throws SQLException {  
  28.               // TODO Auto-generated method stub  
  29.               String columnValue = cs.getString(columnIndex);  
  30.               return this.getStringArray(columnValue);  
  31.        }  
  32.    
  33.        public void setParameter(PreparedStatement ps, int i, String[] parameter,  
  34.                      JdbcType jdbcType) throws SQLException {  
  35.               if (parameter == null)  
  36.                      ps.setNull(i, Types.VARCHAR);  
  37.               else {  
  38.                      StringBuffer result = new StringBuffer();  
  39.                      for (String value : parameter)  
  40.                             result.append(value).append(",");  
  41.                      result.deleteCharAt(result.length()-1);  
  42.                      ps.setString(i, result.toString());  
  43.               }  
  44.        }  
  45.    
  46.        private String[] getStringArray(String columnValue) {  
  47.               if (columnValue == null)  
  48.                      return null;  
  49.               return columnValue.split(",");  
  50.        }  
  51.    
  52. }  

 

1.2.2  BaseTypeHandler抽象类

       在实现自己的TypeHandler时,除了上面提到的实现最原始的接口之外,Mybatis还为我们提供了一个实现了TypeHandler接口的抽象类BaseTypeHandler。所以我们也可以通过继承BaseTypeHandler来实现自己的TypeHandler。

       我们先来看一下BaseTypeHandler类的定义:

Java代码  收藏代码
  1. public abstract class BaseTypeHandler<T> extends TypeReference<T> implements TypeHandler<T> {  
  2.    
  3.   protected Configuration configuration;  
  4.    
  5.   public void setConfiguration(Configuration c) {  
  6.     this.configuration = c;  
  7.   }  
  8.    
  9.   public void setParameter(PreparedStatement ps, int i, T parameter, JdbcType jdbcType) throws SQLException {  
  10.     if (parameter == null) {  
  11.       if (jdbcType == null) {  
  12.         throw new TypeException("JDBC requires that the JdbcType must be specified for all nullable parameters.");  
  13.       }  
  14.       try {  
  15.         ps.setNull(i, jdbcType.TYPE_CODE);  
  16.       } catch (SQLException e) {  
  17.         throw new TypeException("Error setting null for parameter #" + i + " with JdbcType " + jdbcType + " . " +  
  18.              "Try setting a different JdbcType for this parameter or a different jdbcTypeForNull configuration property. " +  
  19.              "Cause: " + e, e);  
  20.       }  
  21.     } else {  
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值