转自:http://jackandroid.iteye.com/blog/614032

iBATIS的自定义类型处理器TypeHandlerCallback

BATIS提供TypeHandlerCallback来提供对用户自定义类型的处理。

Java代码  
  1. public interface TypeHandlerCallback {
  2. public void setParameter(ParameterSetter setter, Object parameter)
  3. throws SQLException;
  4. public Object getResult(ResultGetter getter)
  5. throws SQLException;
  6. public Object valueOf(String s);
  7. }

它主要利用上述的三个方法来对自定义类型转换提供支持。下面我详细讲述下如何利用其来对自定义数据进行支持。

演示的内容主要是将表单中gender列中的字段转换为自己需要的内容(female<->女,male<->男)

1.数据库表people

Sql代码  
  1. create table people(
  2. id int not null auto_increment,
  3. gender varchar(10),
  4. constraint pk primary key(id)
  5. );
  6. insert into people(id,gender) values (null,'female');
  7. insert into people(id,gender) values (null,male);
  8. insert into people(id,gender) values (null,null);

表单很简单,主要提供一个自增主键和一个可以为null的性别,并插入了实验数据。

2.POJO类

Java代码  
  1. package com.xxx.pojos;
  2. public class People{
  3. private int id;
  4. private String gender;
  5. /**
  6. * @return the id
  7. */
  8. public int getId() {
  9. return id;
  10. }
  11. /**
  12. * @param id
  13. *            the id to set
  14. */
  15. public void setId(int id) {
  16. this.id = id;
  17. }
  18. /**
  19. * @return the gender
  20. */
  21. public String getGender() {
  22. return gender;
  23. }
  24. /**
  25. * @param gender
  26. *            the gender to set
  27. */
  28. public void setGender(String gender) {
  29. this.gender = gender;
  30. }
  31. @Override
  32. public String toString() {
  33. return "id:" + id + "  gender:" + gender;
  34. }
  35. }

3.TypeHandlerCallback实现类

Java代码  
  1. public class GenderTypeHandlerCallback implements TypeHandlerCallback {
  2. private static final String R_FEMALE = "女";
  3. private static final String R_MALE = "男";
  4. private static final String FEMALE = "female";
  5. private static final String MALE = "male";
  6. /**
  7. * @see com.ibatis.sqlmap.client.extensions.TypeHandlerCallback#getResult(com.ibatis.sqlmap.client.extensions.ResultGetter)
  8. */
  9. public Object getResult(ResultGetter getter) throws SQLException {
  10. if (getter.getObject() == null)
  11. {
  12. return null;
  13. }
  14. return convertDbToValue(getter.getString());
  15. }
  16. /**
  17. * @see com.ibatis.sqlmap.client.extensions.TypeHandlerCallback#setParameter(com.ibatis.sqlmap.client.extensions.ParameterSetter,
  18. *      java.lang.Object)
  19. */
  20. public void setParameter(ParameterSetter setter, Object value)
  21. throws SQLException {
  22. setter.setString(saveValueToDb((String) value));
  23. }
  24. /**
  25. * @see com.ibatis.sqlmap.client.extensions.TypeHandlerCallback#valueOf(java.lang.String)
  26. */
  27. public Object valueOf(String value) {
  28. return convertDbToValue(value);
  29. }
  30. /**
  31. * 将POJO中的值转换数据库值存储
  32. *
  33. * @param value
  34. * @return
  35. */
  36. private String saveValueToDb(String value) {
  37. if (value.equals(R_MALE))
  38. {
  39. return FEMALE;
  40. } else if (value.equals(R_FEMALE))
  41. {
  42. return MALE;
  43. } else
  44. {
  45. throw new IllegalArgumentException("参数值不正确!" + value);
  46. }
  47. }
  48. /**
  49. * 将数据库的值转换为POJO所需要的值
  50. *
  51. * @param value
  52. * @return
  53. */
  54. private String convertDbToValue(String value) {
  55. if (value.equals(FEMALE))
  56. {
  57. return R_FEMALE;
  58. } else if (value.equals(MALE))
  59. {
  60. return R_MALE;
  61. } else
  62. {
  63. throw new IllegalArgumentException("参数值不正确!" + value);
  64. }
  65. }
  66. }

4.注册TypehandlerCallback

可以在多个配置文件中进行注册:

1).sqlMapConfig.xml。全局配置注册.

2)单独的parameterMap或resultMap中注册。

本例主要演示在parameterMap中进行注册

Xml代码  
  1. <resultMap class="com.xxx.pojos.People" id="people">
  2. <result property="id" column="id" javaType="int" jdbcType="INT"/>
  3. <result property="gender" column="gender" javaType="string"   nullValue="male" jdbcType="VARCHAR"  typeHandler="com.xxx.typeHandler.GenderTypeHandlerCallback" />
  4. </resultMap>

5.运行结果

可以发现,原本在数据库中存储中gender列内容为female,male和null,但是经过自定义类型转换后相应变成了男或女。

6.遇到的问题

上述内容经过我测试没有任何问题,不过我在看到相关资料时却出现了一个问题:

在TypeHandlerCallback方法中,存在一个valueOf()方法,其主要作用是当数据库中列可以为空(null)时进行处理。相应地,你需要在注册时在result的nullValue中填写为空时的默认值,如上面的nullValue="male"。

此外,还需要特别注意的一点就是:即使你在注册时填写了nullValue='male',仍然会出现NUllpointer异常,并且跟踪发现valueOf方法没有被调用,解决方法是在getResult方法中添加 if (getter.getObject() == null) { return null; }

