mybatis自定义typeHandler

自定义typeHandler继承自BaseTypeHandler

第一步,实现一个集成自BaseTypeHandler的公共数据格式处理的类JsonTypeHandler:

public class JsonTypeHandler<T> extends BaseTypeHandler<T> {
 
  @Override
  public void setNonNullParameter(PreparedStatement ps, int i, T parameter, JdbcType jdbcType)
      throws SQLException {
    ps.setString(i, JSON.toJSONString(parameter));
  }
 
  @Override
  public T getNullableResult(ResultSet rs, String columnName) throws SQLException {
    return JSON.parseObject(rs.getString(columnName), getRawType());
  }
 
  @Override
  public T getNullableResult(ResultSet rs, int columnIndex) throws SQLException {
    return JSON.parseObject(rs.getString(columnIndex), getRawType());
  }
 
  @Override
  public T getNullableResult(CallableStatement cs, int columnIndex) throws SQLException {
    return JSON.parseObject(cs.getString(columnIndex), getRawType());
  }
}
第二步,自定义TypeHandler类型:

@Component
@MappedTypes(Handler.class)
public class HandlerTypeHandler extends JsonTypeHandler<Handler> {
 
}
另外我们还可以实现下面两种场景,比如我有一个Java中的Date数据类型,我想将之存到数据库的时候存成一个1970年至今的毫秒数,怎么实现?再比如我有一个User类,User类中有一个属性叫做interest,这个属性用来描述用户的爱好,它的数据类型是一个List集合,那么我想在把这个List集合存入数据库的时候能够自动的变成{XXX,XXX,XXX}这样一个字符串然后存起来,当我从数据库读取的时候也是读取到这样一个字符串,读取成功之后再自动的将之转为一个List集合

1:日期转换

@MappedJdbcTypes({JdbcType.VARCHAR})
@MappedTypes({Date.class})
public class MyDateTypeHandler extends BaseTypeHandler<Date> {
    public void setNonNullParameter(PreparedStatement preparedStatement, int i, Date date, JdbcType jdbcType) throws SQLException {
        preparedStatement.setString(i, String.valueOf(date.getTime()));
    }
 
    public Date getNullableResult(ResultSet resultSet, String s) throws SQLException {
        return new Date(resultSet.getLong(s));
    }
 
    public Date getNullableResult(ResultSet resultSet, int i) throws SQLException {
        return new Date(resultSet.getLong(i));
    }
 
    public Date getNullableResult(CallableStatement callableStatement, int i) throws SQLException {
        return callableStatement.getDate(i);
    }
}
自定义好了typeHandler之后,接下来我们需要在userMapper.xml中进行简单的配置,首先我们可以像上文说的,配置resultMap,如下:

<resultMap id="userResultMap" type="com.bean.User">
        <result typeHandler="com.db.MyDateTypeHandler" column="regTime" javaType="java.util.Date"
                jdbcType="VARCHAR"
                property="regTime"/>
    </resultMap>
配置resultMap的时候我们指定了javaType和jdbcType,同时也指定了处理的typeHandler,然后在select中使用这个resultMap:

<select id="getUser" resultMap="userResultMap">
        select * from user4
    </select>
但是这种方式有一个缺点那就是只适用于查询操作,即在查询的过程中系统会启用我们自定义的typeHandler,会将秒数转为Date对象,但是在插入的时候却不会启用我们自定义的typeHandler,想要在插入的时候启用自定义的typeHandler,需要我们在insert节点中简单配置一下,如下:

<insert id="insertUser" parameterType="org.sang.bean.User">
        INSERT INTO user4(username,password,regTime) VALUES (#{username},#{password},#{regTime,javaType=Date,jdbcType=VARCHAR,typeHandler=org.sang.db.MyDateTypeHandler})
    </insert>
也可以只配置javaType和jdbcType,如下:

<insert id="insertUser2">
        INSERT INTO user4(username,password,regTime) VALUES (#{username},#{password},#{regTime,javaType=Date,jdbcType=VARCHAR})
    </insert>
或者只配置typeHandler:

<insert id="insertUser3">
        INSERT INTO user4(username,password,regTime) VALUES (#{username},#{password},#{regTime,typeHandler=com.db.MyDateTypeHandler})
    </insert>
这三种效果都是一样的,都是在插入的时候将数据Date对象转为秒数

扫描二维码关注公众号,回复: 4298581 查看本文章


2:List集合的转换

@MappedTypes(List.class)
@MappedJdbcTypes({JdbcType.VARCHAR})
public class MyListTypeHandler extends BaseTypeHandler<List<String>> {
    public void setNonNullParameter(PreparedStatement preparedStatement, int i, List<String> strings, JdbcType jdbcType) throws SQLException {
        //1.List集合转字符串
        StringBuffer sb = new StringBuffer();
        for (String string : strings) {
            sb.append(string).append(",");
        }
        //2.设置给ps
        preparedStatement.setString(i, sb.toString().substring(0, sb.toString().length() - 1));
    }
 
    public List<String> getNullableResult(ResultSet resultSet, String s) throws SQLException {
        String[] split = resultSet.getString(s).split(",");
        return Arrays.asList(split);
    }
 
    public List<String> getNullableResult(ResultSet resultSet, int i) throws SQLException {
        String[] split = resultSet.getString(i).split(",");
        return Arrays.asList(split);
    }
 
    public List<String> getNullableResult(CallableStatement callableStatement, int i) throws SQLException {
        String[] split = callableStatement.getString(i).split(",");
        return Arrays.asList(split);
    }
}
查询:

<select id="getPerson" resultType="com.bean.Person">
        select * from person
    </select>
插入:

<insert id="insertPerson">
        INSERT INTO person(interest) VALUES (#{interest,typeHandler=com.db.MyListTypeHandler})
</insert>

猜你喜欢

转载自blog.csdn.net/ly199108171231/article/details/84345952