使用mybatis中的自定义TypeHandler处理PostgreSQL中的Json类型

自定义TypeHandler处理PostgreSQL Json字段
本文介绍了在使用PostgreSQL数据库时,如何结合Mybatis处理json和jsonb格式的字段。通过自定义TypeHandler,实现了对这两种类型字段的映射。在mapper.xml文件中配置自定义的typeHandler,并在需要时将json字段转换为对象。

postgres里的json格式

我们在使用postgres数据库时会使用到json格式来存放一些格式不固定的字段,postgres支持json和jsonb两种格式,两者的区别以后再说,今天说一下结合mybatis的使用方法:

  • 1. typeHandler的实现
    mybatis默认是没有实现json类型字段对应的TypeHandler,所以一般我们需要自定义mybatis的TypeHandler:
    json类型字段对应的TypeHandler的一个简单实现:
import org.apache.ibatis.type.BaseTypeHandler;
import org.apache.ibatis.type.JdbcType;
import org.apache.ibatis.type.MappedTypes;
import org.postgresql.util.PGobject;

import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

@MappedTypes({Object.class})
public class JsonTypeHandler extends BaseTypeHandler <Object> {

    private static final PGobject jsonObject = new PGobject();
    @Override
    public void setNonNullParameter(PreparedStatement preparedStatement, int i, Object o, JdbcType jdbcType) throws SQLException {
        jsonObject.setType("json");
        jsonObject.setValue(JsonUtil.toJsonString(o));
        preparedStatement.setObject(i,jsonObject);

    }

    @Override
    public Object getNullableResult(ResultSet resultSet, String s) throws SQLException {
        return JsonUtil.fromJson(resultSet.getString(s), Object.class);
    }

    @Override
    public Object getNullableResult(ResultSet resultSet, int i) throws SQLException {
        return JsonUtil.fromJson(resultSet.getString(i), Object.class);
    }

    @Override
    public Object getNullableResult(CallableStatement callableStatement, int i) throws SQLException {
        return JsonUtil.fromJson(callableStatement.getString(i), Object.class);
    }
}

jsonb类型字段对应的TypeHandler的一个简单实现:

import org.apache.ibatis.type.BaseTypeHandler;
import org.apache.ibatis.type.JdbcType;
import org.apache.ibatis.type.MappedTypes;
import org.postgresql.util.PGobject;

import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

@MappedTypes({Object.class})
public class JsonbTypeHandler extends BaseTypeHandler <Object> {

    private static final PGobject jsonObject = new PGobject();
    @Override
    public void setNonNullParameter(PreparedStatement preparedStatement, int i, Object o, JdbcType jdbcType) throws SQLException {
        jsonObject.setType("jsonb");
        jsonObject.setValue(JsonUtil.toJsonString(o));
        preparedStatement.setObject(i,jsonObject);

    }

    @Override
    public Object getNullableResult(ResultSet resultSet, String s) throws SQLException {
        if(null != resultSet.getString(s)){
            return JsonUtil.fromJson(resultSet.getString(s), Object.class);
        }
        return null ;

    }

    @Override
    public Object getNullableResult(ResultSet resultSet, int i) throws SQLException {
        if(null != resultSet.getString(i)){
            return JsonUtil.fromJson(resultSet.getString(i), Object.class);
        }
        return null ;

    }

    @Override
    public Object getNullableResult(CallableStatement callableStatement, int i) throws SQLException {
        if(null != callableStatement.getString(i)){
            return JsonUtil.fromJson(callableStatement.getString(i), Object.class);
        }
        return null ;

    }
}
  • 2.mapper.xml文件中的配置
 <resultMap id="BaseResultMap" type="com.jun.test.handler.mapper.entity.EventLog">
    <id column="uuid" jdbcType="VARCHAR" property="uuid" />
    <result column="device_name" jdbcType="VARCHAR" property="deviceName" />
    <result column="status" jdbcType="SMALLINT" property="status" />
    <result column="extend" jdbcType="OTHER" property="extend" typeHandler="com.jun.test.handler.JsonTypeHandler" />
   ...
  </resultMap>

注意在insert和update语句等用到json字段的属性都要手动去引用自定义的typeHandler。

<insert id="insert" parameterType="com.jun.test.mapper.entity.EventLog">
    insert into ec.event_log (uuid,  
      device_name, resource_name, status, 
      extend
      )
    values (#{uuid,jdbcType=VARCHAR},
      #{deviceName,jdbcType=VARCHAR},  #{status,jdbcType=SMALLINT}, 
      #{extend,jdbcType=OTHER,typeHandler=com.jun.test.handler.JsonTypeHandler}
      )
  </insert>

想要进行解析时,可以获取到该Object对象后,先转成json字符串,再转成对应的对象,如下:

 Extend extend  = JsonUtil.parser(JsonUtil.toJson(eventLog.getExtend ()), Extend .class);
评论 9
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值