即需要你手动判断一次是否为null,当其结果返回null时才有会调用valueOf方法载入所设置的nullValue的值。

转载于:https://www.cnblogs.com/summer520/p/3328323.html

iBATIS的自定义类型处理器TypeHandlerCallback解决乱码相关推荐

  1. 自定义类型处理器的应用

    问题描述: 一个JSON字符串在转对象的时候报JSON解析异常的错误,我仔细看了一下错误堆栈,是枚举导致的数组越界问题. [{"fee":0,"amount": ...

  2. MyBatis自定义类型处理器 TypeHandler

    在项目开发中经常会遇到一个问题: 当我们在javabean中自定义了枚举类型或者其它某个类型,但是在数据库中存储时往往需要转换成数据库对应的类型,并且在从数据库中取出来时也需要将数据库类型转换为jav ...

  3. MyBatis核心源码剖析(SqlSession XML解析 Mapper executor SQL执行过程 自定义类型处理器 缓存 日志)

    MyBatis核心源码剖析 MyBatis核心源码剖析 1 MyBatis源码概述 1.1 为什么要看MyBatis框架的源码 1.2 如何深入学习MyBatis源码 1.3 源码分析的5大原则 2 ...

  4. MyBatis自定义类型处理器(typeHandler)

    MyBatis自定义类型处理器(typeHandler) 我们执行sql语句通过PreparedStatement语句实现,PreparedStatement会设置?值,类型处理器帮PreparedS ...

  5. 在mybatis里如何自定义类型处理器

    类型处理器(typeHandlers) MyBatis 在设置预处理语句(PreparedStatement)中的参数或从结果集中取出一个值时, 都会用类型处理器将获取到的值以合适的方式转换成 Jav ...

  6. 【Mybatis】类型处理器TypeHandler的作用与自定义

    一.什么是类型处理器 1.类型处理器(TypeHandler) MyBatis 在设置预处理语句(PreparedStatement)中的参数或从结果集中取出一个值时,都会用类型处理器将获取到的值以合 ...

  7. desc 枚举类型id_想让代码更优雅?Mybatis类型处理器了解一下!

    明确需求 在设计之初,sys_role表的enabled字段有2个可选值,其中0 代表禁用,1代表启用,而且实体类中我们使用的是Interger类型: 源码展示 /** * 有效标志 */ priva ...

  8. mybatis-plus/mybatis的组件们——拦截器、字段填充器、类型处理器、表名替换、SqlInjector(联合主键处理)

    最近有个练手的小例子,大概就是配置两个数据源,从一个数据源读取数据写到另一个数据源,虽然最后做了出来,但是不支持事务...就当是对mybatis-plus/mybatis组件使用方式的记录吧,本次例子 ...

  9. 09_Mybatis-plus类型处理器示例,例如 json 字段对象转换

    DROP TABLE IF EXISTS user;CREATE TABLE user (id BIGINT(20) NOT NULL COMMENT '主键ID',name VARCHAR(30) ...

  10. Mybatis——类型处理器TypeHandler

    在日常开发中使用mybatis时,mybatis的mapper.xml.mapper接口.entity实体一般会由mybatis-generator自动生成,其中实体的每个属性与数据库表的列一一对应, ...

最新文章

  1. java 反复器_Java数组去掉反复的方法集
  2. matlab simulink笔记02——延迟模块delay与单位延迟模块unit delay
  3. 参加 JSConf China 2019 是怎样的体验?VS Code 和 TypeScript 都很火
  4. ios UIScrollView 基础属性
  5. java导出服务器已经配置好的excel模板
  6. 【Tomcat】Tomcat下设置项目为默认项目
  7. igress+nginx部署
  8. python基础题目大全,测试你的水平,巩固知识(含答案)
  9. 【百度分享】javascript中函数调用过程中的this .
  10. Asp.net自定义控件开发任我行(4)-ViewState保存控件状态
  11. android svg按钮图标下载,安卓android中小图标使用优化(svg矢量图与iconfiy)
  12. RS485MODBUS转PROFINET网关配置-科隆OPTIFLUX7000MODBUS通信协议电磁流量计接入西门子PLC S7-1500PROFINET以太网通讯网络配置方法
  13. 3dXXX Android,Android横竖屏 mdpi hdpi xhdpi xxhdpi xxxhdpi
  14. 计算机中的文件及文件命名规则,文件名的命名规则是什么
  15. HTML网页媒体元素(视频音频)
  16. AMD首款5纳米PC处理器锐龙7000亮相,频率首破5GHz大关,单核性能提升15%
  17. 实验实例 —逻辑门设计
  18. 双因子与多因子身份验证有什么区别?
  19. DeDeCMS v5.7 SP2 前台任意用户密码修改漏洞复现
  20. 6. Java并发编程-并发包-Lock和Condition

热门文章

  1. Sql Server 日期格式化函数
  2. Sqlite和mysql的区别及优缺点
  3. IOI2008Island 基环树直径。
  4. 响应式布局与自适应式布局有什么不同
  5. java 实现在线预览功能
  6. Android推送方案分析(MQTT/XMPP/GCM)
  7. WPF程序,运行时,结束时,要运行的操作(自动保存,检查单程序)
  8. Fedora 11的新特征和简易安置教程
  9. VC里一些容易混淆的地方(转)
  10. 用Not Exists 代替Not In