Mybatis工具类JdbcTypeInterceptor运行时自动添加jdbcType属性

时间:2022-09-02 19:59:43

jdbctypeinterceptor

运行时自动添加 jdbctype 属性

拦截器签名

?
1
2
3
4
5
6
@intercepts({
    @signature(
      type = parameterhandler.class,
      method = "setparameters",
      args = {preparedstatement.class})
})

这类拦截器很少见,所以和其他拦截器(如分页插件)等搭配使用时不需要考虑顺序。

这个插件最适合的场景可能就是 oracle 数据库,可以自动给所有方法添加 jdbctype 属性,避免 null 导致的错误。遇到这种情况时,你可以先尝试配置 setting:

?
1
2
3
<settings>
 <setting name="jdbctypefornull" value="null"/>
</settings>

如果这个配置仍然无法解决你的问题,就可以试试jdbctype插件。

说明,必看!

首先,这个插件默认情况下是适合通用 mapper 使用的!因为默认情况下,这个拦截器会处理所有继承自mapper<t> 的方法,代码如下:

?
1
2
3
4
5
//设置默认的方法,是用 mapper 所有方法
method[] methods = tk.mybatis.mapper.common.mapper.class.getmethods();
for (method method : methods) {
  methodset.add(method.getname());
}

上面这是默认的方法,如果你不是用于通用mapper,建议去掉这段代码,或者换成你自己的默认方法。

默认会自动根据java类型自动配置的jdbctype类型如下:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
//设置默认的类型转换,参考 typehandlerregistry
register(boolean.class, jdbctype.boolean);
register(boolean.class, jdbctype.boolean);
register(byte.class, jdbctype.tinyint);
register(byte.class, jdbctype.tinyint);
register(short.class, jdbctype.smallint);
register(short.class, jdbctype.smallint);
register(integer.class, jdbctype.integer);
register(int.class, jdbctype.integer);
register(long.class, jdbctype.bigint);
register(long.class, jdbctype.bigint);
register(float.class, jdbctype.float);
register(float.class, jdbctype.float);
register(double.class, jdbctype.double);
register(double.class, jdbctype.double);
register(string.class, jdbctype.varchar);
register(bigdecimal.class, jdbctype.decimal);
register(biginteger.class, jdbctype.decimal);
register(byte[].class, jdbctype.blob);
register(byte[].class, jdbctype.blob);
register(date.class, jdbctype.date);
register(java.sql.date.class, jdbctype.date);
register(java.sql.time.class, jdbctype.time);
register(java.sql.timestamp.class, jdbctype.timestamp);
register(character.class, jdbctype.char);
register(char.class, jdbctype.char);

除了上面这些默认类型外,还可以通过参数进行配置。

参数代码:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
@override
public void setproperties(properties properties) {
  string methodstr = properties.getproperty("methods");
  if (isnotempty(methodstr)) {
    //处理所有方法
    if (methodstr.equalsignorecase("all")) {
      methodset.clear();
    } else {
      string[] methods = methodstr.split(",");
      for (string method : methods) {
        methodset.add(method);
      }
    }
  }
  //手动配置
  string typemapstr = properties.getproperty("typemaps");
  if (isnotempty(typemapstr)) {
    string[] typemaps = typemapstr.split(",");
    for (string typemap : typemaps) {
      string[] kvs = typemap.split(":");
      if (kvs.length == 2) {
        register(kvs[0], kvs[1]);
      }
    }
  }
}

从代码可以看到,支持下面两个参数:

  • methods:拦截的方法,如果配置为all,就会拦截所有的方法,你可以配置为方法名用逗号隔开的形式。
  • typemaps:配置 java 到 jdbctype 的类型映射,使用如:java1:jdbctype1,java2:jdbctype2这种形式进行配置,java1代表具体的类型,要用全限定名称方式。jdbctype 的值参考 org.apache.ibatis.type.jdbctype枚举。

配置方式

?
1
2
3
4
5
6
<plugins>
  <plugin interceptor="tk.mybatis.plugin.jdbctypeinterceptor">
    <property name="methods" value="all"/>
    <property name="typemaps" value="java.lang.string:varchar"/>
  </plugin>
</plugins>

特别注意,上面配置的两个参数只是示例,不要照抄,最简单的就是下面这样配置:

?
1
2
3
<plugins>
  <plugin interceptor="tk.mybatis.plugin.jdbctypeinterceptor"/>
</plugins>

因为这个插件就一个类,所以有什么问题自己看源码解决,发现bug可以提!

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,谢谢大家对服务器之家的支持。如果你想了解更多相关内容请查看下面相关链接

原文链接:https://blog.csdn.net/isea533/article/details/58307149